Статьи

JBoss AS7 JNDI & EJB 3.1 Изменения в именах

В результате того, что «функциональный поезд» продолжает развиваться, и мы не поддерживаем наш программный стек в актуальном состоянии, наша команда оказывается в незавидном положении при переходе:

  • JBoss 4.2.3 для AS 7.1.x (в настоящее время глядя на 7.1.1)
  • EJB 2.1 до EJB 3.1
  • Hibernate 2 до Hibernate 3 или 4

в быстрой моде. Я имею в виду, кто хочет выпустить новую версию с программным обеспечением 8-10 лет, а не я! Следующее является результатом некоторых исследований, которые я проводил, глядя на обновление с JBoss 4.2.3 с EJB 2.1 до AS 7.1.x с EJB 3.1. Я уверен, что будет больше

сообщения, связанные с этой миграцией в ближайшем будущем, но эта связана с изменениями в области именования JNDI.

В прошлом / настоящем

В нашем текущем коде именование JNDI было очень простым:

  1. Мы объединили «ejb /» с именем удаленного интерфейса Session Bean в дескрипторе развертывания, чтобы указать имя, с которым должна быть связана служба.
  2. В коде мы используем следующий код для обработки поиска JNDI. Действительно хорошая часть заключалась в том, что один и тот же код мог использоваться удаленными клиентами И на сервере, внутри контейнера.

Текущий код

1
2
3
4
5
6
Hashtable properties = new Hashtable();
properties.put("java.naming.factory.initial","org.jnp.interfaces.NamingContextFactory");
properties.put("java.naming.factory.url.pkgs","org.jboss.naming:org.jnp.interfaces");
properties.put("java.naming.provider.url", "jnp://localhost:1099");
Context ctx = new InitialContext(properties);
Object ref = ctx.lookup(jndiName);

AS7 и EJB 3.1

Спецификация EJB 3.1 внесла некоторые изменения в мандат переносимых имен JNDI для EJB, и вы наследуете это в AS 7.1.1. Другая хитрость, которую я обнаружил, заключалась в том, что я больше не мог использовать точно такой же код поиска от наших удаленных клиентов и сервера.

AS 7 теперь имеет две опции для удаленного вызова EJB . Информацию, которая вам нужна, можно найти в документации JBoss, она просто не поразила меня! После нескольких дней борьбы с этой проблемой я решил создать небольшую программу, которая поможет сделать различия (надеюсь) очень ясными. Ниже приведена программа, которую я создал для вызова сессионного компонента без сохранения состояния с удаленного клиента. Я развернул пример « ejb-remote» из примеров быстрого запуска 7.1. Код пытается загрузить удаленный сервис, используя оба удаленных метода. Ожидается, что для первого набора поисков первый поиск будет успешным, а второй с использованием формата именования «ejb: /» завершится неудачно. Затем я добавляю свойство Context.URL_PKG_PREFIXES со значением «org.jboss.ejb.client.naming» к свойствам jndi, переданным конструктору InitialContext, и повторяю поиск. Теперь оба поиска должны быть успешными. Я включил все свойства JNDI в код, а не полагался на копию « jboss-ejb-client.properties » или « jndi.properties », полученную из пути к классам.

01
02
03
04
05
06
07
08
09
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
 
import java.util.Hashtable;
 
public class EJBClient {
 
     private static String[] JNDINAME = {
          "jboss-as-ejb-remote-app/CalculatorBean!org.jboss.as.quickstarts.ejb.remote.stateless.RemoteCalculator",
          "ejb:/jboss-as-ejb-remote-app/CalculatorBean!org.jboss.as.quickstarts.ejb.remote.stateless.RemoteCalculator"
     };
 
     private Hashtable jndiProps;
 
     public EJBClient() {
       // setup 'base' jndi properties - no jboss-ejb-client.properties being picked up from classpath!
       jndiProps = new Hashtable();
          jndiProps.put("java.naming.factory.initial",
"org.jboss.naming.remote.client.InitialContextFactory");
          jndiProps.put(InitialContext.PROVIDER_URL, "remote://localhost:4447");
          jndiProps.put("jboss.naming.client.ejb.context", true);
 
          // needed for remote access - remember to run add-user.bat
          jndiProps.put(Context.SECURITY_PRINCIPAL, "client");
          jndiProps.put(Context.SECURITY_CREDENTIALS, "password");
     }
 
    public void doLookups() {
         // the 'exported' namespace
         for (int i = 0; i < JNDINAME.length; i++) {
               lookup(JNDINAME[i]);
          }
 
         // This is an important property to set if you want to do EJB invocations via the remote-naming project
        jndiProps.put(Context.URL_PKG_PREFIXES, "org.jboss.ejb.client.naming");
 
        // now with the ejb
        for (int i = 0; i < JNDINAME.length; i++) {
               lookup(JNDINAME[i]);
          }
    }
 
    private void lookup(String name) {
         System.out.println("Lookup name="+name);
 
         Context ctx = null;
        try {
               ctx = new InitialContext(jndiProps);
               Object ref = ctx.lookup(name);
               System.out.println("...Successful");
          } catch (NamingException e) {
               System.out.println("...Failed");
               //System.out.println(e.getMessage());
               e.printStackTrace();
          } finally {
               if (ctx != null) {
                    try {
                         ctx.close();
                    } catch (NamingException e) {}
               }
          }
    }
 
    public static void main(String[] args) throws Exception {
         EJBClient client = new EJBClient();
         client.doLookups();
 
         System.out.println("Done!");
    }
 
}

AS7 на стороне сервера

Теперь простая часть, выполнение поиска JNDI на сервере, очень похожа на старый способ, за исключением того, что вам все еще нужно отформатировать имя JNDI в соответствии с новыми спецификациями, а фабрика имен больше не является версией jnp!

1
2
3
4
Hashtable jndiProps = new Hashtable();
    jndiProps.put("java.naming.factory.initial", "org.jboss.as.naming.InitialContextFactory");
    ctx = new InitialContext(jndiProps);
    Object ref = ctx.lookup(jndiName);

Вывод

Как я уже говорил ранее, информация была / есть в документации JBoss, но я, вероятно, читал ее несколько раз. Я искал пример, показывающий загрузку EJB-компонентов как с клиента, так и с сервера.

Надеюсь это поможет!

Ссылка: JBoss AS7 JNDI & EJB 3.1 Изменение имен от нашего партнера по JCG Майка Миллера в блоге Scratching my itch .