How to get workflowStub using runId?

I need the stub of an executing workflow to send it signals.
Can I get the stub with only runId and without WorkflowId?

HI, are you talking about testing? Do you want to test workflow code which receive signal?

The workflow id is its business identifier and is required to identify a workflow execution.

WorkflowExecution that you get from WorkflowClient.start(…) for example includes both the workflow id and its run ids. You can use it in your client / activity code to signal it:

WorkflowStub uws = client.newUntypedWorkflowStub(myWorkflowExecution, Optional.empty()); 
uws.signal("mySignalName", args);

Another thing you could do is use ListWorkflowExecution and a query for example:

String query =
        "RunId='"
            + runId
            + "' and ExecutionStatus="
            + WorkflowExecutionStatus.WORKFLOW_EXECUTION_STATUS_RUNNING_VALUE;

    ListWorkflowExecutionsRequest listWorkflowExecutionRequest =
        ListWorkflowExecutionsRequest.newBuilder()
            .setNamespace(client.getOptions().getNamespace())
            .setQuery(query)
            .build();
    ListWorkflowExecutionsResponse listWorkflowExecutionsResponse =
        service.blockingStub().listWorkflowExecutions(listWorkflowExecutionRequest);

    List<WorkflowExecutionInfo> executionInfo = listWorkflowExecutionsResponse.getExecutionsList();

    // should be just one or zero for the used query..
    for (WorkflowExecutionInfo wei : executionInfo) {
      WorkflowStub uws = client.newUntypedWorkflowStub(wei.getExecution(), Optional.empty());
      uws.signal("mySignalName", myArgs));
    }

Note that for this you have to have ES enabled on the Temporal server level when you start it.

Thankyou tihomir.
Your second solution is the kind of solution that i am looking for.

I think I was too brief in the question. Let me expand the use case.

My Application will spin a workflow (say wfid is W456 and runid is R123) and the workflow will make a request to an endsystem and ask it do some work. In the request I am passing run id - R123.
The endsystem will acknowdge the request (Synchronous resposne).

Post that my workflow will pause the execution untill it gets a singnal (say continueSignal).

The endsystem once the work is done will call my application back (Asynchronous response). The callback will contain the run ID.

At this point, My application needs to use the runId received in the asynchronous response and create the correspoding workflow stub and then invoke the signal (continueSignal) using the stub.

Constraits

  1. I can only pass one variable to the endsystem. Either runID or workflowId
  2. I can’t use workflow id because, my use case can have 2 workflows with the same id.

Your second solution does the job. But it is too complicated.
Is there a simpler solution?

Workflow id and run id and namespace are strings. They identify the workflow execution.
You could pass to end system a single string like

“workflowid-workflowrunid-namespace” (or use some other delimiter)

@Vikas_NS I wouldn’t recommend the second solution unless your workflow rate is very low. The list API wasn’t designed to support high query rates. So making a list query per workflow is an anti-pattern.

  1. I can only pass one variable to the endsystem. Either runID or workflowId
  2. I can’t use workflow id because, my use case can have 2 workflows with the same id.

The solution is to not use RunId to identify workflows. Use WorkflowID instead. Temporal doesn’t allow having multiple workflows with the same id. So you constraint is not really valid.

Hi Maxim,
I understand that we can’t have 2 workflows with same wfid running. Our usecase invovles reuse of workflow id. So we can have few completed workflows and a running one with the same workflow id.

Based on your recommendation we have decided not to use the second solution.
We will use both runId and worklfowId to create the stub.

Thankyou.

1 Like

Hey everyone
Could you please advise if there are some legal and recommended ways to get the workflow type and workflow’s Id by a runId?

Could you please advise if there are some legal and recommended ways to get the workflow type and workflow’s Id by a runId?

What’s the use case for this?

Thank you @maxim for the reply

The use case is the following:
We want to expose an API for

  1. initiating a workflow execution
  2. retrieving a workflow’s state (a field inside the workflow class).

Let’s say the workflow is responsible for creating an “employee” entity.

An API’s caller supplies an employee’s data (enn and additional attributes) into a workflow’s initiation endpoint.
According to the enn, we generate a workflow’s id and start the workflow.
To allow for the client to furtherly track the workflow’s state (via short pooling), we need to respond to him with the workflow’s Id + runId.

Why only workflow’s id is not enough?
Because If a particular workflow’s run completes with a specific state, API’s client may decide to re-run the workflow with the previously used workflow’s id (enn) with different additional data.

It would be much easier for the client to operate only with a runId and don’t use the workflow’s id during communication with the API.

So, inside the API responsible for retrieving the workflow’s execution state, we would like to consume only runId and invoke workflow’s “query” method for fetching state field.

I see. In this case, I would recommend not use customerId as WorkflowId, but generate a new WorkflowId for each transaction.

Another option is to not complete ever the customer workflow and communicate with it through signals, possibly using SignalWithStart to initiate it for new customers.