Issues accessing already Created Process Instance

We are having issues with Camunda when trying to use an already created Process Instance , where we are running into some sort of race conditions where we are not able to Query the already created process instance for a particular businesskey.
The ProcessInstance ( Variablename - 'existingProcess; in below code) that was created for a quote returns null and we end up creating a new process instance through the correlate method.
We are expecting the existingProcess(ProcessInstance) to return a value if the processInstance has already been created for that particular businesskey(quotenumber below) . This creates duplicate process instance for the same quoteNumber.

Sample Code:

import org.camunda.bpm.engine.RuntimeService;
import org.camunda.bpm.engine.delegate.DelegateExecution;
import org.camunda.bpm.engine.delegate.JavaDelegate;
import org.camunda.bpm.engine.runtime.ProcessInstance;
import org.springframework.stereotype.Component;

import java.util.Collection;
import java.util.Objects;
import java.util.Set;
import java.util.stream.Collectors;

@Component
@Slf4j
public class ProcessQuoteDelegate implements JavaDelegate {

@Override
public synchronized void execute(DelegateExecution execution) throws Exception {
    ProjectDto project = (ProjectDto) execution.getVariable("project");
    String projectNumber = (String) execution.getVariable("projectNumber");
    String quoteNumber = (String) execution.getVariable("quoteNumber");

    Set<String> lineItemMasterIds = project.getPurchaseOrders().stream()
            .map(PurchaseOrderDto::getLineItemMasters)
            .flatMap(Collection::stream)
            .filter(lineItemMaster -> Objects.equals(lineItemMaster.getQuoteNumber(), quoteNumber))
            .map(LineItemMasterDto::getLineItemMasterId)
            .collect(Collectors.toSet());

    RuntimeService runtimeService = execution.getProcessEngine().getRuntimeService();
    ProcessInstance existingProcess = runtimeService.createProcessInstanceQuery()
            .processDefinitionKey("process-quote")
            .processInstanceBusinessKey(quoteNumber)
            .singleResult();

    if (existingProcess == null) {
        log.info("No existing process instances found for quote {}, creating new process instance", quoteNumber);

        runtimeService.createMessageCorrelation("LineItemMastersReceivedEvent")
                .processInstanceBusinessKey(quoteNumber)
                .setVariable("projectNumber", projectNumber)
                .setVariable("quoteNumber", quoteNumber)
                .setVariable("lineItemMasterIds", lineItemMasterIds)
                .correlate();
    } else {
        log.info("Merging new line item masters for quote {} into existing process instance {}", quoteNumber, existingProcess.getProcessInstanceId());

        runtimeService.createMessageCorrelation("AdditionalLineItemMastersReceivedEvent")
                .processInstanceId(existingProcess.getId())
                .setVariableLocal("newLineItemMasterIds", lineItemMasterIds)
                .correlate();
    }
}

}

Hello @Madan_Kumar_Maha and welcome to the forum,

To query the process instance via the runtime service, the instance must be written to the database.
By default, Camunda 7 commits an instance to the database when it reaches a wait state. You can read more about process instances and wait states in the documentation.
In your case, you should set the async before flag on your process start event:

I hope this helps.

Stephan

1 Like