Message Flow for Beginner

1,719 views
Skip to first unread message

jens_l...@freenet.de

unread,
Mar 19, 2015, 10:05:05 AM3/19/15
to camunda-...@googlegroups.com
Hi everyone,

i'm quite new to camunda and bpmn and try to figure out how I can communicate between two process pools.

I looked up some examples, but they didn't work for me.
It's easy to start another process and works fine, but how can I correlate a message to and Intermediate Catch Event?

I tried something like

runtimeService.correlateMessage("NotifyMasterContinueMessage");

and got this exception:
org.camunda.bpm.engine.MismatchingMessageCorrelationException: Cannot correlate message NotifyMasterContinueMessage: No process definition or execution matches the parameters


Do I need to add a String (process)bussinessKey to the correlateMessage parameters?
If so, how can I set this key?
Everytime I tried to read this value with something like:

String processBusinessKey = execution.getProcessBusinessKey().toString();

failed and tiggered a NullPointerException.



Can somebody explain me that?

Sincerely
Jens

thorben....@camunda.com

unread,
Mar 19, 2015, 10:23:20 AM3/19/15
to camunda-...@googlegroups.com, jens_l...@freenet.de
Hi Jens,

It appears that either the message name is not correct or that the receiving process instance has not yet reached the catching message event. Could you please post the XML of your process models (either as an attachment or via http://www.camunda.org/share/)?

The business key is not required for correlation. It can be used to distinguished between multiple process instances that all wait for a message with the same name. In that case, you can add a business key as a correlation criterion. The business key can be set on process instantiation, see for example the method RuntimeService#startProcessInstanceByKey(String definitionKey, String businessKey). But again, the business key is not the problem here.

Cheers,
Thorben

jens_l...@freenet.de

unread,
Mar 19, 2015, 10:29:57 AM3/19/15
to camunda-...@googlegroups.com, jens_l...@freenet.de
Hi Thorben,

here the shared bpmn: http://www.camunda.org/share/#/process/465119e0-9111-4759-9968-78502e5a7171

I'm going to try RuntimeService#startProcessInstanceByKey(String definitionKey, String businessKey) could be very useful!

Thank you for reading this!


Cheers
Jens

thorben....@camunda.com

unread,
Mar 19, 2015, 10:48:25 AM3/19/15
to camunda-...@googlegroups.com, jens_l...@freenet.de
Hi Jens,

Thanks for posting your process.

The reason why the message cannot be delivered lies in the execution and threading model of the process engine. Here is what happens:

The master process has a timer start event. That means, a job exists that is executed in a regular time interval. "Executing a job" means a single thread is assigned with the task to instantiate the process and execute the process instance until it ends or wait states are reached.

In detail, this means the following steps are executed sequentially within a single thread:
1. A master process instance is created
2. The service task "Send Start Message" begins. The API call it makes is synchronous.
3. A slave process instance is created
4. The service task "Send Notification" is executed

The problem is that at this point, the master process instance has not yet reached the catching message event, because it is still executing the service task "Send Start Message" (as the API call is synchronous). Thus, you see the exception you posted.

In order to avoid this, you can add asynchronous continuations to your process. One possibility would be to make the start event of the slave process asynchronous (property camunda:asyncAfter as an XML attribute of the startEvent element). This would result in the following execution order when the timer job fires:

1. A master process instance is created
2. The service task "Send Start Message" is executed. The API call it makes is again synchronous.
3. A slave process instance is created.
4. Because the "Start Slave Process" is asynchronous, the process engine does not attempt to execute "Send Notification" immediately, but persists a job in the database to continue execution after the start event. The slave process instance has reached a wait state now.
5. The API call from step 2 returns and the service task "Send Start Message" completes.
6. The master process instance reaches the message catch event. A message catch event is as well a wait state because the process instance has to wait for a message. The current process execution state is persisted to the database.

<some time later>

7. The Job executor executes the asynchronous job created in step 4. Now, the master process instance has already reached the catching message event and is able to receive the message properly.

I hope that makes sense. Feel free to ask for clarifications. Some background reading on wait states in processes, transaction boundaries, and how you can control them is provided under [1].

Cheers,
Thorben

[1] http://docs.camunda.org/latest/guides/user-guide/#process-engine-transactions-in-processes

jens_l...@freenet.de

unread,
Mar 19, 2015, 11:08:11 AM3/19/15
to camunda-...@googlegroups.com, jens_l...@freenet.de
Hi Thoben,

You. Are. Just. Awesome!
Thank you very much!

Works absolutely fine! Problem solved.

I already read about asynchron and synchron process calls so your explaination makes of course sense. Thanks for this summary. :)


Have a nice day
Jens
Reply all
Reply to author
Forward
0 new messages