0 Replies Latest reply on Aug 10, 2017 3:54 AM by nuno.godinhomatos

    CI System testing - Invoking remote EJBs via dynamic configuration

    nuno.godinhomatos

      Hi,

       

      Here is a simple question related to configurability/adaptiblity of system test code to environments with several deployment settings (e.g. multiple wildfly application servers running parallel with different port configurations).

      This question also relates with the following wildfly documentation chapter:

      https://docs.jboss.org/author/display/WFLY10/Remote+EJB+invocations+via+JNDI+-+EJB+client+API+or+remote-naming+project

       

      Which is brilliantly written in my opinion.

       

      Motivation:

      The context is simple. You have N applications, that you want to system test, and one of the menas by which you implement system tests, is to have client side code, not depoyed into the container, that perhaps use @Remote ejbs to both trigger backend business logic and as well run assertions of DB state and such.

       

      Now when you are on localhost, you typically run with all the default configurations.

      Your http port 8080, your management port 9990. And so on.

       

      In this context, originally, I was making remote ejb calls under the jndi lookup namespeace: "ejb:".

      So your jndi lookup string for a remote EJB would be something of the form:

      jndiName = "ejb:" + appName + "/" + moduleName + "/" + distinctName + "/" + beanName + "!"

                              + viewClassName;

       

      The problem I now have with this approach, is that there is one piece of configuration I really dislike.

      And that is the:

      jboss-ejb-client.properties

       

      While the above file you can conveniently put into your serc/test/resources and it goes into the classpath and is used during you eclipse development time.

      That file of course is like an abchor that pulls you down, when you step ouside of your local setup and want to have all the static information in the file being dynamic.

      I want to be rid of any hard-coded url.

      Due to my ignorance, I right now do know if there is anything to be done with this ejb: namespace when you are a dynamic context, short of dynamically creating the file during Junit system test @Before phase.

      And such an approach I would like to avoid.

      There might be a programtic solution that rescues this "ejb:" namesapce, but if there is I do not know it, so I abandoned the approach.

       

      Reading the above documentation page, it is make clear that every deployed @Remote ejb is conveniently - by default - exposed under the java:jboss/exported namespace.

      And that we can leverage this if we setup our JNDI initial context with a very important property:

      initialContextProperties.setProperty("jboss.naming.client.ejb.context", "true");

       

      And now my questions would be the following:

      (a) By using the traditional JNDI lookup approach where the EJBs are leveraging the connection metadata used to setup a new InitialContext(), are we losing any sort of performance to the more di-associated process of executing the ejb proxies that consume the metadata on the jboss-ejb-client.properties?

      There must be a reason for supporting and maintaining two approaches.

      Intuitively, I would say the JNDI appraoch is best since there is less redundant information involved and it is on first appareance for a developer a  more dynamic more configurable approach.

       

      (b) I fail to understand while the following bean could only be looked up using a name that looks quite far from the java:global convention and from the java:jboss/exported name.

       

      - (b.1) During deployment in a sample application we log this remote EJB:

       

      2017-08-10 09:00:52,766 INFO  [org.jboss.as.ejb3.deployment] (MSC service thread 1-4) WFLYEJB0473: JNDI bindings for session bean named 'LogMessageOnServerLogTestFacadeImpl' in deployment unit 'deployment "wildfly-jta-commit-reproducebug.war"' are as follows:

      java:global/wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade

      java:app/wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade

      java:module/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade

      java:jboss/exported/wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade

      java:global/wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl

      java:app/wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl

      java:module/LogMessageOnServerLogTestFacadeImpl

       

      - (b.2) My first attempt to lookup the EJB using the java:jboss/exported name looked as follows:

      jndiName = "java:jboss/exported/" + appName + "/" + moduleName + "/" + beanName + "!" + viewClassName;

       

      Which hard-coded would translated into:

      jndiName = "java:jboss/exported//wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade";

       

      Notice that the appName in the case above is the empty string since we are not deploying the sample war into a EAR, is straight otu WAR deployment.

       

      This name could not be found, I would get exceptions such as:

      Caused by: javax.naming.NameNotFoundException:

      jboss/exported//wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade -- service jboss.naming.context.java.jboss.exported.jboss.exported.wildfly-jta-commit-reproducebug."LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade"

       

       

      - (b.3) Looking closer at the example on the documentation, I could see that the lookup for the Foo EJB did not make any mention of the java:jboss/exported namespace.

      So then by re-writing the lookup name to:

      initialContext.lookup("wildfly-jta-commit-reproducebug/LogMessageOnServerLogTestFacadeImpl!facade.systemtest.LogMessageOnServerLogTestFacade")

       

      I was fine getting the ejb proxy.

       

      So here, I really do not understand why the name used on the lookup apparently must start on the remote client already at the modulename name and not on java:jboss/exported?

      Should it be this way?

       

       

      (C) My final question what would be the most fleixible/efficient approach to setup Remote EJBs where all configuration is fully dynamic.

      Is the approach I am using with the

      initialContextProperties.setProperty("jboss.naming.client.ejb.context", "true");

       

      The best way to go forward?

       

      Kindest regards.