TriggerSnapshots not cleared after identity refresh causing repeated trigger execution

Share all details about your problem, including any error messages you may have received.

Hello,

We are facing an issue with a looping trigger after identity refresh and triggerSnapshots remaining stored on an Identity

The scenario is:

  • We have an Identity Trigger configured on an identity attribute value change
  • The trigger launches a custom workflow.
  • The workflow performs some provisioning operations and identity attributes updates with save/commitTransaction with a refresh identity step at the end
  • After the workflow completes, the triggerSnapshots entry is still present in the Identity XML.
  • At the next refresh the trigger fires again

Are they any essential elements to check in order to find why this is happening ?

Thanks
Best Regards

Hi Alshahim,

Could you share a few more details?

- How is the trigger configured (attribute change or a Trigger Rule)?

- If you’re using a Trigger Rule, could you share the logic?

- Which identity attributes are being updated in the workflow? Are they part of the trigger condition?

- How is the Identity Refresh being called at the end of the workflow?

It looks like the workflow or refresh might be causing the trigger condition to be met again. Seeing the trigger configuration and rule logic would help narrow it down.

Hi @santhirajumunganda

For the trigger :

  • It is an attribut change
  • The changed attributes are not part of attributes changes , in the workflow we remove remaining assigned roles using provisionner in one step , and remove manuel attributes assignement in another step wich has the saveObject and commit transaction on the identity object
  • identity refresh call :
  <Step action="call:refreshIdentity" icon="Task" monitored="true" name="Refresh Identity" posX="314" posY="11">
    <Arg name="identityName" value="ref:identityName"/>
    <Arg name="promoteAttributes" value="true"/>
    <Arg name="correlateEntitlements" value="true"/>
    <Arg name="refreshIdentityEntitlements" value="true"/>
    <Arg name="synchronizeAttributes" value="true"/>
    <Transition to="Stop"/>
  </Step>

Best regards

Hello Alshahim. Based on what you have described, I would first check the Identity object you are using in the step where you remove manual attribute assignments and call saveObject/commitTransaction. If that is the same object loaded when the trigger launched the workflow, it would still carry the old triggerSnapshots map on it. Saving that object writes those snapshots right back to the database, even if a refresh already cleared them.

The thing to try: right before you update and save the Identity, decache it and reload a fresh copy:

context.decache(identity);
identity = context.getObjectByName(Identity.class, identityName);

Then apply your manual assignment changes on this fresh object and commit.

On processTriggers, I would not add it to the refresh step inside this workflow. That option is what maps to “Process Events” in the Identity Refresh task, and it evaluates configured IdentityTriggers during the refresh (Compass reference). Since your workflow was launched by that same trigger, enabling it here can cause the workflow to fire itself again. Your scheduled Identity Refresh task with Process Events enabled should handle that part.

Test with one affected identity after making the decache fix. If triggerSnapshots clears after the next scheduled refresh, that confirms it. If it still sticks around, I would check the refresh and workflow logs for anything re-creating it.

Hello @punna0001 ,
Thanks for this detailed answer ,

For our case thers is no identity loaded in the workflow for each step we do :

 Identity identity = context.getObjectByName(Identity.class, identityName);

The first 2 steps build and execute provisioning plan for target applications and roles removal , And for the last step where identity is updated has saveObject/commitTransaction

Thanks Alshahim. Since the first two steps only execute provisioning plans, I would focus on the last step where the Identity is directly saved and committed.

triggerSnapshots may still be present while the parent refresh is processing the lifecycle event, and it should normally be cleared when event processing completes. The saveObject() and commitTransaction() inside the triggered workflow may be interfering with that cleanup.

For one test identity, temporarily skip only that final save/commit step and run the same refresh. If triggerSnapshots clears and the trigger does not repeat, that strongly points to the direct Identity commit as the cause.

In that case, I would move the manual AttributeAssignment cleanup to a separate process that runs after the lifecycle event refresh completes, rather than committing the Identity from inside the triggered workflow.

I would also keep processTriggers out of the workflow refresh step. It evaluates IdentityTriggers, so enabling it inside a workflow launched by the same trigger can cause the event to be evaluated again.

If the snapshots still remain without the final save/commit, then that step is not the cause. At that point, I would review the refresh and workflow logs or raise it with SailPoint Support.

Just one thing to check. Are you comparing both the previous and new values of the attribute, or checking only one value?

Attribute change triggers in IIQ are very sensitive. During every Identity Refresh, IIQ evaluates the trigger condition again. If the condition is still true, it may keep adding/retaining the triggerSnapshot and fire the trigger again.

Since you’re using a custom workflow, you could consider using a Trigger Rule instead. In the rule, return true only when the change happens for the first time and false for subsequent refreshes.

I had seen a similar issue before, and we resolved it by adding this additional check in the Trigger Rule. It might help in your case as well.

looking like is the problem. Can you turn off the flag and try it? I hope it should work.

Thanks,

PVR.

@alshahim04 Can you please check your Provisioning Approval Subprocess and see if noTrigger variable is defined or not. If not, please create one and set the value to true.

Try and let us know if it resolve your issue.