WildFly 10 / JBoss EAP 7.0

EJBCA 6.x compiles, deploys and runs with WildFly 10 (release following 6.3.1.1). JBoss EAP 7.0 is based on Wildfly 10 and these instructions apply for EAP 7.0 as well. Note that JDK 8 is required.

For WildFly, deploy and install does not automatically configure the application server for you. Configure the application server according to the following instructions:

Run your installation without mixing root and user accounts as this may lead to root privileges being set on files which later WildFly is unable to read. It is recommended to run the installation as your "wildfly" user.

Add Database Driver

Add MariaDB database driver by hot-deploying it into the Ddeployment directory. This will be picked up by WildFly and deployed so we can create a datasource straight away. You can use a generic name, without version number, in order to get a generic 'driver-name' for the data source command.

>cp mariadb-java-client-2.1.0.jar wildfly_home/standalone/deployments/mariadb-java-client.jar

If you are using another type of database, copy the JDBC driver to the deployments-directory and make note of the driver class and driver-name shown in the server log and for later use when adding the DataSource. E.g.

... INFO [org.jboss.as.connector.deployers.jdbc] (...) WFLYJCA0005: Deploying non-JDBC-compliant driver class org.postgresql.Driver (version 9.2)
... INFO [org.jboss.as.connector.deployers.jdbc] (...) WFLYJCA0018: Started Driver service with driver-name = postgresql-jdbc3.jar

Increase allowed Memory Usage

By default, only 512MiB of heap is allowed. Edit wildfly_home/bin/standalone.conf to increase this to a more suitable value, e.g.

JAVA_OPTS="-Xms2048m -Xmx2048m -Djava.net.preferIPv4Stack=true"

Create Database

Before creating the datasource in the following step, create your database. In MariaDB the command to create the database, matching the datasource in the next step, and add privileges to connect to the database is:

$ mysql -u root -p
mysql> CREATE DATABASE ejbca CHARACTER SET utf8 COLLATE utf8_general_ci;
mysql> GRANT ALL PRIVILEGES ON ejbca.* TO 'ejbca'@'localhost' IDENTIFIED BY 'ejbca';

You should define secure passwords for your database in production. You can also improve the security by limiting access to tables. For more information, see Database Privileges.

If you don't set utf8 as character set, EJBCA may not start because of index limitations if using the default charset utf8mb4 in some configurations of MariaDB/MySQL. It will result in an error:

Specified key was too long; max key length is 767 bytes

In some configurations for InnoDB the binlog_format defaults to statement. Running EJBCA requires is to be set to row.Example: binlog_format=row

Add Datasource

Add data source for EJBCA to use.

Start JBoss and run two commands in JBoss CLI. Note that "-jindi-name" is linked to the database.properties value (default value in this example).

> wildfly_home/bin/jboss-cli.sh -c
> data-source add --name=ejbcads --driver-name="mariadb-java-client.jar" --connection-url="jdbc:mysql://127.0.0.1:3306/ejbca" --jndi-name="java:/EjbcaDS" --use-ccm=true --driver-class="org.mariadb.jdbc.Driver" --user-name="ejbca" --password="ejbca" --validate-on-match=true --background-validation=false --prepared-statements-cache-size=50 --share-prepared-statements=true --min-pool-size=5 --max-pool-size=150 --pool-prefill=true --transaction-isolation=TRANSACTION_READ_COMMITTED --check-valid-connection-sql="select 1;"
> :reload

If you are using another type of database, adapt the statement above with the correct driver-name, connection-url, driver-class and check-valid-connection-sql.

Configure WildFly Remoting

EJBCA needs to use JBoss Remoting for the EJBCA CLI to work. We configure it to use a separate port (start by removing any old configuration if it exists).

/subsystem=remoting/http-connector=http-remoting-connector:remove
/subsystem=remoting/http-connector=http-remoting-connector:add(connector-ref="remoting",security-realm="ApplicationRealm")
/socket-binding-group=standard-sockets/socket-binding=remoting:add(port="4447")
/subsystem=undertow/server=default-server/http-listener=remoting:add(socket-binding=remoting)
:reload

images/s/en_US/7901/58be3fa11e9ad58113c0ea45e7063389a7c7d344/_/images/icons/emoticons/warning.svg Wait for reload to complete by checking the server log or the result of ":read-attribute(name=server-state)" before continuing.

Configure Logging

Configure logging in JBoss, to be able to dynamically change logging (DEBUG enabled in this example).

/subsystem=logging/logger=org.ejbca:add
/subsystem=logging/logger=org.ejbca:write-attribute(name=level, value=DEBUG)
/subsystem=logging/logger=org.cesecore:add
/subsystem=logging/logger=org.cesecore:write-attribute(name=level, value=DEBUG)

Deploy EJBCA

Finally build and deploy the EJBCA (application ear file) to WildFly, without touching any WildFly configuration, by running the EJBCA deployear command.

Before running deployear below, ensure to point to your application server by setting APPSRV_HOME and configure your database in conf/database.properties.

Run the following commands at the regular command prompt in EJBCA_HOME:

ant clean deployear

Check the JBoss/WildFly console or server.log that EJBCA was deployed without errors.

Run Install

Run the installation part of EJBCA creating the initial Management CA (for TLS and Super administrator), as well as TLS and Superadmin keystores.

If you are moving an existing installation that already has TLS keystores available, this step is not needed.

ant runinstall

Deploy TLS Keystores to WildFly

After the install, TLS keystores have been created. Run this command to copy them to wildfly_home/standalone/configuration/keystore:

ant deploy-keystore

Remove existing TLS and HTTP Configuration

Run the following commands in JBoss CLI to remove existing TLS and HTTP configuration (just to be safe).

/subsystem=undertow/server=default-server/http-listener=default:remove
/subsystem=undertow/server=default-server/https-listener=https:remove
/socket-binding-group=standard-sockets/socket-binding=http:remove
/socket-binding-group=standard-sockets/socket-binding=https:remove
:reload

Wait for reload to complete by checking the server log or the result of ":read-attribute(name=server-state)" before continuing.

Configure TLS

Make sure the passwords in this section are correct, in order for the commands not to fail. In production the passwords should be changed to "real" passwords.

Run the following commands in JBoss CLI (jboss-cli.sh -c) to configure TLS:

  1. Add interfaces, using 0.0.0.0 to make it available for the world:

    /interface=http:add(inet-address="0.0.0.0")
    /interface=httpspub:add(inet-address="0.0.0.0")
    /interface=httpspriv:add(inet-address="0.0.0.0")
    /socket-binding-group=standard-sockets/socket-binding=http:add(port="8080",interface="http")
    /subsystem=undertow/server=default-server/http-listener=http:add(socket-binding=http)
    /subsystem=undertow/server=default-server/http-listener=http:write-attribute(name=redirect-socket, value="httpspriv")
    :reload
  2. Wait for reload to complete by checking the server log or the result of ":read-attribute(name=server-state)" before continuing.

  3. Configure identities and socket bindings:

    1. Update the keystore alias to match httpsserver.hostname in web.properties. Also, update the keystore-password for keystore.jks to match httpsserver.password and the keystore-password for truststore.jks to match java.truststore in web.properties.

      /core-service=management/security-realm=SSLRealm:add()
      /core-service=management/security-realm=SSLRealm/server-identity=ssl:add(keystore-path="${jboss.server.config.dir}/keystore/keystore.jks", keystore-password="serverpwd", alias="localhost")
      /core-service=management/security-realm=SSLRealm/authentication=truststore:add(keystore-path="${jboss.server.config.dir}/keystore/truststore.jks", keystore-password="changeit")
      /socket-binding-group=standard-sockets/socket-binding=httpspriv:add(port="8443",interface="httpspriv")
      /socket-binding-group=standard-sockets/socket-binding=httpspub:add(port="8442", interface="httpspub")
    2. Restart the application server completely. Wait for it to finish start up by checking the server log or the result of ":read-attribute(name=server-state)" before continuing.

      /subsystem=undertow/server=default-server/https-listener=httpspriv:add(socket-binding=httpspriv, security-realm="SSLRealm", verify-client=REQUIRED)
      /subsystem=undertow/server=default-server/https-listener=httpspriv:write-attribute(name=max-parameters, value="2048")
      /subsystem=undertow/server=default-server/https-listener=httpspub:add(socket-binding=httpspub, security-realm="SSLRealm")
      /subsystem=undertow/server=default-server/https-listener=httpspub:write-attribute(name=max-parameters, value="2048")
      :reload
  4. Finalize the Wildfly configuration with the following important items:

    /system-property=org.apache.tomcat.util.buf.UDecoder.ALLOW_ENCODED_SLASH:add(value=true)
    /system-property=org.apache.catalina.connector.CoyoteAdapter.ALLOW_BACKSLASH:add(value=true)
    /system-property=org.apache.catalina.connector.URI_ENCODING:add(value="UTF-8")
    /system-property=org.apache.catalina.connector.USE_BODY_ENCODING_FOR_QUERY_STRING:add(value=true)
    /subsystem=webservices:write-attribute(name=wsdl-host, value=jbossws.undefined.host)
    /subsystem=webservices:write-attribute(name=modify-wsdl-address, value=true)
    :reload

If you are using OCSP GET requests, setting URI encoding and allowing encoding for Query and backslash above are needed.

At this point, WildFly will most likely need to be restarted using ":shutdown(restart=true)".

Optional: Enable AJP Connector

Only needed if you run an Apache front-end in front of WildFly.

/subsystem=undertow/server=default-server/ajp-listener=ajp-listener:add(socket-binding=ajp, scheme=https, enabled=true)

Optional: Add Support for PKCS#11 (HSMs)

WildFly by default isolates most sun classes. EJBCA configures JBoss/WildFly to expose these classes (sun/security/pkcs11/wrapper), as of EJBCA 6.6.3, by using a jboss-deployment-structure.xml. This makes configuration in modules/system/layers/base/sun/jdk/main/module.xml not needed.

Optional: Add Support for Sending Email

If you need support for sending email (smtp), configure EjbcaMail with:

/socket-binding-group=standard-sockets/remote-destination-outbound-socket-binding=ejbca-mail-smtp:add(port="993", host="my.mail.server")
/subsystem=mail/mail-session="java:/EjbcaMail":add(jndi-name=java:/EjbcaMail, from=noreply@mymail)
/subsystem=mail/mail-session="java:/EjbcaMail"/server=smtp:add(outbound-socket-binding-ref=ejbca-mail-smtp, tls=true, username=smtpuser, password=smtppassword)