π Camunda 8: A Complete Guide to Local Deployment with Docker + Spring Boot Application with Zeebe
Camunda 8 is an industry-leading platform for workflow and decision automation. Deploying it locally allows developers to test, iterate, and develop workflow applications before pushing them into production. This tutorial will guide you step-by-step on how to install and deploy Camunda 8 using Docker Compose on your local machine.
π οΈ Prerequisites
Before getting started, make sure you have the following installed on your system:
- Docker Desktop : Install Docker Compose
Make sure that Docker and Docker Compose are up and running on your system. We will use Docker Compose to orchestrate the different Camunda components in a single environment.
π§βπ» Step 1: Set Up Environment Variables
Start by defining the environment variables for the different versions of Camunda and supporting components. These versions will ensure compatibility among all containers.
# Camunda 8 versions
CAMUNDA_CONNECTORS_VERSION=8.5.7
CAMUNDA_PLATFORM_VERSION=8.5.7
CAMUNDA_IDENTITY_VERSION=8.5.5
CAMUNDA_OPERATE_VERSION=8.5.6
CAMUNDA_TASKLIST_VERSION=8.5.7
CAMUNDA_OPTIMIZE_VERSION=8.5.5
CAMUNDA_WEB_MODELER_VERSION=8.5.8
# Supporting tools
ELASTIC_VERSION=8.15.1
OPENSEARCH_VERSION=2.16.0
MAILPIT_VERSION=v1.20.4
POSTGRES_VERSION=14.5-alpine
KEYCLOAK_SERVER_VERSION=24.0.5
These version numbers ensure that the correct versions of Camunda components, Elasticsearch, and OpenSearch are pulled into your Docker environment.
ποΈ Step 2: Create Docker Compose File
Next, youβll need a docker-compose.yml
file that defines all the services Camunda 8 relies on, including Zeebe, Operate, Tasklist, OpenSearch/Elasticsearch, and Connectors.
Create a file named docker-compose.yml
in your working directory, and paste the following configuration into it:
yamlCopy codeversion: '3.7'
services:
zeebe:
image: camunda/zeebe:${CAMUNDA_PLATFORM_VERSION}
container_name: zeebe
ports:
- "26500:26500"
- "9600:9600"
environment:
- ZEEBE_BROKER_DATA_DISKUSAGECOMMANDWATERMARK=0.998
- ZEEBE_BROKER_DATA_DISKUSAGEREPLICATIONWATERMARK=0.999
- JAVA_TOOL_OPTIONS=-Xms512m -Xmx512m
volumes:
- zeebe:/usr/local/zeebe/data
networks:
- camunda-platform
restart: unless-stopped
healthcheck:
test: ["CMD-SHELL", "timeout 10s bash -c ':> /dev/tcp/127.0.0.1/9600' || exit 1"]
operate:
image: camunda/operate:${CAMUNDA_OPERATE_VERSION}
container_name: operate
ports:
- "8081:8080"
environment:
- CAMUNDA_OPERATE_ZEEBE_GATEWAYADDRESS=zeebe:26500
- CAMUNDA_OPERATE_CSRFPREVENTIONENABLED=false
networks:
- camunda-platform
depends_on:
- zeebe
tasklist:
image: camunda/tasklist:${CAMUNDA_TASKLIST_VERSION}
container_name: tasklist
ports:
- "8082:8080"
environment:
- CAMUNDA_TASKLIST_ZEEBE_GATEWAYADDRESS=zeebe:26500
- CAMUNDA_TASKLIST_CSRFPREVENTIONENABLED=false
networks:
- camunda-platform
depends_on:
- zeebe
connectors:
image: camunda/connectors-bundle:${CAMUNDA_CONNECTORS_VERSION}
container_name: connectors
ports:
- "8085:8080"
environment:
- ZEEBE_CLIENT_BROKER_GATEWAY_ADDRESS=zeebe:26500
- CAMUNDA_OPERATE_CLIENT_URL=http://operate:8080
networks:
- camunda-platform
depends_on:
- zeebe
- operate
opensearch:
image: opensearchproject/opensearch:${OPENSEARCH_VERSION}
container_name: opensearch
environment:
- cluster.name=opensearch-cluster
- network.bind_host=0.0.0.0
- discovery.type=single-node
ulimits:
memlock:
soft: -1
hard: -1
ports:
- "9200:9200"
- "9601:9600"
volumes:
- opensearch-data:/usr/share/opensearch/data
networks:
- camunda-platform
elasticsearch:
image: docker.elastic.co/elasticsearch/elasticsearch:${ELASTIC_VERSION}
container_name: elasticsearch
ports:
- "9200:9200"
- "9300:9300"
environment:
- discovery.type=single-node
- cluster.routing.allocation.disk.threshold_enabled=false
networks:
- camunda-platform
volumes:
zeebe:
opensearch-data:
networks:
camunda-platform:
This configuration sets up Zeebe, Operate, Tasklist, Connectors, and the search engines (OpenSearch and Elasticsearch).
Step 3: Run the Docker Containers
Now that youβve created the docker-compose.yml
file, you can start your Camunda 8 environment. Run the following command in the terminal:
docker-compose up -d
Docker will pull the required images, create the containers, and start them. You can verify everything is running using:
code docker ps
You should see the containers for Zeebe, Operate, Tasklist, Connectors, and OpenSearch or Elasticsearch.
Step 4: Access the Camunda Services
Once all containers are running, you can access the various Camunda services via your web browser:
Operate: localhost:8081
Tasklist: localhost:8082
Connectors: localhost:8085
OpenSearch: http://localhost:9200
Each component has its own dashboard that allows you to manage workflows, monitor tasks, and configure connectors.
π― Why Use Tasklist, Zeebe, and Operate?
Before diving into the example application, let's break down the purpose of key components in Camunda 8: Tasklist, Zeebe, and Operate.
β 1. Tasklist
The Tasklist is a user interface designed for managing human tasks within business processes. Whenever a process model includes user tasks, they are listed in Tasklist, allowing assigned users to claim, complete, or reassign tasks.
Why is Tasklist important?
Tasklist bridges the gap between automated workflow execution and human interaction, ensuring that tasks requiring user input are not missed and are handled in a structured manner.Use Case:
When you have business processes where human approval or interaction is necessary, Tasklist will manage these interactions efficiently.
π Zeebe
Zeebe is the core workflow engine in Camunda 8, responsible for executing BPMN workflows. It handles process orchestration, managing workflow execution through tasks, services, and message events.
Why is Zeebe important?
Zeebe is lightweight and highly scalable, allowing you to automate and execute complex workflows with minimal overhead. It can orchestrate services, microservices, and human tasks.Use Case:
Zeebe is ideal for automating end-to-end workflows that span different services or require integration with multiple systems.
𧩠Operate
Operate is a monitoring tool used to visualize, monitor, and troubleshoot running process instances in real time.
Why is Operate important?
Operate provides visibility into the execution of workflows. It allows you to track the progress of individual process instances, find bottlenecks, and debug errors efficiently.Use Case:
When you need to monitor and analyze running instances of your workflows, Operate gives you real-time insights, which is critical for keeping workflows optimized and ensuring they run as expected.
π» Example: Camunda Spring Boot Application with Zeebe
Now that we understand the role of Tasklist, Zeebe, and Operate, letβs look at a practical emxample of how Zeebe is used in a Spring Boot application to automate message-based workflows.
package com.camunda.demo;
import java.util.HashMap;
import java.util.Map;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.boot.CommandLineRunner;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import io.camunda.zeebe.client.ZeebeClient;
import io.camunda.zeebe.spring.client.annotation.Deployment;
@SpringBootApplication
@Deployment(resources = "classpath:message-start.bpmn")
public class MessageStartAppApplication implements CommandLineRunner {
public static void main(String[] args) {
SpringApplication.run(MessageStartAppApplication.class, args);
}
@Autowired
private ZeebeClient client;
@Override
public void run(String... args) throws Exception {
final Map<String, Object> variables = new HashMap<String, Object>();
variables.put("name", "HAMZA BRAIMI");
variables.put("age", 23);
String messageId = "message-1";
client.newPublishMessageCommand()
.messageName("Message-Received")
.correlationKey(messageId)
.variables(variables)
.send()
.exceptionally(throwable -> {
throw new RuntimeException("Could not publish message", throwable);
});
}
}
Explanation of the Code
Spring Boot Application: This is a simple Spring Boot application that integrates with the Zeebe workflow engine.
Zeebe Client: The
ZeebeClient
is used to connect to the running Zeebe engine (which, in this case, would be running in Docker atlocalhost:26500
).Publish Message Command: A message with the name
"Message-Received"
is published. This message correlates with a BPMN process that listens for a message event with a matching correlation key (messageId
). The message includes process variables like"name"
and"age"
that are sent along with it.
application.properties
Configuration
To ensure the application can communicate with the Zeebe broker (which is running locally in Docker), you need the following configuration in application.properties
:
propertiesCopy codeserver.port=8099
zeebe.client.broker.gatewayAddress=localhost:26500
zeebe.client.security.plaintext=true
zeebe.client.requestTimeout=15000
π Monitoring Your Process
Deploy the BPMN Model: The process definition (e.g.,
message-start.bpmn
) should be deployed in Zeebe, and this can be done automatically using the@Deployment
annotation, as shown in the example.Monitor in Operate: Once the application starts sending messages to Zeebe, you can monitor the workflow instances and their progress using Operate.
π And that's the final result!
With this setup, you can deploy Camunda 8 locally, integrate Zeebe with Spring Boot, and monitor your processes in real time.
Happy coding! π»
HAMZA BRAIMI