> ## Documentation Index
> Fetch the complete documentation index at: https://aletyx.ai/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# KIE Server Java client API for KIE containers and business assets

> Connect to KIE Server using REST protocol from your Java client application to interact with KIE containers and business assets as an alternative to the KIE Server REST API.

jBPM provides a KIE Server Java client API that enables you to connect to KIE Server using REST protocol from your Java client application. You can use the KIE Server Java client API as an alternative to the KIE Server REST API to interact with your KIE containers and business assets (such as business rules, processes, and solvers) in jBPM without using the Business Central user interface. This API support enables you to maintain your jBPM resources more efficiently and optimize your integration and development with jBPM.

With the KIE Server Java client API, you can perform the following actions also supported by the KIE Server REST API:

* Deploy or dispose KIE containers
* Retrieve and update KIE container information
* Return KIE Server status and basic information
* Retrieve and update business asset information
* Execute business assets (such as rules and processes)

KIE Server Java client API requests require the following components:

**Authentication**

The KIE Server Java client API requires HTTP Basic authentication for the user role `kie-server`. To view configured user roles for your jBPM distribution, navigate to `~/$SERVER_HOME/standalone/configuration/application-roles.properties` and `~/application-users.properties`.

To add a user with the `kie-server` role, navigate to `~/$SERVER_HOME/bin` and run the following command:

```bash theme={null}
$ ./bin/jboss-cli.sh --commands="embed-server --std-out=echo,/subsystem=elytron/filesystem-realm=ApplicationRealm:add-identity(identity=<USERNAME>),/subsystem=elytron/filesystem-realm=ApplicationRealm:set-password(identity=<USERNAME>, clear={password='<PASSWORD>'}),/subsystem=elytron/filesystem-realm=ApplicationRealm:add-identity-attribute(identity=<USERNAME>, name=role, value=['kie-server'])"
```

For more information about user roles and jBPM installation options, see
[Installing the KIE Server](/docs/kie-server/installation).

**Project dependencies**

The KIE Server Java client API requires the following dependencies on the relevant classpath of your Java project:

```xml theme={null}
<!-- For remote execution on KIE Server -->
<dependency>
  <groupId>org.kie.server</groupId>
  <artifactId>kie-server-client</artifactId>
  <version>${jbpm.version}</version>
</dependency>

<!-- For runtime commands -->
<dependency>
  <groupId>org.drools</groupId>
  <artifactId>drools-compiler</artifactId>
  <scope>runtime</scope>
  <version>${jbpm.version}</version>
</dependency>

<!-- For debug logging (optional) -->
<dependency>
  <groupId>ch.qos.logback</groupId>
  <artifactId>logback-classic</artifactId>
  <version>${logback.version}</version>
</dependency>
```

The `<version>` for jBPM dependencies is the Maven artifact version for jBPM currently used in your project (for example, 7.67.2.Final). {/* TODO: Review this */}

**Client request configuration**

All Java client requests with the KIE Server Java client API must define at least the following server communication components:

* Credentials of the `kie-server` user
* KIE Server location, such as `http://localhost:8080/kie-server/services/rest/server`
* Marshalling format for API requests and responses (JSON, JAXB, or XSTREAM)
* A `KieServicesConfiguration` object and a `KieServicesClient` object, which serve as the entry point for starting the server communication using the Java client API
* A `KieServicesFactory` object defining REST protocol and user access
* Any other client services used, such as `RuleServicesClient`, `ProcessServicesClient`, or `QueryServicesClient`

The following are examples of basic and advanced client configurations with these components:

```java Basic client configuration example theme={null}
import org.kie.server.api.marshalling.MarshallingFormat;
import org.kie.server.client.KieServicesClient;
import org.kie.server.client.KieServicesConfiguration;
import org.kie.server.client.KieServicesFactory;

public class MyConfigurationObject {

  private static final String URL = "http://localhost:8080/kie-server/services/rest/server";
  private static final String USER = "baAdmin";
  private static final String PASSWORD = "password@1";

  private static final MarshallingFormat FORMAT = MarshallingFormat.JSON;

  private static KieServicesConfiguration conf;
  private static KieServicesClient kieServicesClient;

  public static void initialize() {
    conf = KieServicesFactory.newRestConfiguration(URL, USER, PASSWORD);

    //If you use custom classes, such as Obj.class, add them to the configuration.
    Set<Class<?>> extraClassList = new HashSet<Class<?>>();
    extraClassList.add(Obj.class);
    conf.addExtraClasses(extraClassList);

    conf.setMarshallingFormat(FORMAT);
    kieServicesClient = KieServicesFactory.newKieServicesClient(conf);
  }
}
```

```java Advanced client configuration example with additional client services theme={null}
import org.kie.server.api.marshalling.MarshallingFormat;
import org.kie.server.client.CaseServicesClient;
import org.kie.server.client.DMNServicesClient;
import org.kie.server.client.DocumentServicesClient;
import org.kie.server.client.JobServicesClient;
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.QueryServicesClient;
import org.kie.server.client.RuleServicesClient;
import org.kie.server.client.SolverServicesClient;
import org.kie.server.client.UIServicesClient;
import org.kie.server.client.UserTaskServicesClient;
import org.kie.server.api.model.instance.ProcessInstance;
import org.kie.server.api.model.KieContainerResource;
import org.kie.server.api.model.ReleaseId;

public class MyAdvancedConfigurationObject {

    // REST API base URL, credentials, and marshalling format
    private static final String URL = "http://localhost:8080/kie-server/services/rest/server";
    private static final String USER = "baAdmin";
    private static final String PASSWORD = "password@1";;

    private static final MarshallingFormat FORMAT = MarshallingFormat.JSON;

    private static KieServicesConfiguration conf;

    // KIE client for common operations
    private static KieServicesClient kieServicesClient;

    // Rules client
    private static RuleServicesClient ruleClient;

    // Process automation clients
    private static CaseServicesClient caseClient;
    private static DocumentServicesClient documentClient;
    private static JobServicesClient jobClient;
    private static ProcessServicesClient processClient;
    private static QueryServicesClient queryClient;
    private static UIServicesClient uiClient;
    private static UserTaskServicesClient userTaskClient;

    // DMN client
    private static DMNServicesClient dmnClient;

    // Planning client
    private static SolverServicesClient solverClient;

    public static void main(String[] args) {
        initializeKieServerClient();
        initializeDroolsServiceClients();
        initializeJbpmServiceClients();
        initializeSolverServiceClients();
    }

    public static void initializeKieServerClient() {
        conf = KieServicesFactory.newRestConfiguration(URL, USER, PASSWORD);
        conf.setMarshallingFormat(FORMAT);
        kieServicesClient = KieServicesFactory.newKieServicesClient(conf);
    }

    public static void initializeDroolsServiceClients() {
        ruleClient = kieServicesClient.getServicesClient(RuleServicesClient.class);
        dmnClient = kieServicesClient.getServicesClient(DMNServicesClient.class);
    }

    public static void initializeJbpmServiceClients() {
        caseClient = kieServicesClient.getServicesClient(CaseServicesClient.class);
        documentClient = kieServicesClient.getServicesClient(DocumentServicesClient.class);
        jobClient = kieServicesClient.getServicesClient(JobServicesClient.class);
        processClient = kieServicesClient.getServicesClient(ProcessServicesClient.class);
        queryClient = kieServicesClient.getServicesClient(QueryServicesClient.class);
        uiClient = kieServicesClient.getServicesClient(UIServicesClient.class);
        userTaskClient = kieServicesClient.getServicesClient(UserTaskServicesClient.class);
    }

    public static void initializeSolverServiceClients() {
        solverClient = kieServicesClient.getServicesClient(SolverServicesClient.class);
    }
}
```

## Sending requests with the KIE Server Java client API

The KIE Server Java client API enables you to connect to KIE Server using REST protocol from your Java client application. You can use the KIE Server Java client API as an alternative to the KIE Server REST API to interact with your KIE containers and business assets (such as business rules, processes, and solvers) in jBPM without using the Business Central user interface.

**Prerequisites**

* KIE Server is installed and running.
* You have `kie-server` user role access to KIE Server.
* You have a Java project with jBPM resources.

**Procedure**

1. In your client application, ensure that the following dependencies have been added to the relevant classpath of your Java project:

   ```xml theme={null}
   <!-- For remote execution on KIE Server -->
   <dependency>
     <groupId>org.kie.server</groupId>
     <artifactId>kie-server-client</artifactId>
     <version>${jbpm.version}</version>
   </dependency>

   <!-- For runtime commands -->
   <dependency>
     <groupId>org.drools</groupId>
     <artifactId>drools-compiler</artifactId>
     <scope>runtime</scope>
     <version>${jbpm.version}</version>
   </dependency>

   <!-- For debug logging (optional) -->
   <dependency>
     <groupId>ch.qos.logback</groupId>
     <artifactId>logback-classic</artifactId>
     <version>${logback.version}</version>
   </dependency>
   ```

2. In the `~/kie/server/client` folder of the Java client API in [GitHub](https://github.com/kiegroup/droolsjbpm-integration/tree/master/kie-server-parent/kie-server-remote/kie-server-client/src/main/java/org/kie/server/client), identify the relevant Java client for the request you want to send, such as `KieServicesClient` to access client services for KIE containers and other assets in KIE Server.

3. In your client application, create a `.java` class for the API request. The class must contain the necessary imports, KIE Server location and user credentials, a `KieServicesClient` object, and the client method to execute, such as `createContainer` and `disposeContainer` from the `KieServicesClient` client. Adjust any configuration details according to your use case.

   ```java Creating and disposing a container theme={null}
   import org.kie.server.api.marshalling.MarshallingFormat;
   import org.kie.server.client.KieServicesClient;
   import org.kie.server.client.KieServicesConfiguration;
   import org.kie.server.client.KieServicesFactory;
   import org.kie.server.api.model.KieContainerResource;
   import org.kie.server.api.model.ServiceResponse;

   public class MyConfigurationObject {

     private static final String URL = "http://localhost:8080/kie-server/services/rest/server";
     private static final String USER = "baAdmin";
     private static final String PASSWORD = "password@1";

     private static final MarshallingFormat FORMAT = MarshallingFormat.JSON;

     private static KieServicesConfiguration conf;
     private static KieServicesClient kieServicesClient;

     public static void initialize() {
       conf = KieServicesFactory.newRestConfiguration(URL, USER, PASSWORD);

     public void disposeAndCreateContainer() {
         System.out.println("== Disposing and creating containers ==");

         // Retrieve list of KIE containers
         List<KieContainerResource> kieContainers = kieServicesClient.listContainers().getResult().getContainers();
         if (kieContainers.size() == 0) {
             System.out.println("No containers available...");
             return;
         }

         // Dispose KIE container
         KieContainerResource container = kieContainers.get(0);
         String containerId = container.getContainerId();
         ServiceResponse<Void> responseDispose = kieServicesClient.disposeContainer(containerId);
         if (responseDispose.getType() == ResponseType.FAILURE) {
             System.out.println("Error disposing " + containerId + ". Message: ");
             System.out.println(responseDispose.getMsg());
             return;
         }
         System.out.println("Success Disposing container " + containerId);
         System.out.println("Trying to recreate the container...");

         // Re-create KIE container
         ServiceResponse<KieContainerResource> createResponse = kieServicesClient.createContainer(containerId, container);
         if(createResponse.getType() == ResponseType.FAILURE) {
             System.out.println("Error creating " + containerId + ". Message: ");
             System.out.println(responseDispose.getMsg());
             return;
         }
         System.out.println("Container recreated with success!");
         }
     }
   }
   ```

   You define service responses using the `org.kie.server.api.model.ServiceResponse<T>` object, where `T` represents the type of returned response. The `ServiceResponse` object has the following attributes:

   * `String message`: Returns the response message
   * `ResponseType type`: Returns either `SUCCESS` or `FAILURE`
   * `T result`: Returns the requested object

   In this example, when you dispose a container, the `ServiceResponse` returns a `Void` response. When you create a container, the `ServiceResponse` returns a `KieContainerResource` object.

   <Note>
     A conversation between a client and a specific KIE Server container in a clustered environment is secured by a unique `conversationID`. The `conversationID` is transferred using the `X-KIE-ConversationId` REST header. If you update the container, unset the previous `conversationID`. Use `KieServicesClient.completeConversation()` to unset the `conversationID` for the Java API.
   </Note>

4. Run the configured `.java` class from your project directory to execute the request, and review the KIE Server response.

   If you enabled debug logging, KIE Server responds with a detailed response according to your configured marshalling format, such as JSON.

   Example server response for a new KIE container (log):

   ```text theme={null}
   10:23:35.194 [main] INFO  o.k.s.a.m.MarshallerFactory - Marshaller extensions init
   10:23:35.396 [main] DEBUG o.k.s.client.balancer.LoadBalancer - Load balancer RoundRobinBalancerStrategy{availableEndpoints=[http://localhost:8080/kie-server/services/rest/server]} selected url 'http://localhost:8080/kie-server/services/rest/server'
   10:23:35.398 [main] DEBUG o.k.s.c.i.AbstractKieServicesClientImpl - About to send GET request to 'http://localhost:8080/kie-server/services/rest/server'
   10:23:35.440 [main] DEBUG o.k.s.c.i.AbstractKieServicesClientImpl - About to deserialize content:
    '{
     "type" : "SUCCESS",
     "msg" : "Kie Server info",
     "result" : {
       "kie-server-info" : {
         "id" : "default-kieserver",
         "version" : "7.11.0.Final-redhat-00003",
         "name" : "default-kieserver",
         "location" : "http://localhost:8080/kie-server/services/rest/server",
         "capabilities" : [ "KieServer", "BRM", "BPM", "CaseMgmt", "BPM-UI", "BRP", "DMN", "Swagger" ],
         "messages" : [ {
           "severity" : "INFO",
           "timestamp" : {
     "java.util.Date" : 1540814906533
   },
           "content" : [ "Server KieServerInfo{serverId='default-kieserver', version='7.11.0.Final-redhat-00003', name='default-kieserver', location='http://localhost:8080/kie-server/services/rest/server', capabilities=[KieServer, BRM, BPM, CaseMgmt, BPM-UI, BRP, DMN, Swagger], messages=null}started successfully at Mon Oct 29 08:08:26 EDT 2018" ]
         } ]
       }
     }
   }'
    into type: 'class org.kie.server.api.model.ServiceResponse'
   10:23:35.653 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - KieServicesClient connected to: default-kieserver version 7.11.0.Final-redhat-00003
   10:23:35.653 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Supported capabilities by the server: [KieServer, BRM, BPM, CaseMgmt, BPM-UI, BRP, DMN, Swagger]
   10:23:35.653 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability KieServer
   10:23:35.653 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - No builder found for 'KieServer' capability
   10:23:35.654 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability BRM
   10:23:35.654 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Builder 'org.kie.server.client.helper.DroolsServicesClientBuilder@6b927fb' for capability 'BRM'
   10:23:35.655 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Capability implemented by {interface org.kie.server.client.RuleServicesClient=org.kie.server.client.impl.RuleServicesClientImpl@4a94ee4}
   10:23:35.655 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability BPM
   10:23:35.656 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Builder 'org.kie.server.client.helper.JBPMServicesClientBuilder@4cc451f2' for capability 'BPM'
   10:23:35.672 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Capability implemented by {interface org.kie.server.client.JobServicesClient=org.kie.server.client.impl.JobServicesClientImpl@1189dd52, interface org.kie.server.client.admin.ProcessAdminServicesClient=org.kie.server.client.admin.impl.ProcessAdminServicesClientImpl@36bc55de, interface org.kie.server.client.DocumentServicesClient=org.kie.server.client.impl.DocumentServicesClientImpl@564fabc8, interface org.kie.server.client.admin.UserTaskAdminServicesClient=org.kie.server.client.admin.impl.UserTaskAdminServicesClientImpl@16d04d3d, interface org.kie.server.client.QueryServicesClient=org.kie.server.client.impl.QueryServicesClientImpl@49ec71f8, interface org.kie.server.client.ProcessServicesClient=org.kie.server.client.impl.ProcessServicesClientImpl@1d2adfbe, interface org.kie.server.client.UserTaskServicesClient=org.kie.server.client.impl.UserTaskServicesClientImpl@36902638}
   10:23:35.672 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability CaseMgmt
   10:23:35.672 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Builder 'org.kie.server.client.helper.CaseServicesClientBuilder@223d2c72' for capability 'CaseMgmt'
   10:23:35.676 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Capability implemented by {interface org.kie.server.client.admin.CaseAdminServicesClient=org.kie.server.client.admin.impl.CaseAdminServicesClientImpl@2b662a77, interface org.kie.server.client.CaseServicesClient=org.kie.server.client.impl.CaseServicesClientImpl@7f0eb4b4}
   10:23:35.676 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability BPM-UI
   10:23:35.676 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Builder 'org.kie.server.client.helper.JBPMUIServicesClientBuilder@5c33f1a9' for capability 'BPM-UI'
   10:23:35.677 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Capability implemented by {interface org.kie.server.client.UIServicesClient=org.kie.server.client.impl.UIServicesClientImpl@223191a6}
   10:23:35.678 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability BRP
   10:23:35.679 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Capability implemented by {interface org.kie.server.client.SolverServicesClient=org.kie.server.client.impl.SolverServicesClientImpl@77fbd92c}
   10:23:35.679 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability DMN
   10:23:35.679 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Builder 'org.kie.server.client.helper.DMNServicesClientBuilder@67c27493' for capability 'DMN'
   10:23:35.680 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Capability implemented by {interface org.kie.server.client.DMNServicesClient=org.kie.server.client.impl.DMNServicesClientImpl@35e2d654}
   10:23:35.680 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - Building services client for server capability Swagger
   10:23:35.680 [main] DEBUG o.k.s.c.impl.KieServicesClientImpl - No builder found for 'Swagger' capability
   10:23:35.681 [main] DEBUG o.k.s.client.balancer.LoadBalancer - Load balancer RoundRobinBalancerStrategy{availableEndpoints=[http://localhost:8080/kie-server/services/rest/server]} selected url 'http://localhost:8080/kie-server/services/rest/server'
   10:23:35.701 [main] DEBUG o.k.s.c.i.AbstractKieServicesClientImpl - About to send PUT request to 'http://localhost:8080/kie-server/services/rest/server/containers/employee-rostering3' with payload '{
     "container-id" : null,
     "release-id" : {
       "group-id" : "employeerostering",
       "artifact-id" : "employeerostering",
       "version" : "1.0.0-SNAPSHOT"
     },
     "resolved-release-id" : null,
     "status" : null,
     "scanner" : null,
     "config-items" : [ ],
     "messages" : [ ],
     "container-alias" : null
   }'
   10:23:38.071 [main] DEBUG o.k.s.c.i.AbstractKieServicesClientImpl - About to deserialize content:
    '{
     "type" : "SUCCESS",
     "msg" : "Container employee-rostering3 successfully deployed with module employeerostering:employeerostering:1.0.0-SNAPSHOT.",
     "result" : {
       "kie-container" : {
         "container-id" : "employee-rostering3",
         "release-id" : {
           "group-id" : "employeerostering",
           "artifact-id" : "employeerostering",
           "version" : "1.0.0-SNAPSHOT"
         },
         "resolved-release-id" : {
           "group-id" : "employeerostering",
           "artifact-id" : "employeerostering",
           "version" : "1.0.0-SNAPSHOT"
         },
         "status" : "STARTED",
         "scanner" : {
           "status" : "DISPOSED",
           "poll-interval" : null
         },
         "config-items" : [ ],
         "messages" : [ {
           "severity" : "INFO",
           "timestamp" : {
     "java.util.Date" : 1540909418069
   },
           "content" : [ "Container employee-rostering3 successfully created with module employeerostering:employeerostering:1.0.0-SNAPSHOT." ]
         } ],
         "container-alias" : null
       }
     }
   }'
    into type: 'class org.kie.server.api.model.ServiceResponse'
   ```

   If you encounter request errors, review the returned error code messages and adjust your Java configurations accordingly.

## Supported KIE Server Java clients

The following are some of the Java client services available in the `org.kie.server.client` package of your jBPM distribution. You can use these services to interact with related resources in KIE Server similarly to the KIE Server REST API.

* `KieServicesClient`: Used as the entry point for other KIE Server Java clients, and used to interact with KIE containers
* `JobServicesClient`: Used to schedule, cancel, re-queue, and get job requests
* `RuleServicesClient`: Used to send commands to the server to perform rule-related operations, such as executing rules or inserting objects into the KIE session
* `ProcessServicesClient`: Used to start, signal, and abort processes or work items
* `QueryServicesClient`: Used to query processes, process nodes, and process variables
* `UserTaskServicesClient`: Used to perform all user-task operations, such as starting, claiming, or canceling a task, and to query tasks by a specified field, such as by user or by process instance ID
* `UIServicesClient`: Used to get a String representation of forms (XML or JSON) and of a process image (SVG)
* `ProcessAdminServicesClient`: Provides an interface for operations with process instances (found in `~/org/kie/server/client/admin`)
* `UserTaskAdminServicesClient`: Provides an interface for operations with user tasks (found in `~/org/kie/server/client/admin`)

The `getServicesClient` method provides access to any of these clients:

```java theme={null}
RuleServicesClient rulesClient = kieServicesClient.getServicesClient(RuleServicesClient.class);
```

For the full list of available KIE Server Java clients,
see the Java client API source in [GitHub](https://github.com/kiegroup/droolsjbpm-integration/tree/master/kie-server-parent/kie-server-remote/kie-server-client/src/main/java/org/kie/server/client).

## Example requests with the KIE Server Java client API

The following are examples of KIE Server Java client API requests for basic interactions with KIE Server. For the full list of available KIE Server Java clients,
see the Java client API source in [GitHub](https://github.com/kiegroup/droolsjbpm-integration/tree/master/kie-server-parent/kie-server-remote/kie-server-client/src/main/java/org/kie/server/client).

**Listing KIE Server capabilities**

You can use the `org.kie.server.api.model.KieServerInfo` object to identify server capabilities. The `KieServicesClient` client requires the server capability information to correctly produce service clients. You can specify the capabilities globally in `KieServicesConfiguration`; otherwise they are automatically retrieved from KIE Server.

```java Example request to return KIE Server capabilities theme={null}
public void listCapabilities() {

  KieServerInfo serverInfo = kieServicesClient.getServerInfo().getResult();
  System.out.print("Server capabilities:");

  for (String capability : serverInfo.getCapabilities()) {
    System.out.print(" " + capability);
  }

  System.out.println();
}
```

**Listing KIE containers in KIE Server**

KIE containers are represented by the `org.kie.server.api.model.KieContainerResource` object. The list of resources is represented by the `org.kie.server.api.model.KieContainerResourceList` object.

```java Example request to return KIE containers from KIE Server theme={null}
public void listContainers() {
    KieContainerResourceList containersList = kieServicesClient.listContainers().getResult();
    List<KieContainerResource> kieContainers = containersList.getContainers();
    System.out.println("Available containers: ");
    for (KieContainerResource container : kieContainers) {
        System.out.println("\t" + container.getContainerId() + " (" + container.getReleaseId() + ")");
    }
}
```

You can optionally filter the KIE container results using an instance of the `org.kie.server.api.model.KieContainerResourceFilter` class, which is passed to the `org.kie.server.client.KieServicesClient.listContainers()` method.

```java Example request to return KIE containers by release ID and status theme={null}
public void listContainersWithFilter() {

    // Filter containers by releaseId "org.example:container:1.0.0.Final" and status FAILED
    KieContainerResourceFilter filter = new KieContainerResourceFilter.Builder()
            .releaseId("org.example", "container", "1.0.0.Final")
            .status(KieContainerStatus.FAILED)
            .build();

    // Using previously created KieServicesClient
    KieContainerResourceList containersList = kieServicesClient.listContainers(filter).getResult();
    List<KieContainerResource> kieContainers = containersList.getContainers();

    System.out.println("Available containers: ");

    for (KieContainerResource container : kieContainers) {
        System.out.println("\t" + container.getContainerId() + " (" + container.getReleaseId() + ")");
    }
}
```

**Creating and disposing KIE containers in KIE Server**

You can use the `createContainer` and `disposeContainer` methods in the `KieServicesClient` client to dispose and create KIE containers. In this example, when you dispose a container, the `ServiceResponse` returns a `Void` response. When you create a container, the `ServiceResponse` returns a `KieContainerResource` object.

```java Example request to dispose and re-create a KIE container theme={null}
public void disposeAndCreateContainer() {
    System.out.println("== Disposing and creating containers ==");

    // Retrieve list of KIE containers
    List<KieContainerResource> kieContainers = kieServicesClient.listContainers().getResult().getContainers();
    if (kieContainers.size() == 0) {
        System.out.println("No containers available...");
        return;
    }

    // Dispose KIE container
    KieContainerResource container = kieContainers.get(0);
    String containerId = container.getContainerId();
    ServiceResponse<Void> responseDispose = kieServicesClient.disposeContainer(containerId);
    if (responseDispose.getType() == ResponseType.FAILURE) {
        System.out.println("Error disposing " + containerId + ". Message: ");
        System.out.println(responseDispose.getMsg());
        return;
    }
    System.out.println("Success Disposing container " + containerId);
    System.out.println("Trying to recreate the container...");

    // Re-create KIE container
    ServiceResponse<KieContainerResource> createResponse = kieServicesClient.createContainer(containerId, container);
    if(createResponse.getType() == ResponseType.FAILURE) {
        System.out.println("Error creating " + containerId + ". Message: ");
        System.out.println(responseDispose.getMsg());
        return;
    }
    System.out.println("Container recreated with success!");
}
```

**Executing runtime commands in KIE Server**

jBPM supports runtime commands that you can send to KIE Server for asset-related operations, such as inserting or retracting objects in a KIE session or firing all rules. The full list of supported runtime commands is located in the `org.drools.core.command.runtime` package in your jBPM instance.

You can use the `org.kie.api.command.KieCommands` class to insert commands, and use `org.kie.api.KieServices.get().getCommands()` to instantiate the `KieCommands` class. If you want to add multiple commands, use the `BatchExecutionCommand` wrapper.

```java Example request to insert an object and fire all rules theme={null}
import org.kie.api.command.Command;
import org.kie.api.command.KieCommands;
import org.kie.server.api.model.ServiceResponse;
import org.kie.server.client.RuleServicesClient;
import org.kie.server.client.KieServicesClient;
import org.kie.api.KieServices;

import java.util.Arrays;

...

public void executeCommands() {

  String containerId = "hello";
  System.out.println("== Sending commands to the server ==");
  RuleServicesClient rulesClient = kieServicesClient.getServicesClient(RuleServicesClient.class);
  KieCommands commandsFactory = KieServices.Factory.get().getCommands();

  Command<?> insert = commandsFactory.newInsert("Some String OBJ");
  Command<?> fireAllRules = commandsFactory.newFireAllRules();
  Command<?> batchCommand = commandsFactory.newBatchExecution(Arrays.asList(insert, fireAllRules));

  ServiceResponse<String> executeResponse = rulesClient.executeCommands(containerId, batchCommand);

  if(executeResponse.getType() == ResponseType.SUCCESS) {
    System.out.println("Commands executed with success! Response: ");
    System.out.println(executeResponse.getResult());
  } else {
    System.out.println("Error executing rules. Message: ");
    System.out.println(executeResponse.getMsg());
  }
}
```

<Note>
  A conversation between a client and a specific KIE Server container in a clustered environment is secured by a unique `conversationID`. The `conversationID` is transferred using the `X-KIE-ConversationId` REST header. If you update the container, unset the previous `conversationID`. Use `KieServicesClient.completeConversation()` to unset the `conversationID` for the Java API.
</Note>

**Listing available business processes in a KIE container**

You can use the `QueryServicesClient` client to list available process definitions. The `QueryServicesClient` methods use pagination, so in addition to the query you make, you must provide the current page and the number of results per page. In this example, the query starts on page `0` and lists the first `1000` results.

```java Example request to list business processes in KIE Server theme={null}
public void listProcesses() {
    System.out.println("== Listing Business Processes ==");
    QueryServicesClient queryClient = kieServicesClient.getServicesClient(QueryServicesClient.class);
    List<ProcessDefinition> findProcessesByContainerId = queryClient.findProcessesByContainerId("rewards", 0, 1000);
    for (ProcessDefinition def : findProcessesByContainerId) {
        System.out.println(def.getName() + " - " + def.getId() + " v" + def.getVersion());
    }
}
```

**Starting a business process in a KIE container**

You can use the `ProcessServicesClient` client to start a business process. Ensure that any custom classes that you require for your process are added into the `KieServicesConfiguration` object, using the `addExtraClasses()` method.

```java Example request to start a business process theme={null}
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;

import javax.xml.bind.JAXBContext;
import javax.xml.bind.JAXBException;
import javax.xml.bind.Marshaller;

import org.kie.server.api.marshalling.MarshallingFormat;
import org.kie.server.client.KieServicesClient;
import org.kie.server.client.KieServicesConfiguration;
import org.kie.server.client.KieServicesFactory;
import org.kie.server.client.ProcessServicesClient;
...

public static void startProcess() {

  //Client configuration setup
  KieServicesConfiguration config = KieServicesFactory.newRestConfiguration(SERVER_URL, LOGIN, PASSWORD);

  //Add custom classes, such as Obj.class, to the configuration
  Set<Class<?>> extraClassList = new HashSet<Class<?>>();
  extraClassList.add(Obj.class);
  config.addExtraClasses(extraClassList);
  config.setMarshallingFormat(MarshallingFormat.JSON);

  // ProcessServicesClient setup
  KieServicesClient client = KieServicesFactory.newKieServicesClient(config);
  ProcessServicesClient processServicesClient = client.getServicesClient(ProcessServicesClient.class);

  // Create an instance of the custom class
  Obj obj = new Obj();
  obj.setOk("ok");

  Map<String, Object> variables = new HashMap<String, Object>();
  variables.put("test", obj);

  // Start the process with custom class
  processServicesClient.startProcess(CONTAINER, processId, variables);
}
```

**Running a custom query**

You can use the `QueryDefinition` object of the `QueryServicesClient` client to register and execute custom queries in KIE Server.

```java Example request to register and execute a custom query in KIE Server theme={null}
// Client setup
KieServicesConfiguration conf = KieServicesFactory.newRestConfiguration(SERVER_URL, LOGIN, PASSWORD);
KieServicesClient client = KieServicesFactory.newKieServicesClient(conf);

// Get the QueryServicesClient
QueryServicesClient queryClient = client.getServicesClient(QueryServicesClient.class);

// Build the query
QueryDefinition queryDefinition = QueryDefinition.builder().name(QUERY_NAME)
        .expression("select * from Task t")
        .source("java:jboss/datasources/ExampleDS")
        .target("TASK").build();

// Specify that two queries cannot have the same name
queryClient.unregisterQuery(QUERY_NAME);

// Register the query
queryClient.registerQuery(queryDefinition);

// Execute the query with parameters: query name, mapping type (to map the fields to an object), page number, page size, and return type
List<TaskInstance> query = queryClient.query(QUERY_NAME, QueryServicesClient.QUERY_MAP_TASK, 0, 100, TaskInstance.class);

// Read the result
for (TaskInstance taskInstance : query) {
    System.out.println(taskInstance);
}
```

In this example, the `target` instructs the query service to apply default filters. Alternatively, you can set filter parameters manually. The `Target` class supports the following values:

```java theme={null}
public enum Target {
    PROCESS,
    TASK,
    BA_TASK,
    PO_TASK,
    JOBS,
    CUSTOM;
}
```
