One of my recent jobs was to design a bpmn-process with Camunda for one of my clients.
The requirements were clear and not too complicated. I had to struggle with some technical challenges regarding Camunda though. One of these challenges was that a task within the process can take some time. Standard synchronous Camunda tasks are not designed to do long lasting work by design.
At my client the Camunda engine runs within a Wildfly application server and therefore uses the transaction handling of Wildfly. The default transaction timeout for a Wildfly managed database transaction is 10 minutes. This means that your task's transaction will also timeout after 10 minutes which might not be enough in particular cases. Of course you could increase the transaction timeout, but this will affect all applications deployed within wildfly. And what if your transaction has to run for several days or weeks? Consulting the Camunda forum (Camunda has a great community) and the documentation I found a solution in using "external tasks".
External tasks enable you to provide a work load to an external worker. This way the task's transaction can finish right away and let some other service deal with the complexity of the long running job. This service can use its own transaction handling completely independent of the Camunda process.
The following steps are necessary to implement an external task:
- Activate the Camunda REST-API (it is probably also possible to use external tasks with the Camunda Java API but I have found only examples with the REST-API). The REST-API is activated by extending the Application class and overriding the getClasses method: (only applicable for a Java EE application)
- Define your service task in your bpmn-file by setting the caunda:type attribute to external und providing a topic name. You can choose any topic name you want:
- Create and an external task client and subscripe to the topic:
- The external task handler is the place where the actual business logic is defined that will be executed when a task is written to the topic. This handler is not bound to any transactions and can define on its own how the work should be executed. The handler implements the ExternalTaskHandler interface.