mirror of
https://github.com/hs-web/hsweb-framework.git
synced 2026-06-04 20:03:22 +08:00
优化i18n
This commit is contained in:
@@ -5,6 +5,10 @@ import lombok.AccessLevel;
|
||||
import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import org.hswebframework.web.i18n.LocaleUtils;
|
||||
import reactor.core.publisher.Mono;
|
||||
|
||||
import java.util.Locale;
|
||||
import java.util.Objects;
|
||||
|
||||
/**
|
||||
* 支持国际化消息的异常,code为
|
||||
@@ -45,11 +49,24 @@ public class I18nSupportException extends RuntimeException {
|
||||
|
||||
@Override
|
||||
public String getMessage() {
|
||||
if (Objects.equals(super.getMessage(), this.getI18nCode())) {
|
||||
return getLocalizedMessage();
|
||||
}
|
||||
return super.getMessage() != null ? super.getMessage() : getLocalizedMessage();
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getLocalizedMessage() {
|
||||
return LocaleUtils.resolveMessage(i18nCode, args);
|
||||
public final String getLocalizedMessage() {
|
||||
return getLocalizedMessage(LocaleUtils.current());
|
||||
}
|
||||
|
||||
public String getLocalizedMessage(Locale locale) {
|
||||
return LocaleUtils.resolveMessage(i18nCode, locale, getMessage(), args);
|
||||
}
|
||||
|
||||
public final Mono<String> getLocalizedMessageReactive() {
|
||||
return LocaleUtils
|
||||
.currentReactive()
|
||||
.map(this::getLocalizedMessage);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -6,10 +6,13 @@ import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import org.hswebframework.web.i18n.LocaleUtils;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.util.CollectionUtils;
|
||||
import org.springframework.util.StringUtils;
|
||||
import org.springframework.web.bind.annotation.ResponseStatus;
|
||||
|
||||
import javax.validation.ConstraintViolation;
|
||||
import java.util.*;
|
||||
import java.util.stream.Collectors;
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
@@ -31,9 +34,6 @@ public class ValidationException extends I18nSupportException {
|
||||
public ValidationException(String message, List<Detail> details, Object... args) {
|
||||
super(message, args);
|
||||
this.details = details;
|
||||
for (Detail detail : this.details) {
|
||||
detail.translateI18n(args);
|
||||
}
|
||||
}
|
||||
|
||||
public ValidationException(Set<? extends ConstraintViolation<?>> violations) {
|
||||
@@ -48,23 +48,44 @@ public class ValidationException extends I18nSupportException {
|
||||
|
||||
//{0} 属性 ,{1} 验证消息
|
||||
//property也支持国际化?
|
||||
String resolveMessage = propertyI18nEnabled ?
|
||||
LocaleUtils.resolveMessage(first.getRootBeanClass().getName() + "." + property, property)
|
||||
String propertyI18n = propertyI18nEnabled ?
|
||||
first.getRootBeanClass().getName() + "." + property
|
||||
: property;
|
||||
|
||||
setArgs(new Object[]{resolveMessage, first.getMessage()});
|
||||
setArgs(new Object[]{propertyI18n, first.getMessage()});
|
||||
|
||||
details = new ArrayList<>(violations.size());
|
||||
for (ConstraintViolation<?> violation : violations) {
|
||||
details.add(new Detail(violation.getPropertyPath().toString(), violation.getMessage(), null));
|
||||
details.add(new Detail(violation.getPropertyPath().toString(),
|
||||
violation.getMessage(),
|
||||
null));
|
||||
}
|
||||
}
|
||||
|
||||
public List<Detail> getDetails(Locale locale) {
|
||||
return CollectionUtils.isEmpty(details)
|
||||
? Collections.emptyList()
|
||||
: details
|
||||
.stream()
|
||||
.map(detail -> detail.translateI18n(locale))
|
||||
.collect(Collectors.toList());
|
||||
}
|
||||
|
||||
@Override
|
||||
public String getLocalizedMessage(Locale locale) {
|
||||
if (propertyI18nEnabled && "validation.property_validate_failed".equals(getI18nCode()) && getArgs().length > 0) {
|
||||
Object[] args = getArgs().clone();
|
||||
args[0] = LocaleUtils.resolveMessage(String.valueOf(args[0]), locale, String.valueOf(args[0]));
|
||||
return LocaleUtils.resolveMessage(getI18nCode(), locale, getMessage(), args);
|
||||
}
|
||||
return super.getLocalizedMessage(locale);
|
||||
}
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
@AllArgsConstructor
|
||||
public static class Detail {
|
||||
|
||||
@Schema(description = "字段")
|
||||
String property;
|
||||
|
||||
@@ -74,10 +95,11 @@ public class ValidationException extends I18nSupportException {
|
||||
@Schema(description = "详情")
|
||||
Object detail;
|
||||
|
||||
public void translateI18n(Object... args) {
|
||||
if (message.contains(".")) {
|
||||
message = LocaleUtils.resolveMessage(message, message, args);
|
||||
public Detail translateI18n(Locale locale) {
|
||||
if (StringUtils.hasText(message) && message.contains(".")) {
|
||||
return new Detail(property, LocaleUtils.resolveMessage(message, locale, message), detail);
|
||||
}
|
||||
return this;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -4,7 +4,9 @@ import lombok.Getter;
|
||||
import lombok.Setter;
|
||||
import org.hswebframework.web.exception.ValidationException;
|
||||
import org.hswebframework.web.i18n.LocaleUtils;
|
||||
import org.hswebframework.web.i18n.MessageSourceInitializer;
|
||||
import org.junit.Test;
|
||||
import org.springframework.context.support.StaticMessageSource;
|
||||
|
||||
import javax.validation.constraints.NotBlank;
|
||||
|
||||
@@ -14,27 +16,39 @@ import static org.junit.Assert.*;
|
||||
|
||||
public class ValidatorUtilsTest {
|
||||
|
||||
|
||||
@Test
|
||||
public void test(){
|
||||
test(Locale.CHINA,"不能为空");
|
||||
test(Locale.ENGLISH,"must not be blank");
|
||||
static {
|
||||
System.setProperty("i18n.validation.property.enabled", "true");
|
||||
}
|
||||
|
||||
public void test(Locale locale,String msg){
|
||||
@Test
|
||||
public void test() {
|
||||
StaticMessageSource source = new StaticMessageSource();
|
||||
source.addMessage("validation.property_validate_failed", Locale.CHINA, "{0} {1}");
|
||||
source.addMessage("validation.property_validate_failed", Locale.ENGLISH, "{0} {1}");
|
||||
|
||||
source.addMessage(TestEntity.class.getName() + ".notBlank", Locale.ENGLISH, "Test");
|
||||
source.addMessage(TestEntity.class.getName() + ".notBlank", Locale.CHINA, "测试");
|
||||
|
||||
MessageSourceInitializer.init(source);
|
||||
test(Locale.CHINA, "不能为空", "测试 不能为空");
|
||||
test(Locale.ENGLISH, "must not be blank", "Test must not be blank");
|
||||
}
|
||||
|
||||
public void test(Locale locale, String msg, String msg2) {
|
||||
try {
|
||||
LocaleUtils.doWith(locale,en->{
|
||||
LocaleUtils.doWith(locale, en -> {
|
||||
ValidatorUtils.tryValidate(new TestEntity());
|
||||
});
|
||||
throw new IllegalStateException();
|
||||
}catch (ValidationException e){
|
||||
assertEquals(msg,e.getDetails().get(0).getMessage());
|
||||
} catch (ValidationException e) {
|
||||
assertEquals(msg, e.getDetails().get(0).getMessage());
|
||||
assertEquals(msg2, e.getLocalizedMessage(locale));
|
||||
}
|
||||
}
|
||||
|
||||
@Getter
|
||||
@Setter
|
||||
public static class TestEntity{
|
||||
public static class TestEntity {
|
||||
|
||||
@NotBlank
|
||||
private String notBlank;
|
||||
|
||||
Reference in New Issue
Block a user