How to configure datasource settings in EAP 7 for OpenShift
Environment
- Red Hat JBoss Enterprise Application Platform (EAP) / JBoss EAP for OpenShift
- 8.x
- 7.x
- Red Hat OpenShift Container Platform (OCP)
- 3
- 4
Issue
- How to configure datasource settings in EAP for OpenShift
- How to install jdbc driver in EAP for OpenShift
Resolution
There are three options for configuring datasources in EAP 8 / 7 for OpenShift.
1. Use environment variables with a single-JAR driver deployment
A single-JAR JDBC driver can be deployed using the deployments subdirectory in the root of an s2i build. The driver JAR (e.g. postgresql-42.2.5.jar) will be automatically copied to the JBoss EAP standalone/deployments directory in the running pod. At startup, JDBC 4 compliant drivers present in the deployments directory will be automatically deployed and named based on the JAR file.
$ tree helloworld-custom-datasource
helloworld-custom-datasource
├── datasource.env # does not have to be checked into the git repository, consumed by 'oc new-app ...'
├── deployments
│ └── postgresql-42.2.5.jar
├── pom.xml
└── src
└── main
├── java
│ └── quickstarts
│ └── eap
│ └── rs
│ ├── DataSourceResource.java
│ └── MyApplication.java
└── webapp
└── WEB-INF
The datasource is configured via environment variables which are interpreted (prior to JVM launch) by scripts built into the JBoss EAP for OpenShift image (triggered by execution of /opt/eap/bin/openshift-launch.sh which, indirectly, calls /opt/eap/bin/launch/datasource-common.sh to process the datasource variables) and do the injection. The type of injeciton depends on the version of the image see below at Root Cause section.
Environment variables are commonly provided via a series of --env / -e (single key/value pair) parameters or a single --env-file (new-line delimited, key/value file) parameter supplied to the oc new-app ... command as in the example below:
$ oc new-app --template=eap72-basic-s2i -p APPLICATION_NAME=helloworld-custom-datasource -p SOURCE_REPOSITORY_URL=https://<your-git-repository>/jboss-openshift-examples.git -p SOURCE_REPOSITORY_REF=master -p CONTEXT_DIR=helloworld-custom-datasource_by-env --env-file=datasource.env
The datasource.env might consist of content such as the below
DB_SERVICE_PREFIX_MAPPING=PostgresNonXA-POSTGRES=DS1,PostgresXA-POSTGRES=DS2
DS1_URL=jdbc:postgresql://postgres:5432/postgres?socketTimeout=310
DS1_JNDI=java:jboss/PostgresDS1
DS1_DRIVER=postgresql-42.2.5.jar
DS1_USERNAME=postgres
DS1_PASSWORD=postgres
#DS1_MAX_POOL_SIZE=20
#DS1_MIN_POOL_SIZE=20
DS1_CONNECTION_CHECKER=org.jboss.jca.adapters.jdbc.extensions.postgres.PostgreSQLValidConnectionChecker
DS1_EXCEPTION_SORTER=org.jboss.jca.adapters.jdbc.extensions.postgres.PostgreSQLExceptionSorter
# Note that datasources are XA by default. Non-XA datasource require the parameter below.
DS1_NONXA=true
DS2_URL=jdbc:postgresql://postgres:5432/other-database?socketTimeout=310
DS2_JNDI=java:jboss/datasources/other-ds
DS1_DRIVER=postgresql-42.2.5.jar
DS2_USERNAME=postgres
DS2_PASSWORD=postgres
#DS2_MAX_POOL_SIZE=20
#DS2_MIN_POOL_SIZE=20
DS2_CONNECTION_CHECKER=org.jboss.jca.adapters.jdbc.extensions.postgres.PostgreSQLValidConnectionChecker
DS2_EXCEPTION_SORTER=org.jboss.jca.adapters.jdbc.extensions.postgres.PostgreSQLExceptionSorter
# Note that datasources are XA by default. Non-XA datasource require the parameter below.
#DS2_NONXA=true
Properties may also be specified in ConfigMap objects for which content is imported into environment variables via oc set env --from=configmap/myconfigmap .... Alternatively, the environment variables may be expressed in yaml files.
2. Override the default standalone-openshift.xml and use a module-based driver deployment
As mentioned in Customizing standalone-openshift.xml, you can override default standalone-openshift.xml by S2I build.
Note Use of a module-based driver deployment is required if the driver consists of multiple JAR files
- The
standalone-openshift.xmllocated in theconfigurationsubdirectory of the s2i project root will be copied to the JBoss EAPstandalone/configurationdirectory.- Both the binding of a driver name to the driver module and the datasource configuration are hard-coded directly into this file. There is an This content is not included.open request to make it possible to configure the driver entry via environment variables without custom scripting.
- The JDBC driver and
module.xmllocated in themodulessubdirectory of the s2i project root will be copied to the JBoss EAPstandalone/modulesdirectory.
This content is not included.See example that has the following directory structure:
$ tree helloworld-custom-datasource
helloworld-custom-datasource
├── README.md
├── configuration
│ └── standalone-openshift.xml
├── modules
│ └── org
│ └── postgresql
│ └── custom
│ └── main
│ ├── module.xml
│ └── postgresql-42.2.5.jar
├── pom.xml
└── src
└── main
├── java
│ └── quickstarts
│ └── eap
│ └── rs
│ ├── DataSourceResource.java
│ └── MyApplication.java
└── webapp
└── WEB-INF
Because driver/datasource configuration are hardcoded into the custom standalone-openshift.xml, no environment variables need to be supplied to the application to configure the datasource and the application creation command might appear as below:
$ oc new-app --template=eap72-basic-s2i -p APPLICATION_NAME=helloworld-custom-datasource -p SOURCE_REPOSITORY_URL=https://<your-git-repository>/jboss-openshift-examples.git -p SOURCE_REPOSITORY_REF=master -p CONTEXT_DIR=helloworld-custom-datasource
3. Use environment variable with a module-based driver deployment and a custom install.sh
Using custom s2i scripts, it is possible to create a module-based driver deployment and datasource without overriding the default standalone-openshift.xml.
Note Use of a module-based driver deployment is required if the driver consists of multiple JAR files
This approach for module-based driver deployment has greater complexity than use of a custom standalone-openshift.xml but does not require re-creation of the standalone-openshift.xml each time the JBoss EAP for OpenShift source image must be updated (since the standalone-openshift.xml is subject to change with each image version). There is an This content is not included.open request to make it possible to configure the driver entry via environment variables without custom scripting.
This content is not included.See example that has the following directory structure:
$ tree -a helloworld-custom-datasource_by-env
helloworld-custom-datasource_by-env
├── .s2i
│ └── environment
├── README.md
├── pom.xml
├── runtime_artifact
│ └── datasource.env
├── s2i_artifact
│ ├── drivers.env
│ ├── install.sh
│ └── modules
│ └── org
│ └── postgresql
│ └── custom
│ └── main
│ ├── module.xml
│ └── postgresql-42.2.5.jar
└── src
└── main
├── java
│ └── quickstarts
│ └── eap
│ └── rs
│ ├── DataSourceResource.java
│ └── MyApplication.java
└── webapp
└── WEB-INF
└── .gitkeep
The binding of a driver name to the driver module is done via properties specified in the drivers.env. Unlike datasource properties, there is no automated handling for driver properties so addition of a custom driver module (when not hardcoding the driver name/module binding directly into a custom standalone-openshift.xml) requires explicit steps during the s2i build process. Driver configuration is injected into the standalone-openshift.xml via the configure_drivers function declared in the build image' /usr/local/s2i/install-common.shscript (see the sample install.sh). Module creation (i.e. copying the physical driver JAR to the deploy image) is also a custom build step initiated by the sample install.sh though the module could simply be placed in the s2i project root as in the second scenario above (and the install.sh could omit the module installation step).
As discussed in connection with the first approach above, configuration of the datasource is performed using environment variables.
See also WARN At least one MYDS_XA_CONNECTION_PROPERTY_property for datasource MYDS is required ....
Root Cause
About injection
EAP 7.2 images
EAP 7.2 images properties injection is based on markup injections - see below:
The datasource is configured via environment variables which are interpreted (prior to JVM launch) by scripts built into the JBoss EAP for OpenShift image (triggered by execution of /opt/eap/bin/openshift-launch.sh which, indirectly, calls /opt/eap/bin/launch/datasource-common.sh to process the datasource variables) which inject content into the standalone/configuration/standalone-openshift.xml at the <!-- ##DATASOURCES## --> insertion point.
EAP 7.3+ images
EAP 7.3+ images properties injection is based on CLI commands - see below:
The datasource is configured via environment variables which are interpreted (prior to JVM launch) by scripts built into the JBoss EAP for OpenShift image (triggered by execution of /opt/eap/bin/openshift-launch.sh which, indirectly, calls /opt/eap/bin/launch/datasource-common.sh to process the datasource variables) which inject content into the standalone/configuration/standalone-openshift.xml via CLI commands. The CLI is executed at the start of the EAP pod and its output is shown on the execution of the pod.
This solution is part of Red Hat’s fast-track publication program, providing a huge library of solutions that Red Hat engineers have created while supporting our customers. To give you the knowledge you need the instant it becomes available, these articles may be presented in a raw and unedited form.