Posted: 27 Aug 2018 13:39 EDT Last activity: 30 Aug 2018 14:44 EDT
Process all child cases and rollback on error
What's the best way to perform an action on all child cases (covered case), trap errors and handle a rollback? For my use case I have N child cases and I need to perform a flow action on each one. For each child case I'll call a flow action to either withdraw the case or call resumeFlow() to move the case out of a hold workbasket to make it active. As I iterate over each child case and take action I want to trap errors and rollback. I want to rollback all child cases even if the action on the last one of say 10 children fails.
Originally we wrote an activity to iterate over the list of children, called obj-open, then called resumeFlow(). This works when there are no errors but it does not work when I trap an error and try to rollback. All previously updated child items have been committed automatically by PRPC.
There has to be a better way to do this. Perhaps a split for each shape.
The problem here seems to be able to rollback all the changes applied to the child cases already processed in the past in case of a single failure occurring while processing a following child case.
To avoid incurring in scaling issues I would consider refactoring the design to manage it as a long running transaction with compensating actions to deal with process failures that may occur in child cases.
Creating a long running transaction is exactly the design pattern that should be used here. The question is how do you do that in PRPC.
The challenging part is that PRPC controls the transaction boundaries and commits. As you call a flow action on each child case PRPC will commit. I don't have any issues trapping the errors for each child but when I find them any previously processed child item has already been committed. Writing my own code to rollback those cases would be a giant headache. Ideally I would like to create a long running transaction (Saga). If that is possible please share some tips. BTW - resumeFlow() takes the parameter "calledFromServiceLevel". When True commits are handled differently because the agent code will commit at the end. So far this has not helped.
After speaking with several people for advice including pega engineering there is no way to set up a long running transaction as suggested above and using flow actions. Engineering suggested that I avoid the flow action and just use pxChangeStage directly after opening each child case. In this case use pxChangeStage to jump the flow to a resolve stage and trap errors along the way. The expectation is that I'd be able to rollback as needed.
I'm not sure that this will work 100% because resolving an item calls a lot of OOTB pega code that will commit the case negating the ability to rollback. Changing the stage and parking in another assignment would have the same issue too. Using something like pxForceCaseClose may work too but for my use case it is not appropriate.
In the end I've decided to trap errors while processing each child case. If one is found I'll stop iterating, rollback what I can and route back to the original assignment.