How to trigger activity retry from activity interceptor

Hi Temporal Team,

I’m trying to trigger an activity retry by throwing an exception from implementation class of ActivityInboundCallsInterceptor. However, it fails the workflow.

Is there a way to trigger an activity retry from the interceptor?

Should I throw Activity.wrap(e)?

Thanks,
Richard

Should I throw Activity.wrap(e)?

yes that should work, for example:

 @Override
  public ActivityOutput execute(ActivityInput input) {
    throw Activity.wrap(new NullPointerException("simulated error"));
  }

You can catch ActivityFailure in your workflow code and handle it in this case as well.

Can you explain your use case for doing this please?

I have two environments, each with a datastore. The datastores keep each other updated with global quorum.

Also, the two environments have worker nodes that consume tasks from the same task queue.

Before executing an activity, in the interceptor, we read from the datastore.

Workflow:

  • Activity 1
  • Activity 2

Activity 2 can be reading from the datastore before the global quorum completes after Activity 1.
If this scenario occurs, we want to throw an exception from the interceptor so that Activity 2 will retry, giving the datastores more time to complete the global quorum.

Thanks,
Richard

Thanks for explaining.

Tested and you can use both Activity.wrap(…) as well as just throw an unchecked exception, for example: throw new NullPointerException("simulated error").

However, it fails the workflow.

It probably fails because your retries got exhausted and you do not handle ActivityFailure in your workflow code. Note that retries are still going to follow your set activity retry options. Also in case you specify on your activity options “setScheduleToCloseTimeout” this timeout includes retries.

Note that ActivityInboundCallsInterceptorBase->execute applies for all activity invocations, but you can get the activity type from activityExecutionContext.getInfo().getActivityType() (just remember that by default the activity type name is the name of your activity method with first letter capitalized).

I think your requirement could be solved without use of interceptors as well. Take a look at this forum post it explains different polling approaches and recommendations based on the poll frequency.

Note that the only purpose of Activity.wrap is to support rethrowing checked exceptions without adding them to the signature of a method. It is absolutely not needed to throw any unchecked exception.

Yes, looks like we ran out of retries.

Thanks both!