Problem using Exit step and an adapter service in catch block

I am developing an integration where,I need to update a flag in a table when an exception is thrown.
In the catch block of the integration I called the update service and then the Exit-failure step.I used Exit step as once it logs an error mail is sent by another process,so I need to log it.

But problem is that when an exception is thrown, after the update adapter service in catch block when flow goes to Exit-failure step everything is rolled back and the the update of flag is not done.

So can any one help how can I handle the situation.
Task is that:
When an exception is thrown in try block flag sholud be updated in a table and as well as a mail is to be sent.

Surendra,

I can think of two ways of resolving the problem that you are facing -

  1. In the catch block, define explicit transactions in your catch block by using transaction services of the WmART package:
Catch Sequence[Exit on Done] 
   pub.art.transaction:startTransaction 
   update flag in table 
   pub.art.transaction:commitTransaction 
   Exit [Signal Failure]
  1. Instead of using Exit[Signal Failure] in your catch block, you can return an output flag (eg ‘status’) along with a ‘statusMessage’ describing the status. In the calling service, check (branch on) for the status to send out the email, using the statusMessage as the description of error.

Either of these should work.

Rohit

Hi Rohit,

Even we are facing the same problem. I tried your suggestion of using the Art.Transaction services, but the problem i faced here is the Art.transaction.commit service is commiting the JDBC adapter service in the TRY block and not in the CATCH block. For the time being, as a solution we are not using the EXIT [signal failure] step.

Would like to know, huv does the use of an EXIT step affect the FLOW?
The PDFs doesnt say anything about the transactions being rolled back.

Hey Nandan,
How are you making sure your transaction is being rolled back at all. Is your adapter connection LOCAL or NO Transaction. Is the update really happening. Because in catch block under ext on done you will not finad any explicit errors.
Regards,
Pradeep

Nandan,

Plz provides the specifics of what you are trying to achieve for me to be able to answer you better. My reply was to Surendra who was trying to update a table WHEN an exception occurs - which meant, his update service was called in the catch block. Thus, I suggested using pub.art.transaction services to ensure that the commit happens, before exiting the flow and signaling failure. The Exit [signal failure] signals the runtime that the entire flow has failed (as is my understanding), thus any implicit and non committed transactions are rolled back.

Also Pradeep has raised an important question - what kind of adapter connections are you using? LOCAL_TRANSACTIONS?

Rohit

Hi Rohit, Surendra
I’m using the LOCAL_TRANSACTION, in the adapter connection.
Rohit, in my integration i will be publishing a document and after the publish i’ll update the flag as ‘P’ in the source DB. If it errors out in the try block, i’ll update the flag to ‘E’ in the catch block.

“LOCAL_TRANSACTION :With this transaction type, all of the operations on the same connection in one transaction boundary will be committed or rolled back together. A transaction boundary means the scope of the transaction, from the beginning to the end of a transaction. It can be in one adapter service, one flow service, one Java service, or several steps in a flow service.”

According to this when i use the commitTransaction service, the update service in the Catch block should also be commited right? But here its commiting only the update service in the Try block only,though both the adapter service lies in the same “transaction boundary”, Why is this?

Let me put my earlier question this way…
How necessary is it to use the EXIT step in a Flow service? wat are the Pros and cons of using/not using it?

By ‘It errors’, do you mean if the publish errors or the update errors? Also, I don’t quite understand what do you mean by

It will be easier to understand your scenario if you describe your flow.

Finally - Exit step is used to signal the calling service the status of the called service… its use is not mandated unless you wanna signal to the runtime to perform a rollback - for example signalling notification to rollback a message taken off by a listener from a queue.

Anyhow, based on my understanding of what you are trying to do - that is, you publish a document and if the publish step throws an error, you want to update a flag to ‘E’, but if the publish is successful, you wanna update it to ‘P’. You can publish the document and then call your update adapter service to update the flag to ‘P’ as the next step. If the publish causes an error, the update service will never be executed and the flow will go to the catch block. In the catch block, you can again call the update service to update the flag to ‘E’. HOWEVER, if for any reason, you plan to use EXIT[signal failure] as the last step in your catch block, you must use explicit transaction (pub.art.startTransaction and commitTransaction) to commit the update, because in absence of an explicit commit, the EXIT step will tell the runtime that the service has failed and the update will be rolled back.

To summarize the role of EXIT vis-a-vis the transaction in your scenario… if you do not define explicit transactions, IS runtime keeps a track of the modifications made by your service to the database, and if the service completes successfully (ie has last step as EXIT[signal success] or has no EXIT), the runtime commits the transaction but if the service fails (has EXIT set to signal failure), the runtime rollbacks all the database changes. Now, if you wanna use the EXIT[signal failure] step in your flow for some reason and still want to commit the changes in the database, you will need to use explicit transactions. Just start a transaction, call the adapter service (insert, delete or update) and then commit the transaction. Thereafter, even if you use EXIT[signal failure] the update will not be rolled back.

Rohit

Hi Rohit,
The flow of the integration on the source side is like this

Seq1 - Success
Seq2 - Exiit on Failure (Try)
adaptrServ - Fetch the data(Select)
map - mapping to canonical
adpterSrv1 - update the flag to ‘P’
publish - publish the doc
Exit - signal Success
Seq3 - Exit on Done (Catch)
getLasterror
*–> adpterserv2 - Update the flag to ‘E’
send error mail
Exit- signal Failure

Here in the Try block, i’m updating the flag to ‘P’ before publishing, b’coz i faced situation where the Ack recvd from the target side (another service) updates the flag to ‘C’ indicating successfull completion, first and then the adpterSrv1 gets executed. So instead of having the flag as ‘C’, i’ll have flag as ‘P’.

What i meant by “If it errors out” is, if the Broker Q is full or for any other reason, if the Publish step fails, then the flag has to be updated to ‘E’.

Here both the transactions are rolled back(adptrserv1 and adptrserv2).

When I used the Art services, start transaction and commitTransaction in the Catch block. Only the update of the adptrserv1 is commited and not of the adptrserv2.

Hope this time i’m clear in explaining the scenario.

Thanks,
Nandan

FYI: Using an ‘EXIT and signal FAILURE’ step is also useful when trying to log errors to the webMethods Monitor.

Castro, Thanks for adding in.

Nandan,
I am confused in trying to see how you were expecting a commit in the catch block to work on an update that was in the try block, because, if the try block completes successfully, the flow will never get to the catch block - ie, the commit in the catch block will never get executed. On the other hand, if an exception occurs in the try block - you wouldn’t want the update in the try block to get committed anyway… right?

Based on the flow that you have given, here’s what I think will do the trick:

Seq[Success]
Seq[Failure]
adaptrServ - Fetch the data(Select)
map - mapping to canonical
pub.art.transaction:startTransaction[tName=A]
adpterSrv1 - update the flag to ‘P’
publish - publish the doc
pub.art.transaction:commitTransaction[tName=A]
Exit - signal Success
Seq[Done]
getLasterror
pub.art.transaction:rollbackTransaction[tName=A]
pub.art.transaction:startTransaction[tName=B]
adpterserv2 - Update the flag to ‘E’
pub.art.transaction:commitTransaction[tName=B]
send error mail
Exit- signal Failure

I think you will get an idea on how to use transactions… just a note - when you are using transactions in your service, you will not be able to trace/step through it. If you want to step through your service, you will need to disable all the transaction steps, failing which you will get some error message (can’t remember from top of my head what the error is).

HTH, Rohit

U can roll back first and can also go for a no transaction to update the flag instead of going to Local transaction in the catch block.

Murali, I thought tht wihout using a transaction, the update in the catch block would be rolled back when the flow exits using Exit[signal failure]. Don’t you think so?

Rohit

Rohit
You can call the rollback first and then the update, this update is NO_TRANSACTION.
This shud solve the problem.

-Murali

Hi

Rohit,
I was not expecting a commit for the service in the Try block, but that was what happened when i used the transaction services ONLY in the Catch Block. Strange…:confused:

But I used the logic given by you, its working fine.

Thanks Rohit,

And thanks Castro , Murali for your inputs

Murali - the point is that Nandan wants to use EXIT[signal failure] as the last step in the catch block and if you exit a flow signalling failure, wihout using transactions - the update WILL get rolled back. I think you are missing the point about the use of EXIT[signal failure] as the last step in the catch block.

Nandan, I’m glad you got it to work :).