#spring #javabeans #cglib #wicket-6 #apache-servicemix
#spring #javabeans #cglib #калитка-6 #apache-servicemix
Вопрос:
Я пытался использовать руководство Mkyong для доступа к файлу внешних свойств, но безуспешно.
Это мое определение компонента в web-osgi-context.xml файл, расположенный в WEB-INF:
<bean id="messageSource"
class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
<property name="basenames">
<list>
<value>classpath:bundles/resource</value>
<value>classpath:bundles/override</value>
<value>file:c:/test/messages</value>
</list>
</property>
<property name="cacheSeconds" value="10"/>
</bean>
Доступ к компоненту:
@SpringBean
private ReloadableResourceBundleMessageSource messageSource;
Попытка извлечь сообщение следующим образом:
String name = messageSource.getMessage("customer.name",
new Object[] { 28,"http://www.mkyong.com" }, Locale.US);
System.out.println("Customer name (English) : " name);
У меня есть файлы messages_en_US.properties в обоих C:/test/messages и C:/test папки. Они содержат следующую строку:
customer.name=Test, age : {0}, URL : {1}
Это все, что у меня есть, я что-то упускаю? Сообщение, которое я получаю, является:
org.springframework.context.NoSuchMessageException: No message found under code 'customer.name' for locale 'en_US'.
at org.springframework.context.support.AbstractMessageSource.getMessage(AbstractMessageSource.java:155)
Кстати, я также пробовал внутренние свойства, также безуспешно. Я развертываю свой файл .war в своем локальном servicemix(6.1.1), я также использую wicket (6.24.0) и spring (3.2.14). Запуск приложения mkyong (которое не является веб-приложением) локально (без его развертывания в моем локальном servicemix работает).
Комментарии:
1. Похоже, проблема в ServiceMix. Я бы добавил это в теги и надеюсь, что кто-то с опытом ServiceMix поможет.
2. Ну, я думаю, это в основном потому, что это веб-приложение, а не просто строковое приложение. Не тестировал подход mkyongs локально в веб-приложении
Ответ №1:
Ооочень, я несколько обнаружил проблему и получил решение..
Это не сработало:
<bean id="messageSource"
class="org.springframework.context.support.ReloadableResourceBundleMessageSource">
<property name="basename">
<value>classpath:messages</value>
</property>
</bean>
И в коде:
@SpringBean
private ReloadableResourceBundleMessageSource messageSource;
Запустив getClass() в этом источнике, я получаю
class WICKET_org.springframework.context.support.ReloadableResourceBundleMessageSource$$EnhancerByCGLIB$$852b0c02
Но это работает:
@Bean
public MessageSource messageSource() {
ReloadableResourceBundleMessageSource messageSource = new ReloadableResourceBundleMessageSource();
messageSource.setBasename("classpath:messages");
return messageSource;
}
Запустив getClass() в этом источнике, я получаю
class org.springframework.context.support.ReloadableResourceBundleMessageSource
Возможно ли, что усилитель Cglib здесь что-то путает? Как я могу заставить первый вариант работать, зная это?
Комментарии:
1. Wicket использует CGlib для создания прокси-сервера вокруг компонента Spring, но любые вызовы метода на этом прокси-сервере делегируются реальному компоненту. Таким образом, реальный компонент выполняет логику для поиска сообщения, а не прокси. Кроме того, местоположение является корнем пути к классу, поэтому на самом деле не имеет значения, какой класс используется.
2. Как я предположил в комментариях к вопросу: проблема в ServiceMix. Он основан на OSGi, и пути к классам и загрузчики классов ведут себя там иначе, чем на обычном веб-сервере сервлетов.
3. Если нет разницы между тем, какой из них используется, то почему второй работает для меня, а первый — нет?