Using the Java EE Connector Builder with Wildfly Application Server

Example Description

  • This example is based on the scalar type example.
  • It calls a PL/SQL stored procedure and returns a transfer object.
  • The calling api is always identically in any PL/SQL Connector Builder.
  • The Wildfly application server is completely configured inside the Docker container.
  • The Wildfly application server supports EJB-Remoting via HTTP.
    • The protocol HTTP can be routed via NAT (network address translation) on virtual networks. The way Docker is working.
    • The protocol IIOP (Internet Inter-ORB Protocol), the default EJB-Remoting protocol, does normally not work in NAT networks.

Wildfly Server

  • The Docker image 'jboss/wildfly:22.0.1.Final' is used.
  • An admin user and a standard user is configured for remote access.
  • Datasource Configuration: A Wildfly configuration file 'standalone.xml' is copied into the Wildfly configuration folder of the Docker image.
    • This configuration file has a predefined Oracle Datasource 'dbw_examples'.
    • The parameter of user, password and url for the datasource connection are defined by environment variables.
    • These environment variables will be set on docker image startup.
  • Oracle JDBC Driver Module Configuration: To use the Oracle JDBC driver extension and support all data types the JDBC driver has to be defined as module.
    • The following files are copied into the Docker image folder './modules/system/layers/base/com/oracle/jdbc/main/'.
    • modules.xml : located at '/wildfly_configuration'
    • ojdbc8.jar, ucp.jar, xdb6.jar : fetched from maven-assembly and stored in './target/oracle_jdbc_driver/'
  • Using the Oracle JDBC Driver inside EAR-Application:
    • jboss-deployment-structure.xml : Configuration to use the Oracle JDBC driver module inside the EAR-Application.
  • The Docker container image is created by maven in the build process of the server project.
Docker Containerization Config
Docker Configuration : Dockerfile
FROM jboss/wildfly:22.0.1.Final

# user configuration : user dbworkbench100 is configured for remote access (see jave_ee_factoryapi_client/.../wildfly-config.xml)
RUN /opt/jboss/wildfly/bin/add-user.sh admin admin --silent
RUN /opt/jboss/wildfly/bin/add-user.sh -a -u dbworkbench100 -p dbworkbench100 --silent

# wildfly configuration (datasource dbw_examples preconfigured : url, username and password set via docker run call from client pom.xml)
COPY wildfly_configuration/standalone.xml /opt/jboss/wildfly/standalone/configuration

# oracle jdbc driver configuration
COPY wildfly_configuration/module.xml /opt/jboss/wildfly/modules/system/layers/base/com/oracle/jdbc/main/
COPY target/oracle_jdbc_driver/ojdbc8.jar /opt/jboss/wildfly/modules/system/layers/base/com/oracle/jdbc/main/
COPY target/oracle_jdbc_driver/ucp.jar /opt/jboss/wildfly/modules/system/layers/base/com/oracle/jdbc/main/
COPY target/oracle_jdbc_driver/xdb6.jar /opt/jboss/wildfly/modules/system/layers/base/com/oracle/jdbc/main/

# copy application to deployments
COPY target/java_ee_factoryapi_server.jar /opt/jboss/wildfly/standalone/deployments
EXPOSE 8080 9990

# run command
CMD ["/opt/jboss/wildfly/bin/standalone.sh", "-b", "0.0.0.0", "-bmanagement", "0.0.0.0"]
Module configuration allows direct access to the Oracle JDBC driver.
XML-File : <wildfly-home>/modules/system/layers/base/com/oracle/jdbc/main/module.xml
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<module xmlns="urn:jboss:module:1.0" name="com.oracle.jdbc">
    <resources>
        <resource-root path="ojdbc8.jar"/>
        <resource-root path="ucp.jar"/>
        <resource-root path="xdb6.jar"/>
    </resources>
    <dependencies>
        <module name="javax.api"/>
        <module name="javax.transaction.api"/>
    </dependencies>
</module>
EAR module configuration to access the Oracle jdbc driver.
XML-File : src/main/application/META-INF/jboss-deployment-structure.xml
<?xml version="1.0" encoding="UTF-8"?>
<jboss-deployment-structure>
  <deployment>
    <dependencies>
      <module name="com.oracle.jdbc" />
    </dependencies>
    <resources>
        <resource-root path="ojdbc8.jar"/>
    </resources>
   </deployment>
</jboss-deployment-structure>
Create Docker Image
The Docker Image is created during the Maven build process.
XML-File : pom.xml (part)
...
<plugin>
  <groupId>org.codehaus.mojo</groupId>
  <artifactId>exec-maven-plugin</artifactId>
  <executions>
    <execution>
      <id>docker-build</id>
      <phase>install</phase>
      <goals>
        <goal>exec</goal>
      </goals>
      <configuration>
        <executable>docker</executable>
        <workingDirectory>${project.basedir}</workingDirectory>
        <arguments>
          <argument>build</argument>
          <argument>-t</argument>
          <argument>java_ee_factoryapi_server:${project.version}</argument>
          <argument>.</argument>
        </arguments>
      </configuration>
    </execution>
  </executions>
</plugin>
...

Client Configuration

  • Configuration of a user account.
  • Configuration of JavaEE call context.
Configuration of a User Account
This is the same account already installed throw the Dockerfile.
XML-File : src/main/resources/META-INF/wildfly-config.xml
<?xml version="1.0" encoding="UTF-8"?>
<configuration>
    <authentication-client xmlns="urn:elytron:1.0">
        <authentication-rules>
                    <rule use-configuration="default" />
        </authentication-rules>
        <authentication-configurations>
            <configuration name="default">
                <sasl-mechanism-selector selector="#ALL" />
                <set-mechanism-properties>
                    <property key="wildfly.sasl.local-user.quiet-auth" value="true" />
                 </set-mechanism-properties>
                <providers>
                    <use-service-loader/>
                </providers>
                <!-- Used for EJB over HTTP, remoting invocations will use transparent auth-->
                <set-user-name name="dbworkbench100" />
                <credentials>
                    <clear-password password="dbworkbench100" />
                </credentials>
             </configuration>
        </authentication-configurations>
    </authentication-client>
</configuration>
Configuration of JavaEE Call Context
Java Class : JavaEeContext.java
package factory;

import java.util.Hashtable;

import javax.naming.Context;
import javax.naming.InitialContext;

final class JavaEeContext {
  static Context getContext() throws Exception
  {
    final Hashtable<String, String> jndiProperties = new Hashtable<>();
    jndiProperties.put(Context.INITIAL_CONTEXT_FACTORY, "org.wildfly.naming.client.WildFlyInitialContextFactory");
    if (Boolean.getBoolean("http")) {
      //use HTTP based invocation. Each invocation will be a HTTP request
      jndiProperties.put(Context.PROVIDER_URL, "http://localhost:13456/wildfly-services");
    }
    else {
      //use HTTP upgrade, an initial upgrade requests is sent to upgrade to the remoting protocol
      jndiProperties.put(Context.PROVIDER_URL, "remote+http://localhost:13456");
    }
    return new InitialContext(jndiProperties);
  }

  static String getJndiModulePrefix() throws Exception
  {
    return "ejb:/java_ee_factoryapi_server";
  }
}
Start Docker Image
The Docker Image is started during the Maven client build process. The Oracle Database configuration parameter are set as environment variables and used by standalone.xml.
XML-File : pom.xml (part)
...
  <plugin>
    <groupId>org.codehaus.mojo</groupId>
    <artifactId>exec-maven-plugin</artifactId>
    <executions>
      <!-- start docker -->
      <execution>
        <id>docker-start</id>
        <phase>process-test-classes</phase>
        <goals>
          <goal>exec</goal>
        </goals>
        <configuration>
          <executable>docker</executable>
          <workingDirectory>${project.basedir}</workingDirectory>
          <arguments>
            <argument>run</argument>
            <argument>--name</argument>
            <argument>java_ee_factoryapi_server</argument>
            <argument>--rm</argument>
            <argument>-p</argument>
            <argument>13456:8080</argument>
            <argument>-d</argument>
            <argument>-e</argument>
            <!-- set database url here -->
            <argument>dbUrl=jdbc:oracle:thin:@192.168.0.109:1521/orcl</argument>
            <argument>-e</argument>
            <!-- set your user name here -->
            <argument>dbUsername=dbw_examples</argument>
            <argument>-e</argument>
            <!-- set database user password here -->
            <argument>dbPassword=dbw_examples</argument>
            <argument>java_ee_factoryapi_server:${project.version}</argument>
          </arguments>
        </configuration>
      </execution>
...

Configuring and Running the Example

  • The PL/SQL package has been installed in your Oracle database.
  • Docker is installed and running.
  • Configure the database connection parameter in the client/pom.xml.
  • Just run mvn clean package from the JavaEE parent folder.