2013-02-18 2 views
12

У меня есть проект Java EE 5 с использованием JBoss 5.1 и проблема вроде этого. Мне нужно выполнить поиск во время выполнения для некоторых EJB в MDB, используя строку, которая получается из содержимого сообщения. Это просто своего рода шаблон локатора сервисов, используемый в MDB. Теперь, поскольку MDB начинают потреблять сразу после развертывания, у меня есть много NameNotFoundException, так как неявный порядок развертывания здесь не работает (поиск во время выполнения). Что вы думаете об этом? Возможно ли это сделать с помощью EJB 3.0? Для меня также приемлемо использовать любые специфические для вендора вещи (JBoss 5.1), если это устраняет проблему.Поиск времени для EJB в MDB, потребляющем сразу после развертывания

Некоторые фрагмент кода, чтобы визуализировать ситуацию:

@MessageDriven(mappedName="jms/Queue") 
public class MessageBean implements MessageListener { 

    @Resource 
    private MessageDrivenContext mdc; 

    public void onMessage(Message msg) { 

     final String beanName = // extract somehow the bean's name from 'msg' 
     final Context ctx = new InitialContext(); 
     final Object obj = ctx.lookup(beanName); // NameNotFoundException 
     // do something with 'obj' 
    } 
} 
+0

Быстрая идея: если вы выполнили транзакцию потребления, возможно, вы отклоните tx на 'NameNotFoundException', получите разумную политику повтора и надеетесь, что EJB развернутся в следующий раз? –

+0

Это что-то, но заметьте, что если у меня будут миллионы сообщений, ожидающих в очередях (это действительно мой случай), каждый из них будет сначала обработан, чтобы просто отклонить tx. База данных, вероятно, преклонит колени. Это в любом случае получает огромную нагрузку на запуск приложения. –

+0

Можете ли вы вставить фрагмент кода здесь .. как выполняется поиск. Каково определение вашего класса MDB? – user1428716

ответ

4

Используйте один из четырех различных подходов.

  1. Declare EJB зависимостей (ссылки EJB) с использованием "@EJB" аннотацию (не использовать JNDI поиск). Для ссылок на объекты bean-объекта необходимо ссылаться на домашний интерфейс entity bean. Контейнер должен обеспечить все зависимости впрыскивают перед тем методы/сообщение-слушатели обрабатываются:

    MessageDriven (mappedName = "JMS/Queue")
    общественного класса MessageBean реализует MessageListener {

    @EJB private EntityBeanHomeA entityBeanHomeA;  
    
    @EJB private EntityBeanHomeB entityBeanHomeB;  
    
    @EJB private EntityBeanHomeC entityBeanHomeC;  
    
    @EJB private SessionBeanD sessionBeanD;  
    
    @Resource 
    private MessageDrivenContext mdc; 
    
    public void onMessage(Message msg) { 
    
        final String beanName = // extract somehow the bean's name from 'msg' 
        final Object obj = getDependentEJB(beanName); 
        // do something with 'obj' 
    } 
    
    private Object getDependentEJB(String beanName) { 
        Object result = null; 
        if ("EntityBeanHomeA".equals(beanName)) { 
         result = entityBeanHomeA; 
        else if ("EntityBeanHomeB".equals(beanName)) { 
         result = entityBeanHomeB; 
        else ("EntityBeanHomeC".equals(beanName)) { 
         result = entityBeanHomeC; 
        else ("SessionBeanD".equals(beanName)) { 
         result = sessionBeanD; 
        } 
        return result; 
    } 
    

    }

  2. Используйте JNDI-поиск, но объявляйте зависимости EJB через дескрипторы развертывания EJB. Опять же, контейнер должен обеспечить обеспечить все зависимости настраивались до методы/обработки сообщений:

    @MessageDriven (mappedName = "JMS/Queue") общественного класса MessageBean реализует MessageListener {

    // as given in the original Question... 
    

    }

    дескриптор

    развертывания:

    <enterprise-beans> 
        <message-driven> 
         ... 
         <ejb-name>MessageBean</ejb-name> 
         <ejb-class>com.company.pkg.MessageBean</ejb-class> 
         <messaging-type>javax.jms.MessageListener</messaging-type> 
         <message-destination-type>javax.jms.Queue</message-destination-type> 
         <message-destination-link>ExpenseProcessingQueue</message-destination-link> 
         <ejb-ref> 
          <description> This is a reference to an EJB 2.1 entity bean 
           that encapsulates access to employee records. 
          </description> 
          <ejb-ref-name>ejb/EmplRecord</ejb-ref-name> 
          <ejb-ref-type>Entity</ejb-ref-type> 
          <home>com.wombat.empl.EmployeeRecordHome</home> 
          <remote>com.wombat.empl.EmployeeRecord</remote> 
          <ejb-link>EmployeeRecord</ejb-link> <-- if in same EJB jar --> 
             <-- ../emp/emp.jar#EmployeeRecord if in diff EJB jar --> 
         </ejb-ref> 
         <ejb-local-ref> 
          <description> This is a reference to the local business interface 
           of an EJB 3.0 session bean that provides a payroll service. 
          </description> 
          <ejb-ref-name>ejb/Payroll</ejb-ref-name> 
          <local>com.aardvark.payroll.Payroll</local> 
          <ejb-link>Payroll</ejb-link> 
         </ejb-local-ref> 
         <ejb-local-ref> 
          <description> This is a reference to the local business interface of an 
           EJB 3.0 session bean that provides a pension plan service. 
          </description> 
          <ejb-ref-name>ejb/PensionPlan</ejb-ref-name> 
          <local>com.wombat.empl.PensionPlan</local> 
          <ejb-link>PensionPlan</ejb-link> <-- if in same EJB jar --> 
         </ejb-local-ref> 
         ... 
        </message-driven> 
        ... 
    </enterprise-beans> 
    
  3. Использование JNDI поиск, но не объявлять зависимости USI ng или аннотации @EJB или развертывание EJB - полностью обрабатывайте свою логику без помощи контейнера. Используйте задержки/обработку ошибок.

  4. Использование JBoss патентованных конфигураций для управления развертыванием заказа:

    http://texnoblog.wordpress.com/2010/09/16/depends-in-jboss/

    How to order deployment of EJBs and JMS queue config in JBoss 5?

+0

Глен, спасибо за ответ. Это подтверждает, что нет никаких строгих и элегантных решений, использующих эти технологии. В любом случае, нужен хакер. Вероятно, я попробую с 3 или 4 вариантами. –

2

Одним из способов было бы создать фиктивный EJB, который вы впрыснуть в ваш MDB, таким образом ваш MDB не начать потреблять до тех пор, что инъекции не может на самом деле взять место.

Если манекен-EJB поставляются с EJBs вы намеревались сделать динамический поиск на это должно работать

Моего ответа here решает похожий потребительский случай.

1

Я думаю, что лучший подход был бы отсрочить развертывание вашего MDB, пока все ваши EJBs вверх & бег. Это в основном подход номер 4 в ответе выше.

"фирменная настройка Использование JBoss для управления порядком развертывания:

http://texnoblog.wordpress.com/2010/09/16/depends-in-jboss/

How to order deployment of EJBs and JMS queue config in JBoss 5?"

1

можно реализовать цикл с отсрочки вокруг вызова поиска.

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