ValidationMessages.properties文件之间的冲突
我用来收集公共库中的所有validation约束。 在jar的根目录中,我放了一个ValidationMessages_it.properties
文件。 一切正常,如果我将这个库放入jsf 2 war项目中,所有validation消息都会正确显示。 但是,如果我在war工件中放置另一个ValidationMessages_it.properties
,则会出现问题。 在这种情况下,会显示{library.message_key}字符串。
我认为Bean Validation在战争中找到了正确的属性文件,并没有考虑到库中的那个。 我怎么解决?
编辑
尝试澄清我的配置:
我有一个包含自定义约束的库commons.jar。 为了设置这些约束的消息,我在这个库的根目录中添加了ValidationMessages_it.properties
commons.jar | + library | | | + CustomConstraint.class | + ValidationMessages_it.properties
Validation_it.properties:
library.custom=Questo è l'errore di cui parlavo
CustomConstraint.java:
@Pattern( regexp = "[az]", message = "{library.custom}" ) @Constraint( validatedBy = {} ) @Documented @Target( { ElementType.METHOD, ElementType.FIELD } ) @Retention( RetentionPolicy.RUNTIME ) public @interface CustomConstraint { String message() default "C'è un errore"; Class[] groups() default {}; Class[] payload() default {}; }
PS: 请注意,消息键位于@Pattern注释而不是message(),这似乎是一个错误,但否则它永远不会起作用!
之后我想在我的web应用程序项目中使用这个commons.jar(jsf / mojarra 2.1)。 一切正常。 显示的错误消息是Questoèl’erroredi cui parlavo
但现在假设我在webapp中定义了新的validation约束,所以我想通过在WEB-INF / classes文件夹中添加ValidationMessages_it.properties来为这些约束提供翻译。 在这种情况下,显示的错误消息是{library.custom}
所以我认为BV(或jsf?)在战争中找到了捆绑,并没有考虑到commons.jar中的捆绑。 它没有在位于WEB-INF / classes文件夹中的ValidationMessages_it.properties中找到密钥库.custom ,因此返回{library.custom} 。
编辑2
为了更好地理解Hardy的答案,我打开了另一个问题来validation我的假设是否正确: 共享库中的Bean Validation约束
编辑3
基于上述问题,我的包结构似乎是正确的。 我上传了一个简单的网络应用程序来显示问题:
- 可以部署在符合java EE 6的应用程序服务器中的war工件
- 包含两个maven项目的源zip,一个用于库,一个用于webapp
我测试了Glassfish 3.1.2,JBoss AS 7.1.1,Geronimo 3.0.0中的webapp
Glassfish和Jboss具有相同的行为。 在Geronimo中,它的工作效果更好一些。
我认为您的案例中的解决方案是提到的AggregateResourceBundleLocator 。 但是,属性文件的名称不能相同。 内部ResourceBundle#getBundle被调用,它返回一个ResourceBundle 。 没有组合/合并具有相同名称的属性文件的概念。
编辑1
关于标准的做法 – 不幸的是没有。 Bean Validation 1.1(hibernate.onjira.com/browse/BVAL-252)存在一个未解决的问题,以解决提供约束库的问题,但目前还没有任何决定,消息插值也需要解决。 也许你对它应该如何运作有所了解。 如果是,请向专家组提出您的建议。 检查beanvalidation.org
2015年7月发布的Hibernate Validator 5.2增加了对从不同JAR文件聚合具有相同名称的所有资源包的支持。 默认情况下禁用此function,可以在org.hibernate.validator.resourceloading.PlatformResourceBundleLocator中配置。
例:
PlatformResourceBundleLocator resourceBundleLocator = new PlatformResourceBundleLocator(ResourceBundleMessageInterpolator.USER_VALIDATION_MESSAGES, null, true); Validator validator = Validation.byProvider(HibernateValidator) .configure() .messageInterpolator(new ResourceBundleMessageInterpolator(resourceBundleLocator)) .buildValidatorFactory() .getValidator();
使用Java配置的Spring项目的等效代码:
@Bean public LocalValidatorFactoryBean validator() { PlatformResourceBundleLocator resourceBundleLocator = new PlatformResourceBundleLocator(ResourceBundleMessageInterpolator.USER_VALIDATION_MESSAGES, null, true); LocalValidatorFactoryBean factoryBean = new LocalValidatorFactoryBean(); factoryBean.setMessageInterpolator(new ResourceBundleMessageInterpolator(resourceBundleLocator)); return factoryBean; }
- 如何使用Spring MVC JSR-303 Validator将不同的模型类validation为一个表单
- 使javaxvalidation错误消息更具体
- 方法上的Beanvalidation
- 如何在类级别约束之前validation字段级别约束?
- 由于@Constraint validatedBy,如何避免层之间的交叉依赖?
- Spring MVC – REST服务中bean列表上的@Valid
- JSF:如何validation字段并通过beanvalidation返回错误消息?
- 如何在ConstraintValidator中自动assembly服务
- Spring MVC和JSR-303 hibernate条件validation