Chapter 2. Migrating from Red Hat JBoss Enterprise BRMS 5.3.1 to Red Hat JBoss BRMS 6.x or Red Hat JBoss BPM Suite 6.x

2.1. What is New

With version 6.0, Red Hat introduces Red Hat JBoss Business Process Management (BPM) Suite which includes Red Hat JBoss BRMS 6. You can choose to migrate from Red Hat JBoss BRMS 5.3.1 to either Red Hat JBoss BRMS 6.x or Red Hat JBoss BPM Suite 6.x. However, Red Hat JBoss BRMS 6 does not include business process management capabilities.

Migrating to Red Hat JBoss BRMS 6.x or Red Hat JBoss BPM Suite 6.x from BRMS 5.3.1 provides the following benefits:

  • A higher performance rule engine based on the Drools 6 community project
  • Improved rule authoring tools and an enhanced, integrated user interface
  • A common defined methodology for building and deployment using Maven as the basis for repository management
  • A heuristic planning engine based on the OptaPlanner community project
  • Use of the PHREAK algorithm to handle a larger number of rules and facts
  • New Data Modeler that replaces the declarative Fact Model Editor
  • Many stability, usability and functional improvements

Because Red Hat JBoss BRMS 6.x is backwards compatible with Red Hat JBoss BRMS 5.x, when you migrate to Red Hat JBoss BRMS 6 the rules created with Red Hat JBoss BRMS 5.x will still execute on Red Hat JBoss BRMS 6.x without changes.

A migration tool is provided to facilitate migration of the content of a JBoss BRMS 5.x repository to Red Hat JBoss BRMS 6.x or Red Hat JBoss BPM Suite 6.x. Note, however, that BPMN2 process models created with Red Hat JBoss BRMS 5.x will not execute on Red Hat JBoss BRMS 6.

The following sections describe other changes between these versions.

Naming Changes

First and foremost it is important to understand how older components in the 5 branch that you were familiar with relate to in the 6 branch. The biggest change, of course, is the name of the product and its structure.

JBoss Enterprise BRMS is now called Red Hat JBoss BRMS. Red Hat JBoss BRMS, or Red Hat JBoss RMS, is a standalone product with its own workbench and is used solely to create and manage your business rules.

A new product, called JBoss BPM Suite, or Red Hat JBoss BPM Suite encapsulates the Red Hat JBoss RMS product and on top of that provides Business Process Management which allows you to create, manage, validate, and deploy Business Processes and Rules.

Component Name Migration

Several components from the 5 branch to 6 branch have been renamed or merged with other components to provide a better working environment. The figure below captures these changes.

API Name Changes

5.x API (deprecated in 6.x)Replaced in 6.x by

org.drools.KnowledgeBase

org.kie.api.KieBase

org.drools.runtime.StatefulKnowledgeSession

org.kie.api.runtime.KieSession

org.drools.runtime.StatelessKnowledgeSession

org.kie.api.runtime.KieSession

org.drools.builder.KnowledgeBuilderFactory

org.kie.internal.builder.KnowledgeBuilderFactory

org.drools.io.ResourceFactory

org.kie.internal.io.ResourceFactory

org.drools.io.ResourceType

org.kie.internal.io.ResourceType

org.drools.runtime.Environment

org.kie.api.runtime.Environment

org.drools.runtime.EnvironmentName

org.kie.api.runtime.EnvironmentName

org.drools.runtime.KnowledgeSessionConfiguration

org.kie.api.runtime.KieSessionConfiguration

org.drools.event.AgendaEventListener

org.kie.api.event.rule.AgendaEventListener

org.drools.event.rule.AgendaEventListener

org.kie.api.event.rule.AgendaEventListener

org.drools.event.DefaultAgendaEventListener

org.kie.drools.core.event.DefaultAgendaEventListener

org.drools.event.rule.DefaultAgendaEventListener

org.kie.api.event.rule.DefaultAgendaEventListener

org.drools.event.process.ProcessEventListener

org.kie.api.event.process.ProcessEventListener

org.drools.event.process.DefaultProcessEventListener

org.kie.api.event.process.DefaultProcessEventListener

org.drools.logger.KnowledgeRuntimeLogger

org.kie.api.logger.KieRuntimeLogger

org.drools.logger.KnowledgeRuntimeLoggerFactory

org.kie.api.logger.KieLoggers

Repository Change

Red Hat JBoss BRMS and Red Hat JBoss BPM Suite 6 are backed by a Git repository for source management while Red Hat JBoss RMS 5 was backed by a JCR/JackRabbit implementation. A tool to migrate the repository to Git is provided and discussed later in this guide.

Changes to the REST API

The base url for working with the REST API has changed from http://SERVER_ADDRESS:PORT/jboss-brms/rest/ to http://SERVER_ADDRESS:PORT/business-central/rest/.

Migrating Task Service

Red Hat JBoss BPM Suite 6 provides support for a locally running task server only. This means that you do not need to setup any messaging service in your project. This differs from Red Hat JBoss RMS 5 because it provided a task server that was bridged from the core engine by using, most commonly, the messaging system provided by HornetQ.

To help you bridge the gap until you can migrate this in your current architecture, there is a helper or utility method, LocalHTWorkItemHandler located in org.jbpm.services.task.wih.

Since the TaskService API is part of the public API you will now need to refactor your imports because of package changes, and refactor your methods due to API changes themselves.

Logging factory

Besides the API name change, logging is now implemented through the org.kie.api.logger package, which contains the factory class KieLoggers that can be used to create instances of the KieRuntimeLogger.

2.2. How To Migrate

Migrating your projects from Red Hat JBoss BPM Suite 5 to Red Hat JBoss BPM Suite 6 requires careful planning and step by step evaluation of the various issues. You can plan for migration either manually, or by using automatic processes. Most real world migration will require a combination of these two processes.

Because Red Hat JBoss BPM Suite 6 uses Git for storing assets, artifacts and code repositories including processes and rules, you should start by creating an empty project in Red Hat JBoss BPM Suite 6 as the basis for your migration with dummy files as placeholders for the various assets and artifacts. Running a Git clone of this empty project into your favorite IDE will initiate the migration process.

Based on the placeholder files in your cloned project, you can start adding assets at the correct locations. The Red Hat JBoss BPM Suite 6 system is smart enough to pick these changes and apply them correctly. Ensure that when you are importing old rule files that they are imported with the right package name structure.

Since Maven is used for building projects, the projects assets like the rules, processes and models are accessible as a simple jar file.

This section lists the generally accepted step by step ways to migrate your project. These are just guidelines though, and actual migration may vary a lot from this.

In general, you should:

  1. Migrate the data first: These are your business assets.
  2. Next, migrate your runtime processes.
  3. Finally, convert old API calls to new ones one by one.

Let us look at these steps in more detail in the next few sections:

2.2.1. Data Migration

To migrate data from Red Hat JBoss BPM Suite 5, do the following:

  1. Download the migration tool by logging in at the Red Hat Customer Portal and then navigating to Red Hat JBoss BPM Suite Software Downloads section. Click on Red Hat JBoss BPM Suite Migration Tool to download the ZIP archive.
  2. Unzip the downloaded ZIP archive in a directory of your choice and navigate to this directory in a command prompt. This directory contains four folders:

    • bin - contains the launch scripts.
    • jcr-exporter-libs - contains the libs specific to the export-from-JCR part of the migration.
    • vfs-importer-libs - contains the libs specific to the import-into-Git part of the migration.
    • conf - contains global migration tool configuration.
  3. For production databases, copy the JDBC driver for the database that is used by the JCR repository into the jcr-exporter-libs directory of the migration tool.
  4. Execute the following command:

    ./bin/runMigration.sh -i <source-path> -o <destination-path> -r <repository-name>

    Where:

    • <source-path> is a path to a source JCR repository.
    • <desintation-path> is a path to a destination Git VFS. This folder must not exist already.
    • <repository-name> an arbitrary name for the new repository.

The repository is migrated at the specified destination.

Besides the -i command, you can also use -h to print out a help message and -f which forces an overwrite of the output directory, thus eliminating the need for manual deletion of this directory.

Importing the repository in Business Central

The repository can be imported in business central by cloning it. In the Administration perspective, click on the Repositories menu and then click on Clone Repository menu to start the process.

Note

Assets can also be migrated manually as they are just text files. The BPMN2 specification and the DRL syntax did not change between the different versions.

Importing the repository in JBDS

To import the repository in JBoss Developer Studio, do the following

  1. Start JBoss Developer Studio.
  2. Start the Red Hat JBoss BPM Suite server (if not already running) by selecting the server from the server tab and click the start icon.
  3. Select FileImport…​ and navigate to the Git folder. Open the Git folder to select Projects from Git and click next.
  4. Select the repository source as Existing local repository and click next.
  5. Select the repository that is to be configured from the list of available repositories.
  6. Import the project as a general project in the next window and click next. Name this project and click Finish.

2.2.2. Runtime Migration

To run Red Hat JBoss BPM Suite 5 processes in Red Hat JBoss BPM Suite 6, do the following:

  1. Set the system property jbpm.v5.id.strategy to true in the Red Hat JBoss BPM Suite standalone.xml file:

    <property name="jbpm.v5.id.strategy" value="true"/>
  2. Load the KieSession as shown here:

    KieSession ksession = JPAKnowledgeService.loadStatefulKnowledgeSession(sessionID, kbase, sessionConf, env);
  3. Continue the normal execution of the process using KieSession methods:

    ksession.signalEvent("SomeEvent", null);

2.2.3. API and Backwards Compatibility

Migrating to Version 6.1 and later

In version 6.1, 5.x APIs are no longer officially supported.

Red Hat JBoss BPM Suite no longer provides backward compatibility with the rule, event, and process application programming interface (API) from Red Hat JBoss RMS 5. The content of the knowledge-api JAR file is no longer supported in version 6.1 and onward, and is replaced by APIs contained in the kie-api JAR file that were introduced in Red Hat JBoss BPM Suite 6.0.

If you used the legacy 5.x API (located in knowledge-api.jar), please migrate (rewrite) the API calls to the new KIE API. Please be aware that several other APIs have changed between Red Hat JBoss RMS 5.x and Red Hat JBoss BPM Suite 6.x, namely the task service API and the REST API.

Migrating to Version 6.0

The Red Hat JBoss BPM Suite 6 system provides backward compatibility with the rule, event and process interactions from Red Hat JBoss RMS 5. You should eventually migrate (rewrite) these interactions to the all new revamped core API because this backward compatibility is likely to be deprecated.

If you cannot migrate your code to use the new API, then you can use the API provided by the purpose built knowledge-api jar for backwards compatible code. This API is the public interface for working with Red Hat JBoss BPM Suite and Red Hat JBoss RMS and is backwards compatible.

If you are instead using the REST API in Red Hat JBoss BPM Suite 5, note that this has changed as well and there is no mechanism in it for backwards compatibility.

2.3. Advanced Migration

2.3.1. REST API Migration

As you know, there are two ways you can use Red Hat JBoss BRMS/Red Hat JBoss BPM Suite: in an embedded mode, or in a remote mode. In the embedded mode, you package the runtime libraries with your application and execute the BPMN processes in the same JVM. In the remote mode, the business assets are created, deployed and executed in the same server, but they are accessed via a remote client application using the REST or the JMS API.

Both of these modes presents different challenges when it comes to the migration. In this section we will focus on the migration for the remote usage of Red Hat JBoss BPM Suite with the help of a REST example.

REST API Example

This example shows how to:

  • Start a process which is already deployed on the Red Hat JBoss BPM Suite server.
  • Pass parameters to this process during its creation.

The client side for Red Hat JBoss BRMS 5 can be created using the following code:

import org.apache.commons.httpclient.HttpClient;
import org.apache.commons.httpclient.HttpMethod;
import org.apache.commons.httpclient.NameValuePair;
import org.apache.commons.httpclient.methods.GetMethod;
import org.apache.commons.httpclient.methods.PostMethod;
import org.apache.commons.httpclient.methods.multipart.MultipartRequestEntity;
import org.apache.commons.httpclient.methods.multipart.Part;
import org.apache.commons.httpclient.methods.multipart.StringPart;
import org.jboss.bpm.console.client.model.ProcessDefinitionRef;
import org.jboss.bpm.console.client.model.ProcessDefinitionRefWrapper;
import org.jboss.bpm.console.client.model.ProcessInstanceRef;


 public class RestClientStartWithParam {
    private static final String BASE_URL = "http://localhost:8080/business-central-server/rs/";
    private static final String AUTH_URL = BASE_URL + "identity/secure/j_security_check";
    private final String username;
    private final String password;

    private static final String PROCESS_ID = "defaultPackage.hello";

    public RestClientStartWithParam(final String u, final String p) {
        this.username = u;
        this.password = p;
    }

    public static void main(String[] args) throws Exception {

        RestClientStartWithParam client = new RestClientStartWithParam("admin", "admin");

        // get process definitions
        ProcessDefinitionRefWrapper processDefinitionWrapper = client.getProcessDefinitions(client);

        // pick up "com.sample.bpmn.hello"
        ProcessDefinitionRef definitionRef = null;
        for (ProcessDefinitionRef processDefinitionRef : processDefinitionWrapper.getDefinitions()) {
            if (processDefinitionRef.getId().equals(PROCESS_ID)) {
                definitionRef = processDefinitionRef;
                break;
            }
        }
        if (definitionRef == null) {
            System.out.println(PROCESS_ID + " doesn't exist");
            return;
        }

        // start a process instance with parameters
        Map<String, String> params = new HashMap<String, String>();
        params.put("employee", "thomas");
        params.put("reason", "theReason");
        client.startProcessWithParameters(client, definitionRef, params);
    }

        private void startProcessWithParameters(RestClientStartWithParam client, ProcessDefinitionRef def,
            Map<String, String> params) throws Exception {
        String newInstanceUrl = BASE_URL + "form/process/" + def.getId() + "/complete";
        String dataFromService = client.getDataFromService(newInstanceUrl, "POST", params, true);

        System.out.println(dataFromService);
    }

    // get DataFromService method can be implemented like this

    private String getDataFromService(String urlpath, String method, Map<String, String> params, boolean multipart)
            throws Exception {
        HttpClient httpclient = new HttpClient();

        HttpMethod theMethod = null;
        StringBuffer sb = new StringBuffer();

        if ("GET".equalsIgnoreCase(method)) {
            theMethod = new GetMethod(urlpath);
        } else if ("POST".equalsIgnoreCase(method)) {
            theMethod = new PostMethod(urlpath);

            if (params != null) {

                if (multipart) {
                    List<Part> parts = new ArrayList<Part>();
                    for (String key : params.keySet()) {
                        StringPart stringPart = new StringPart(key, params.get(key));
                        stringPart.setCharSet("UTF-8");
                        parts.add(stringPart);
                    }
                    ((PostMethod) theMethod).setRequestEntity(new MultipartRequestEntity(parts.toArray(new Part[0]),
                            theMethod.getParams()));
                } else {

                    List<NameValuePair> nameValuePairList = new ArrayList<NameValuePair>();
                    for (String key : params.keySet()) {
                        nameValuePairList.add(new NameValuePair(key, params.get(key)));
                    }
                    ((PostMethod) theMethod).setRequestBody(nameValuePairList.toArray(new NameValuePair[0]));

                }
            }

        }

        if (username != null && password != null) {

            try {
                int result = httpclient.executeMethod(theMethod);
                System.out.println("result = " + result);
                // System.out.println(theMethod.getResponseBodyAsString());
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                theMethod.releaseConnection();
            }
            PostMethod authMethod = new PostMethod(AUTH_URL);
            NameValuePair[] data = { new NameValuePair("j_username", username),
                    new NameValuePair("j_password", password) };
            authMethod.setRequestBody(data);
            try {
                int result = httpclient.executeMethod(authMethod);
                System.out.println("result = " + result);
                // System.out.println(theMethod.getResponseBodyAsString());
            } catch (IOException e) {
                e.printStackTrace();
            } finally {
                authMethod.releaseConnection();
            }
        }

        try {
            int result = httpclient.executeMethod(theMethod);
            System.out.println("result = " + result);
            sb.append(theMethod.getResponseBodyAsString());
            String rawResult = sb.toString();
            return rawResult;

        } catch (Exception e) {
            throw e;
        } finally {
            theMethod.releaseConnection();
        }
    }

The Red Hat JBoss BRMS 5 endpoints are documented in BRMS 5.0 User Guide and BRMS 5.0 Business Process Management Guide.

As you can see, even this very simple example looks rather complex when implemented. The reason for this is partially that there is no native client for Red Hat JBoss BRMS 5 server. You can however choose the optional web client—​Apache HttpClient, RestEasy or even use just plain java.net libraries. This applies in Red Hat JBoss BPM Suite/BRMS 6 as well—​you can still choose the web client—​however, there is also a native java client provided for remote communication with version 6 which is much simpler to use.

Migrating to Red Hat JBoss BRMS/Red Hat JBoss BPM Suite 6

Let us migrate the same use case to Red Hat JBoss BPM Suite 6:

  • process is already deployed in the Red Hat JBoss BPM Suite server
  • we want to start it with some parameters
  • this time, there are some human tasks in this process, so we want to complete those.

All of the available REST endpoints for Red Hat JBoss BRMS and Red Hat JBoss BPM Suite are documented here.

You can use either the Business Central remote API, or the Intelligent Process Server remote API. Unless you configure the Intelligent Process Server and Business Central to use the same data source, choose migration API based on what you are using at the moment. See chapter Unified Execution Servers of the Red Hat JBoss BPM Suite Administration and Configuration Guide for more details.

Intelligent Process Server API Example

To migrate using the Intelligent Process Server API, see the following example:

import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.kie.server.api.model.instance.TaskSummary;
import org.kie.server.client.KieServicesClient;
import org.kie.server.client.KieServicesConfiguration;
import org.kie.server.client.KieServicesFactory;
import org.kie.server.client.ProcessServicesClient;
import org.kie.server.client.UserTaskServicesClient;

public class Main {

    private static final String APP_URL = "http://localhost:8080/kie-server/services/rest/server";
    private static final String USER = "john";
    private static final String PASSWORD = "john";

    // Container ID in the Intelligent Process Server/Realtime Decision Server
    private static final String CONTAINER_ID = "sample-container";
    private static final String PROCESS_DEFINITION_ID = "sample-project.sample-process";

    public static void main(String[] args) {
        // Configuration can be used for additional settings, like timeout, marshalling format...
        KieServicesConfiguration configuration = KieServicesFactory.newRestConfiguration(APP_URL, USER, PASSWORD);
        KieServicesClient kieServicesClient = KieServicesFactory.newKieServicesClient(configuration);
        ProcessServicesClient processClient = kieServicesClient.getServicesClient(ProcessServicesClient.class);
        UserTaskServicesClient taskClient = kieServicesClient.getServicesClient(UserTaskServicesClient.class);

        Map<String, Object> params = new HashMap<String, Object>();
        params.put("employee", "thomas");
        params.put("reason", "theReason");
        processClient.startProcess(CONTAINER_ID, PROCESS_DEFINITION_ID, params);

        List<TaskSummary> tasks = taskClient.findTasksAssignedAsPotentialOwner(USER, 0, 10);
        taskClient.startTask(CONTAINER_ID, tasks.get(0).getId(), USER);
        // not passing any data = null
        taskClient.completeTask(CONTAINER_ID, tasks.get(0).getId(), USER, null);
    }
}

For a list of Maven dependencies, see example Client Application Intelligent Process Server Dependencies of the Red Hat JBoss BPM Suite Development Guide.

Business Central API Example

To migrate using the Business Central API, see the following example:

import java.net.MalformedURLException;
import java.net.URL;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.kie.api.runtime.KieSession;
import org.kie.api.task.TaskService;
import org.kie.api.task.model.TaskSummary;
import org.kie.api.runtime.manager.RuntimeEngine;
import org.kie.remote.client.api.RemoteRuntimeEngineFactory;

 public class Main {

	public static void main(String[] args) throws MalformedURLException {

		/*
		 * Set the parameters according to your installation
		 */

		String APP_URL = "http://localhost:8080/business-central/";

		URL url = new URL(APP_URL);
		String USER = "anton";
		String PASSWORD = "password1!";

    RuntimeEngine engine = RemoteRuntimeEngineFactory
                    .newRestBuilder()
                    .addUrl(url)
                    .addUserName(USER)
                    .addPassword(PASSWORD)
                    .addDeploymentId("org.redhat.gss:remote-test-project:3.0")
                    .build();

    KieSession kSession = engine.getKieSession();
    TaskService taskService = engine.getTaskService();

		 // start a process instance with parameters
     Map<String, Object> params = new HashMap<String, Object>();
     params.put("employee", "thomas");
     params.put("reason", "theReason");
     kSession.startProcess("com.sample", params);

     List<TaskService> taskSummaryList = taskService.getTasksAssignedAsPotentialOwner("anton","en-UK");
     taskService.claim(taskSummaryList.get(0).getId(), "anton");
     taskService.start(taskSummaryList.get(0).getId(), "anton");
     taskService.complete(taskSummaryList.get(0).getId(), "anton", null); // not passing any data = null
  }
}

For a list of Maven dependencies, see example Client Dependencies of the Red Hat JBoss BPM Suite Development Guide.

As you can see, this example is much more simple and readable than the one for Red Hat JBoss BRMS 5. The RemoteRuntimeEngine gives us direct access to the TaskService/KieSession and AuditLogService API.

However, it is still possible to use your arbitrary Java web client and achieve the same scenario by sending GET/POST requests to the appropriate endpoints.

Note

While the basic functionality is provided by both APIs—​JBoss BRMS 5 and JBoss BRMS/Red Hat JBoss BPM Suite 6, (starting the process, completing the tasks and so on) not all endpoints from BRMS 5 have their replacement in JBoss BRMS/Red Hat JBoss BPM Suite 6.

If in doubt, consult the corresponding documentation of the REST API.

2.3.2. KnowledgeAgent to KieScanner Migration

KnowledgeAgent is a component of Red Hat JBoss BRMS 5 which allows you to obtain Knowledge Bases dynamically as it gets updated. If you correctly configure an instance of KnowledgeAgent and then you try to obtain the KnowledgeBase from the agent, you will be able to receive the latest version of the KnowledgeBase including updated resources - whether it is a freshly built package (*.PKG) in Business Central or BPMN process definition updated via the Eclipse designer tool.

See a working example of how this works in version 5 here: KnowlegeAgent Example.

In Red Hat JBoss BRMS and Red Hat JBoss BPM Suite 6, it is also possible to obtain KieBase (instead of KnowledgeBase) dynamically as it gets updated. However, the migration is not so straightforward, because of a few things:

  • In Red Hat JBoss BRMS 5, the native storage for packages was Guvnor—​which used JackRabbit repository underneath. You could also point to a single resource (drl, bpmn..) with any valid URL (i.e. file://, http://, …​).
  • The API is completely different as there is no direct mapping between KnowledgeAgent API in Red Hat JBoss BRMS/Red Hat JBoss BPM Suite 6.

The component which replaces the KnowledgeAgent in BRMS 6 is called KieScanner, and therefore you need to include kie-ci library on classpath if you want to use it.

See an example of how this works in version 6 here: KieScanner Example.

In version 6, you no longer refer to *.PKG files or specific business resources such as drl, bpmn. Instead you configure your KieScanner with a specific KJAR, which is a Maven artifact including your resources, identified by GAV (Group, Artifact, Version). KieScanner uses the Maven Repository to figure out where to look for these built KJARs. If not specified otherwise, it will look into your local Maven repository (by default stored under ~/.m2/ directory on your filesystem).

A typical scenario will be where you set GAV so it identifies the project created in Business Central. KieScanner is now bound to this project, and once you make changes to this project in Business Central and build the project, its latest build will be stored into the local Maven repository (this is the default). KieScanner scans the local Maven repository and picks up the changes. If you want to configure KieScanner in a way that it scans other repositories besides your local one you can do so by setting a system property: kie.maven.settings.custom which can point to the custom settings.xml (a standard Maven configuration file where you include all repositories which should be taken into consideration).

KieScanner invokes Maven under the hood for artifact lookup by following known Maven conventions and rules. For example:

  • If the remote repository requires authentication, you need to configure this authentication in a Maven way by updating settings.xml .
  • If you point your KieScanner to a KJar with GAV org.my:project:1.0, your KieBase will never get updated even if you build the project with the same GAV again. This is because Maven will resolve the artifact to a fixed version.
  • If you point your KieScanner to a KJar with GAV org.my:project:1.0-SNAPSHOT, your KieBase will get updated for any new build of the project with that GAV—​it will be resolved to the LATEST build of that GAV, identified by the timestamp.

A KCS article which discuss various scenarios and configurations is available at https://access.redhat.com/solutions/710763.

2.3.3. Database Migration

The default underlying database in Red Hat JBoss BPM Suite is an instance of H2. This is fine for most test systems, but production systems are generally based around MySQL, PostgreSQL, Oracle, or others databases. This section lists some of the tips and tricks related to databases when migrating from BRMS 5 to Red Hat JBoss BPM Suite 6.x.

Include hbm.xml for PostgreSQL

If the underlying database on which the migration is being performed is PostgreSQL, you will need to include an additional configuration file, called hbm.xml inside the META-INF directory, next to persistence.xml, with the following contents:

<?xml version="1.0"?>
<!DOCTYPE hibernate-mapping PUBLIC
    "-//Hibernate/Hibernate Mapping DTD 3.0//EN"
    "http://hibernate.sourceforge.net/hibernate-mapping-3.0.dtd">
<hibernate-mapping>
  <typedef name="materialized_clob" class="org.hibernate.type.TextType" />
</hibernate-mapping>

This file instructs Hibernate to use TextType for materialized CLOBS and solves an issue where Hibernate incorrectly tries to interpret the type of a parameter as Long when it should be String based.

Avoid ID constraint violations in PostgresSQL and Oracle

NodeInstanceLog in BRMS 5.2.x does not have a sequence generator associated with it and was added to have more consistent behavior with multiple databases. Since not all databases initialize the id sequence correctly on migration it is necessary to update the NODE_INST_LOG_ID_SEQ id manually. The two databases that are affected are: PostgreSQL and Oracle.

  • PostgreSQL: In PostgreSQL two actions are required:

    • Find the id with the biggest value in the NodeInstanceLog table:

      SELECT MAX(id) FROM nodeinstancelog;
    • Restart sequence NODE_INST_LOG_ID_SEQ using the result from the previous step, increased by 1. For example, if the command in the previous step returned the number 10, you will use 11 in the following command.

      ALTER SEQUENCE node_inst_log_id_seq RESTART WITH 11;

      The reason to increase the result from the first step by 1 is that restarting the sequence sets the is_called flag to false, which tells the system that the sequence was not yet used.

  • Oracle: In Oracle, the following steps are required:

    • Find the id with the biggest value in the NodeInstanceLog table:

      SELECT MAX(id) FROM nodeinstancelog;
    • Execute the following commands in SQL:

      -- Re-create the sequence by first dropping it and then creating a new one.
      DROP SEQUENCE NODE_INST_LOG_ID_SEQ;
      CREATE SEQUENCE NODE_INST_LOG_ID_SEQ START WITH 11 INCREMENT BY 1 NOCYCLE;
      
      -- Increase the sequence (the result must be greater then the result obtained in step 1)
      ALTER SEQUENCE NODE_INST_LOG_ID_SEQ INCREMENT BY 100;