Wednesday, May 14, 2008

SAP R/3 : Trailing The Pricing Condition

Last several weeks, an unusual incident occured at the area of pricing condition in which one of the pricing (condition type) is not populating price correctly. Initial coding were done in one of the user exit to recorrect the value. However, the value was not updated as the functional wanted. So I had to follow the trail of Indiana Jones by tracing the standard program. So below is one of the gruesome steps on how the pricing condition was determine during invoice creation (VF01).

Put a break point accordingly to each of the path below:

1. SAPMV60A (Travel Here)

2. SAPLV60A (Travel Here)

3. SAPLV60A (Travel Here)

4. SAPLV60A (Travel Here)

5. SAPLV60A (Travel Here)
6. SAPLV60A (Travel Here)
******>(At this point, JIN1 KWERT WAS REINITIALIZE TO 0.22 -> Which We do not WANT!)<br>
7. SAPLV61A (Travel Here)
******>(How all 0.22 started)

8. SAPLV61A (Travel Here)
******> KSTEU and KMPRG (This is the two brothers that caused it!)

Therefore, we had the good owner to initialize the KSTEU and KMPRG to a certain value so it the value can be remain as the Functional wanted to meet the requirements.

is sky the limit... pricing procedures rocks!

SAP R/3 : User Exits in VF01

Something to help everyone on all the userexits and BADI for transaction code VF01. VF01 is to create invoice. Below are the list of all userexits and some BADI invoke (maybe). In which of late, i had a headache to check out why VF01 had problem in creating invoice successfully.


SDVFX010 - for those who wants to do something during SAVE

In any way, if you find this user exit unable to help you and would want to know more if there are other user exits. You can always punch up the ST05 to do an analysis on your VF01.

is sky the limit... user exits on VF01

Tuesday, May 06, 2008

SAP R/3 : Sending Multiple PDF Invoice From Output Type

Sending email with an invoice attached to it has never occured to me if it can be done without the working mechanism of business workflow. The requirement was fairly simple during discussion and it was seriously sounded simple enough to put it straight to development immediately. However, I am not very familiar with business workflow. So the question now was how am I going to send an email out with an invoice attach to it. So here is the requirement in question:

"When user create an invoice via VF01 or from a customized IDOC that creates invoice, several output types are created and one of them is an outbound IDOC that will send back to the sender to let them know invoice has been created. Now, after the invoice and IDOC has been sent out, there should be a mechanism to check whether the outbound IDOC is successfully send out. If it is successfully sent out, the mechanism will grab that invoice, convert it to PDF, attach it to an email and send it to responsible recipients..."

Oh boy, it sounds easy to one who is not aware of the workaround behind or does it sounds very technical to one who has minimal working knowledge on it? I was the latter. So below are some of the questions which had formed in my brain:

1. How do you grab an invoice which has been produced by the system (VF01)?
The CLOSE_FORM function module will return a spool no when the SAPSCript has finish processing and display.
2. How do you convert an invoice to a PDF?
The CONVERT_OTFSPOOLJOB_2_PDF function module take the input of SAPScript and returns in PDF format.

3. How do you attach a PDF to the email?
The SO_NEW_DOCUMENT_ATT_SEND_API1 function module will hold the PDF

4. How do you send an email?
The SO_NEW_DOCUMENT_ATT_SEND_API1 function module will hold the PDF and send the email

After giving some thoughts to those questions above, now comes the big part of the whole mother of all questions:

How on earth at which point in the VF01 should I initiate this whole process?

So the my mind start to processing again. The answer to this might be using USER EXITS or Business Add-Ins (BADI). These two solutions seem to be the most absolute answer to the problem. However, when I revealed a solution at the end of this entry, you might find it with disbelief. But to the very few people who started with that solution was real good! Now, let me tell you what I had implemented initially to cater to that problem.

I went ahead to ST05 to get down all the USER EXITS and BADI from VF01 so I see which of them are more suitable to initiate this process. Doing so, I'd found one, it was XXXX. At this point, my imagination went beyond. Somehow, it is sometimes bad to venture too far from my own imagination. Because the next step I wanted to know how do I check the outbound IDOC's status from this USER EXIT XXX. It was simple, I used transparent table NAST and EDIDC to check the outbound IDOC's status. If its status are 03, 30 and XX, then it should go ahead to process the invoice convertion and IDOC send out. For the time being I'd solved 2 major problems.

Next, I need to get the latest invoice to do conversion. Unfortunately, with the current USER EXIT, I might not be able to get that SPOOL ID because it has not been created yet. VF01 has to be finished first. This pose another problem, how do I let VF01 finish off so I can get the SPOOL ID? After an overnight sleep, I decided that creating another RFC function module in the USER EXIT will do the trick. An RFC that executes with a new process created in the background. Thus, with this RFC initated as a new process run and letting the VF01 to finish processing, I can get the SPOOL ID.
Hence, I was definitely sure that my concept will surely work. However that will not work. Because of the RFC that i am using, it will cause overlapping. If you ever do my silly method, you will come across overlapping problem. RFC does not care if your PDF has been generated and sent by previoius document. It will just grab and resent everything including the new. Thus, my way does not work.

The only solution is to have the PDF converted, attached and sent from the print program. Not only does this eliminate duplicates of document but will ensure that it will not sent out duplicate copies of form due to overlapping. Printprogram should be any program that is used to process and display your SAPScript. For any standard program that prints forms, you can go to NACE to find out which program and form that it is using for print out. This way you also know the output type that is used by the standard program.

is sky the limit.... print, converting and sending...

SAP R/3 : Tracing Outbound IDOC

Troubleshooting outbound IDOCS can be very exciting and interesting activity. You get to see the wonders of sending data out of SAP to some other 3rd party systems. If you are unaware of some technicalities and behavorial of outbound IDOCS then testing it can be quite a challenge. Recently, I had this problem of trying to trace an outbound IDOC.

Previously, I could trace the outbound IDOC with minimal difficulty in WE19. If you put a break-point in your outbound process code or function module, the WE19 will stop at that point. But, what if WE19 fails to stop at that point? You will be scratching your head until you reach to a certain point you want to write an extra program just to trace the outbound IDOC. That is just what i did. Read my statement, I wrote an extra program to do that.

Though its a bit consuming but if you know which table and which fields to use then the concept will work just like the my now ever loving standard output type program RSNAST00. I shall have to thanks one person who let me know this existing program. But first, I would like to let you know what I'd gone through the latter method.

To developed an extra program to trace outbound programs is not as difficult as it seems. All you need is declare three tables i.e. NAST, EDIDC and EDID4. NAST is the output type control table that stores all of your 6 output types from printout to telefax. EDIDC is the IDOC control table. EDID4 is the IDOC data table. Therefore, you need to access the first table, NAST, in order to get the output type that you are supposed to execute. After you had obtain the necessary data from NAST, you will need to approach the EDIDC to get the DOCNUM and subsequently the EDID4 for its data. Then you pass all these three data selected data to your outbound's function module. Therefore, you can primitively test your outbound data. However, you will still need to set your output type to be scheduled run at other time.

Now, let us move on to life saving method to test your outbound IDOC or output types. In any of your standard programs that can send out IDOC, Telefax, Print out, set it to 1 (scheduled run at other time) in the FURTHER DATA section. Then you turn to RSNAST00 program where you put in your APPLICATION, OBJECT KEY, MEDIUM and OUTPUT TYPE. Before executing, put a break-point at your function module. Then you are ready to trace your outbound IDOC.

A note, the RSNAST00 does not only let you trace your outbound IDOC it is in fact a standard program that let you execute output types that you have schedule for later run. Hence, a very great thanks to Vincent Teoh from the SD (Sales and Distribution) module team. The RSNAST00 had definitely helped me a lot. Though I am still keeping my old program for reference. Concept still work very the same like RSNAST00.

is sky the limit... RSNAST00 and NAST, EDIDC, EDID4