Application Development and Automation Discussions
Join the discussions or start your own on all things application development, including tools and APIs, programming models, and keeping your skills sharp.
cancel
Showing results for 
Search instead for 
Did you mean: 
Read only

BAPI_TRANSACTION_COMMIT - return error handling

Former Member
0 Likes
8,934

I have to save N documents in DB. If an error happens in any document, you should not save any other document, that is, or ALL or NOTHING.

The algorithm is as follows:


 Error = ''. 
 LOOP AT ....  "For example, 100 times for 100 Documents
        CALL FUNCTION 'BAPI_ACC_DOCUMENT_POST'
                  EXPORTING ...
                 IMPORTING ...
                 TABLES    ....
                                 RETURN = BAPI_RETURN_TABLE.

         LOOP AT  BAPI_RETURN_TABLE ASSIGNING <ret>.
               IF <ret>-TYPE = 'E'.
	 	 "If an error occurs on a document, do rollback on all the documents 
                 "already posted and flow ends.
                  CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'
                            IMPORTING RETURN = RETURN.
                   "I do not analyze the error in the ROLBACK RETURN, 
                   "because read somewhere that ROLLBACK can not fail.
		   Error = 'X'.  "In case of error, flow ends!
		   EXIT.  
         ENDLOOP.
  	IF Error = 'X'.
 	     EXIT. 
        ENDIF.
 ENDLOOP.        
    
 CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
       EXPORTING
               WAIT = 'X'
      IMPORTING
               RETURN = RETURN.
     "In the COMMIT, in case of error, RETURN table has only one record.
      IF RETURN-TYPE = 'E'.  
            "Point A:      I do not know what to do??????
      ENDIF.

Questions are:

1. The algorithm is correct?

2. I am not sure that I do in "Point A". How does the COMMIT?

If that could happen:

(a) with COMMIT are written in DB, for example, 30 documents, after that fails COMMIT of 31. document?

(b) If (a) is yes, i do ROLLBACK on other documents (from 31. up to 100.), posted but not saved in DB?

(c) If (b) is yes, at the end, 30 documents are saved and 70 documents are not saved.

This situation does not suit me, because, I repeat, I have to saved all 100 or nothing.

Thanks in advance,

Serena

1 ACCEPTED SOLUTION
Read only

SuhaSaha
Product and Topic Expert
Product and Topic Expert
0 Likes
4,232

Hello Serenaa,

If you check 'BAPI_TRANSACTION_COMMIT', you'll see that the 'E' message will be populated only if the COMMIT WORK AND WAIT fails.

From SAP documentation non-zero SY-SUBRC after COMMIT WORK AND WAIT signifies,

the updating of the update function modules was not successful.

So i would not worry much if you've bundled the calls in one LUW. If your BAPI_TRANSACTION_COMMIT fails, all the updates will be reversed

BR,

Suhas

10 REPLIES 10
Read only

former_member222709
Contributor
0 Likes
4,232

Hi serenaaa,

I consider this as a challenging requirement. Though I've never used it before, but, I can suggest you to try the option synchronous Update.

Add the keywords, 'IN UPDATE TASK' after the CALL FUNCTION 'BAPI........' IN UPDATE TASK and then try the COMMIT or ROLLBACK.

In a common scenario, COMMIT is done after every BAPI call.

Regards,

Pranav.

Read only

former_member404244
Active Contributor
0 Likes
4,232

Hi,

The data will be saved to database once you use " BAPI_TRANSACTION_COMMIT".

So what i can suggest is that you pass 100 records to the bapi and check for error message in the return strucure.. if you find any error then throw message else.

call again bapi and pass the data and update .. try like this



LOOP AT ....  "For example, 100 times for 100 Documents
        CALL FUNCTION 'BAPI_ACC_DOCUMENT_POST'
                  EXPORTING ...
                 IMPORTING ...
                 TABLES    ....
                                 RETURN = BAPI_RETURN_TABLE.
 
read table BAPI_RETURN_TABLE with msgtype = 'E'.
if sy-subrc eq 0.
error = 'X'.
exit.
endif.
endloop.
Throw error message here.

if error is initial.
LOOP AT ....  "For example, 100 times for 100 Documents
        CALL FUNCTION 'BAPI_ACC_DOCUMENT_POST'
                  EXPORTING ...
                 IMPORTING ...
                 TABLES    ....
                                 RETURN = BAPI_RETURN_TABLE.

CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
       EXPORTING
               WAIT = 'X'
      IMPORTING
               RETURN = RETURN.
endloop.

endif.

Regards,

Nagaraj

Read only

0 Likes
4,232

Nagaraj, thanks for the reply. Could you clarify this in the response of ".. if you find any error message then throw else.

BAPI call again and pass the time and update .. try like this "

Perhaps I should say that this code should be part of an ABAP program scheduled in the background and the outcome of the update should write a log file. According to the outcome, the end user should repeat the update failed, launching the program at hand.

I appreciate it very much the answer that refers to my algorithm, very precise. Please give me your expert opinion on the things I wrote in the questions and comments.

Regards,

Serena

Read only

SuhaSaha
Product and Topic Expert
Product and Topic Expert
0 Likes
4,233

Hello Serenaa,

If you check 'BAPI_TRANSACTION_COMMIT', you'll see that the 'E' message will be populated only if the COMMIT WORK AND WAIT fails.

From SAP documentation non-zero SY-SUBRC after COMMIT WORK AND WAIT signifies,

the updating of the update function modules was not successful.

So i would not worry much if you've bundled the calls in one LUW. If your BAPI_TRANSACTION_COMMIT fails, all the updates will be reversed

BR,

Suhas

Read only

Former Member
0 Likes
4,232

Thanks Suhas!

1.

If you check 'BAPI_TRANSACTION_COMMIT', you'll see that the 'E' message will be populated only if the COMMIT WORK AND WAIT fails.

This is OK!

2.

From SAP documentation non-zero SY-SUBRC after COMMIT WORK AND WAIT signifies,

the updating of the update function modules was not successful.

These two versions are the same?

 
    " 1. Vesrion
    
    CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
         EXPORTING
                   WAIT = 'X'
         IMPORTING
                   RETURN = RETURN.

    IF RETURN-TYPE = 'E'.
       LOG-TYPE  = RETURN-TYPE.
       LOG-ID    = RETURN-ID.
       LOG-NUMBER= RETURN-NUMBER.
       LOG-MESSAGE= RETURN-MESSAGE.
    ENDIF.
    
    " 2. Vesrion
    
    CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
         EXPORTING
                   WAIT = 'X'
         IMPORTING
                   RETURN = RETURN.

    IF SY-SUBRC <>  0.      " SY-SUBRC NE  0
       LOG-TYPE  = RETURN-TYPE.
       LOG-ID    = RETURN-ID.
       LOG-NUMBER= RETURN-NUMBER.
       LOG-MESSAGE= RETURN-MESSAGE.
    ENDIF.

3.

So i would not worry much if you've bundled the calls in one LUW. If your BAPI_TRANSACTION_COMMIT fails, all the updates will be reversed

Are you telling me if COMMIT fails at any point and for whatever reason, none of the 100 documents are not saved in the DB? If you are very sure, I will believe it !

Grazie e ciao,

Serena

Read only

0 Likes
4,232

Hi,

Suppose you have 10 documents and out of which 9 or correct and the last one is error . If you go with a commit then the 9 records will be created and the last one will be error and it will be roll back.

suppose you have 10 documents , first eight are correct, ninethone is error and tenth one is correct. so it will create 9 documents and will leave 9th one and even though you used roll back it will roll back only 9th one not all 8 one's which already created.

Actaully we use test run fucntionality to check whether the records are correct . it seems the bapi you are using doesn't have any test run functionality.

also i have suggested error message if you run online if not then you can write error log and download to desktop or application server.

Regards,

Nagaraj

Read only

Former Member
0 Likes
4,232

Thanks Nagaraj!

I have verified that all documents are posted without error, with 'BAPI_ACC_DOCUMENT_POST', after which I COMMIT.

In fact, I'm sorry, I forgot two lines in my algorithm. I write CALL FUNCTION 'BAPI_TRANSACTION_COMMIT' between IF Error = '' and ENDIF.

Here is the updated algorithm.

 
  
Error = ''. 
LOOP AT ....  "For example, 100 times for 100 Documents
        CALL FUNCTION 'BAPI_ACC_DOCUMENT_POST'
                  EXPORTING ...
                 IMPORTING ...
                 TABLES    ....
                                 RETURN = BAPI_RETURN_TABLE.
 
         LOOP AT  BAPI_RETURN_TABLE ASSIGNING <ret>.
               IF <ret>-TYPE = 'E'.
	 	 "If an error occurs on a document, do rollback on all the documents 
                 "already posted and flow ends.
                  CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'
                            IMPORTING RETURN = RETURN.
                   "I do not analyze the error in the ROLBACK RETURN, 
                   "because read somewhere that ROLLBACK can not fail.
		   Error = 'X'.  "In case of error, flow ends!
		   EXIT.  
         ENDLOOP.
  	IF Error = 'X'.
         EXIT. 
      ENDIF.
 ENDLOOP.        

 IF Error = ''.
    CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
            EXPORTING
                  WAIT = 'X'
            IMPORTING
               RETURN = RETURN.
                 "In the COMMIT, in case of error, RETURN table has only one record.
     IF RETURN-TYPE = 'E'.  
            "Point A:      I do not know what to do??????
      ENDIF.
 ENDIF.     


.

His speech changed?

Ciao,

Serena

Read only

SuhaSaha
Product and Topic Expert
Product and Topic Expert
0 Likes
4,232

Hello Serena,

SAP transactions adhere to the properties of an [ACID transaction|http://en.wikipedia.org/wiki/ACID#Isolation].

The key point to discuss here is "atomicity" which means "all or nothing". As i had mentioned in my previous post, you should bundle all the BAPI calls in a single LUW. This will ensure if the commit fails all the previous changes are also rolled back.

Hope you get the point.

BR,

Suhas

Read only

Former Member
0 Likes
4,232

Hello Suhas

It is true, the key point here is to discuss "atomicity" - "all or nothing".

Thank you, your response is clear and precise and is worth 10 points :-).

Ciao,

Serena

Read only

Former Member
0 Likes
4,232

Hi Suhas,

just came across this old post and find your suggestion... and I don't think it's 100% correct, sorry. IMHO, your statement would be correct, if saying 'you should bundle all function calls in update task in a single LUW. This will ensure if the commit fails all the previous changes are also rolled back.'

The important thing is that we are discussing the BAPIs here - and these are usually developed the way that all the checks are carried out before the update FM is registered in the BAPI for update processing, with purpose to detect all potential errors at the first place. So, it's very, very unlikely that any BAPI would trigger the same kind of errors in the update FM as we can normally see in dialog transactions where the errors occur time from time and lead to express message about cancelled update.

What I intend to say is that BAPI errors (of application nature, i.e. 'logical' or 'data integrity risk' errors) are detected first and (should any be found) returned in some BAPIRET2 return table actually before BAPI reaches the update FM registration internally. Then if one out of 10 BAPI calls fails this way (which can be detected just by looking for 'E' messages in return table) then COMMIT WORK AND WAIT would not fail but would rather process remaining 9 BAPIs successfully (since the BAPI which 'failed' did not manage to register the update FM yet).

So, to reach 'all or nothing' logic on more BAPIs in one LUW, the only way is to check the presence of 'E' message after each BAPI call and stop the processing on the first 'E' message found.

BR

Michal