2012-03-28 3 views
4

ОБНОВЛЕНО: сводную Постановление от 12/9/2016Установка имени класса Spring боба, используя выражение SPEL и PropertyPlaceHolder

Согласно @ altazar Ответим ниже, this is now possible от Spring 4.2!

Старый краткое постановление от 3/29/2012

По состоянию на эту дату, Spring SPEL не смог выполнить внутри class атрибута <bean>.

Оригинальный вопрос:

Я пытаюсь реализовать динамический class атрибут для Spring бина, в конечном счете, установить, используя комбинацию PropertyPlaceHolder собственности и выражение SPEL. Целью является либо выпускная, либо отладочная версия класса для создания экземпляра. Это не работает, и мне интересно, можно ли этого достичь.

До сих пор у меня есть следующие:

Плоские свойства файла:

is.debug.mode=false 

Spring XML конфигурации:

<bean id="example" 
     class="#{ ${is.debug.mode} ? 
        com.springtest.ExampleDebug : 
        com.springtest.ExampleProd}" 
/> 

Spring самозагрузки Java код:

// Get basic ApplicationContext - DO NOT REFRESH 
    FileSystemXmlApplicationContext applicationContext = new 
      FileSystemXmlApplicationContext 
      (new String[] {pathSpringConfig}, false); 

    // Load properties 
    ResourceLoader resourceLoader = new DefaultResourceLoader(); 
    Resource resource = resourceLoader.getResource("file:" + pathProperties); 
    Properties properties = new Properties(); 
    properties.load(resource.getInputStream()); 

    // Link to ApplicationContext 
    PropertyPlaceholderConfigurer propertyConfigurer = 
      new PropertyPlaceholderConfigurer() ; 
    propertyConfigurer.setProperties(properties) ; 
    applicationContext.addBeanFactoryPostProcessor(propertyConfigurer); 

    // Refresh - load beans 
    applicationContext.refresh(); 

    // Done 
    Example example = (Example) applicationContext.getBean("example"); 

Сообщение об ошибке (с большим количеством пробелов удалены для ясности):

Caused by: java.lang.ClassNotFoundException: 
#{ true ? com.springtest.ExampleDebug : com.springtest.ExampleProd} 
    at java.net.URLClassLoader$1.run(URLClassLoader.java:366) 
    at java.net.URLClassLoader$1.run(URLClassLoader.java:355) 
    . . . 

Как вы можете видеть на «true» в сообщении, is.debug.mode свойство успешно загружен и заменен. Но что-то еще идет не так. Является ли это моей начальной загрузкой в ​​Java? Или синтаксис SPeL в XML? Или другая проблема?

BTW Мне известно о новой функции профилей 3.1, но я хотел бы сделать это через SPeL по разным причинам. Также я понимаю, что я использую контекст и пути на основе файловой системы. У меня есть причины для этого.

ответ

4

Вы могли бы сделать то, что вы собираетесь с factoryBean:

<bean id="example" class="MyFactoryBean"> 
    <property name="class" value="#{ ${is.debug.mode} ? com.springtest.ExampleDebug : com.springtest.ExampleProd}"/> 
</bean> 

где MyFactoryBean является тривиальным FactoryBean реализация возвращения экземпляр указанного класса.

+0

+1 Это еще один хороший способ обхода проблемы. Вы говорите в основном, что оценка SPeL просто не происходит в атрибуте 'class'' '? –

+3

Я думаю, что класс не обрабатывается через EL. Я смутно помню, как это проверялось в источниках. – mrembisz

+1

Я доверяю вашей памяти об установке источника. Я просто получил одно и то же выражение SPeL для работы в '', но все еще не работает в ''. Это для меня подтверждение, и я иду с твоим ответом. –

2

Вы можете это сделать.

debug.class=com.springtest.ExampleDebug 
#debug.class=com.springtest.ExampleProd 

, а затем

<bean id="example" class="${debug.class}"/> 
+0

Это хорошее обходное решение, и я могу прибегнуть к нему. Но уверены ли вы, что SpEL не работает в весеннем контексте XML? [Эта весенняя документация] (http://static.springsource.org/spring/docs/current/spring-framework-reference/htmlsingle/spring-framework-reference.html#expressions-beandef-xml-based), похоже, показывает, что оно делает. Или вы имели в виду тип «ApplicationContext», который я использую сейчас? Благодарю. –

+0

У вас есть право, он должен работать. Какое приложение у вас есть? Вы пытались выразить выражение следующим образом: {{properties ['is.debug.mode']? ..: ..} – chalimartines

+0

Возможно, класс атрибута не поддерживает оценку SpEL. Попробуйте применить выражение к некоторому свойству. – chalimartines

2

С весны 4.2 он is possible использовать SPEL в классе атрибутов так хорошо следующие работы:

<bean id="example" 
     class="#{T(java.lang.Boolean).parseBoolean('${is.debug.mode:false}') ?  
       'com.springtest.ExampleDebug' :        
       'com.springtest.ExampleProd'}"/> 

В моем случае заполнитель ${is.debug.mode:false} не работает, поэтому я разобрать его в явном виде.

+0

Изменит мой вопрос выше - спасибо! –

Смежные вопросы