Skip to Content

In one of our projects, one functionality was to post Audit messages to an external JMS service for all interfaces running through XI. We had a very large volume of data and planned to avoid a BPM. We therefore, decided to go ahead with using a JMS API to post the Audit messages to the JMS service.

One problem with this approach was what happens if the JMS service goes down?

As we were not using a BPM and were publishing the JMS message using the JMS API from within our mapping, we had 2 options when the JMS service was down.

1.Abort the entire process and thereby prevent a valid Business process from happening in XI.

2.Abort the JMS audit message and continue with the Business Process.

We decided to go with the 2nd approach, but we also wanted a mechanism to intimate the operations  support team that the JMS service was down.  If we had gone for a BPM, it would have been easy and simple to just use a Control Step to achieve this functionality. Since we were not using the BPM, we had to duplicate the functionality of the exception branch->control step of the BPM. We had to trigger Alerts from within our Message Mapping.

The Approach:

There is an RFC SALERT_CREATE which can be used to trigger Alerts (Thanks to Alessandro Guarneri for pointing me in the right direction and Anand Torgal for helping me understand this RFC module with his ABAP expertise.). So, perform an RFC Look Up using the LookUp API and call this RFC module to trigger the Alert from the UDF.

SALERT_CREATE:

The Function Module (RFC SALERT_CREATE) in SE37:

image

Input Parameters to the RFC:

1.IP_CAT – Alert Category created in ALRTCATDEF ( ALRTFRMWRKTEST)
2.IT_CONTAINER – This is used to fill up the Container Variables.

  • ELEMENT – The name of the container variable. (DOCNUMBER)
  • ELEMLENGTH – Length of the Element (250)
  • TYPE – Type of the Container variable ( C for character)
  • VALUE– Value to be passed. (12345)

image

The code in the User Defined Function:

We write the code to perform the RFC Look up, wherein we trigger the RFC SALERT_CREATE by using the RFC Look up API.

We brought down our JMS service and the Alert was triggered successfully, and the business flow of the interface continued without any hassles. The Container variables were filled up with the value provided in the UDF. (12345 in our case).

In real time, one can fill up all container variable values like Message ID, Sender Service , Receiver Service , etc and pass them to the Alert from the User Defined Function.

For info on how to get the values, http://help.sap.com/saphelp_nw04/helpdata/en/b3/9a2aeb24dc4ab6b1855c99157529e4/content.htm

image

To report this post you need to login first.

27 Comments

You must be Logged on to comment or reply to a post.

    1. Bhavesh Kantilal Post author
      Hi,
      We had an Audit Mechanism wherein we had to post a JMS message with details regarding the interface for every message passing through XI.
      This Audit was handled by another different module.

      BPM was ruled out due to a large volume  of data passing through XI.Due to the presence of IDOC adapter on the inbound side, Multi Mappingn was  not possible and so, we decided to go ahead using a JMS API.

      The example was just meant to be a starting point . The main purpose of this blog is to bring forward a means to trigger XI alerts from an user defined function.

      Regards,
      Bhavesh

      (0) 
  1. Gaurav Walia
    Hi Bhavesh

    Is it a good design to access JMS from UDF ? Especially when the message volume is large.

    To check if the JMS service is down, you send a JMS message and trap the exception raised by the JMS provider. Is this the best solutiom to the given problem ?

    You may like to rethink the approach if you are using this for one of your projects. Else, if this is proof of concept for raising alerts from a UDF, then its a job well done.

    Cheers,

    (0) 
    1. Bhavesh Kantilal Post author
      Gaurav,
      Thanks for the comments.
      I agree that design wise what we are doing ( using a JMS API ) is not the best approach. The best approach would’ve been to have a BPM , but , as I mentioned, we are expecting huge volumes of data and the data hit the XI box at the same time. So, multiple BPM’s clogging the memory would have been a serious perfromance bottleneck and hence this approach.

      This blog is just an attempt to highligh to the SDn community a means to trigger alerts from an UDF as and when the need arises.

      Regards,
      Bhavesh.

      (0) 
  2. RAJEEV GUPTA
    Hi Bhavesh,

    On executing the FM in SE37, the message which i gave in IT_CONTAINER table is not shown in alert message in alert inbox.

    Can you explain why this is not happening….

    Thanks,
    Rajeev Gupta

    (0) 
    1. Bhavesh Kantilal Post author
      Rajeev,
      Have you created the cotainer variable in your ALRTCATDEF? You need to use the container variable defined in your Alert Category.

      In the long text, the container variable will then be filled up with the value given in IT_CONTAINER.

      Regards,
      Bhavesh

      (0) 
      1. francis ma
        Hi Bhavesh,

        If we are using more than one container variable the value of which one will get substitued by the value given in IT_CONTAINER in the UDF?

        or instead of using the availble container variables in XI can we create a new one whose name we can specify in the IT_CONTAINER as element name? if its like that how many container variables we can specify i think the IT_CONTAINER can afford only one.

        thanks
        francis

        (0) 
  3. JAYANTH DORAISWAMY
    Hi,

      This is really a nice blog, but I need to achieve this same functionality synchronously whereas you have called the rfc asynchronously. Take your blog as an example, I need to retreive the alert id from the fm SALERT_CREATE once alert has been triggered. It would be really helpful if you send me the steps or code samples..

    Thanks,
    Jayanth

    (0) 
    1. Bhavesh Kantilal Post author
      Hi,
      Quite simple. Parse the RFC response and then collect the alert id.
      Append the following code to the code I have posted in my blog above.

      InputStream inp = rfcOutPayload.getContent();
           DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
           /* Create DOM structure from input XML */
           DocumentBuilder builder = factory.newDocumentBuilder();
           Document document = builder.parse(inp);
           /* Assuming EP_ALERT_ID is  the TAG in which the Alert Id is in the Response XML */
           NodeList list = document.getElementsByTagName(“EP_ALERT_ID”);
           Node node = list.item(0);
           if (node != null) {
                node = node.getFirstChild();
                if (node != null) {
                     String alertId = node.getNodeValue();
                }

      (0) 
    2. Bhavesh Kantilal Post author
      Hi,
      Quite simple. Parse the RFC response and then collect the alert id.
      Append the following code to the code I have posted in my blog above.

      InputStream inp = rfcOutPayload.getContent();
           DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();
           /* Create DOM structure from input XML */
           DocumentBuilder builder = factory.newDocumentBuilder();
           Document document = builder.parse(inp);
           /* Assuming EP_ALERT_ID is  the TAG in which the Alert Id is in the Response XML */
           NodeList list = document.getElementsByTagName(“EP_ALERT_ID”);
           Node node = list.item(0);
           if (node != null) {
                node = node.getFirstChild();
                if (node != null) {
                     String alertId = node.getNodeValue();
                }

      (0) 
  4. Aamir Suhail
    Excellant blog Bhavesh,congrats.
    i have a small question,is it possible with ur blog to dead stop the message transfer process.
    wat i mean to say is that suppose i have a simple File to File scenario and i want to abort any message transfer if invoice_number=0000000.
    i can use CreateIf function but even then it will atleast create a empty XML structure on receiver side(right?).i dont want any XML structure on receiver side if the condition is satisfied.
    is this possible?
    thanx
    Ahmad
    (0) 
    1. Bhavesh Kantilal Post author
      Hi Ahmad,
      There are multiple2 solutions to this problem,
      1. Use the UDF in my blog to trigger an alert and then throw a RunTimeException from your UDF.

      2. Use conditional Receiver Determination where you check is the field is not equal to that values and if yes the receievr is choosen else the message processing is stopped without error.

      3. Use a BPM.

      I woulse suggest that you explore option 2 before giving a chance to option 1 and 3.

      Regards
      Bhavesh

      (0) 
      1. Aamir Suhail
        Hey Bhavesh
        i tried second option and its givin me “receiver not found error” in MONI in case the terminate condition is satisfied.
        Looks like BPM is the only condition left,what do you think?
        thanx
        Ahmad
        (0) 
        1. Bhavesh Kantilal Post author
          Ahmad,
          Which SP are on? The option to determine ignore message without error is available in the receievr determination from SP 15 on XI 3.0 and SP 5 on PI 7.0.

          Regards
          Bhavesh

          (0) 
            1. Bhavesh Kantilal Post author
              In that case in your receiver determination you will have 3 options,

              1. Terminate Process with Error.
              2. Terminate Process without Error.
              3. Continue message processing with this Receiver..

              Select Option 2 and you will not get an error in MONI if there is no receiver found.

              Regards
              Bhavesh

              PS : Direct such questions to the XI forum for quick responses.

              (0) 
  5. Gopalkrishna Baliga
    Hi Bhavesh,

        Youe blog is very good. However I have one doubt. My Sender is JMS and receiver is a RFC adapter.

        Now I want to trigger an alert when RFC connection fails due to let us say the remote R/3 system is down.

        The problem is that I want the message title or subject to contain a dynamic parameter that is PIP number (I am sending Rosettenet PIP via JMS).

         I assume that in this case I have to call SALERT_CREATE in message mapping via Java UDF.

         So how to check for RFC connection failure in my UDF? In other words how to handle exception?

       Please help!

    Thanks
    Gopal

    (0) 
  6. ASHWIN KUMAR GUDURU VEERA
    Hi Bhavesh

    Thanks for the blog. Got some insight into how much we can do with alerts. I have set up three alert categories and within each of them used a resposibility rule to determine the recipients that should be intimated, based on actions. There is a button “process data flow” while defining the alert category properties and this points to a binding between two containers, the rule container and alert container…any idea on how that should be mapped..?

    Regards,
    ashwin

    (0) 
  7. Jorge Lopez
    Thanks for your blog Bhavesh,

    do you know of any option to suppress multiple alerts?

    For those “automatic” alerts created by PI and raised through a rule in the RWB there’s a checkbox called “Suppress Multiple Alerts of This Rule”, which is pretty useful if for example the remote system is down and you have 2000 messages failing there, thus 2000 alerts and 2000 mails 🙂

    – I’ve been looking at SALERT_CREATE_API, SALERT_CREATE_LOCAL, SALERT_CREATE_VIA_EVENT and some others, but it seems the option I’m looking for is not there.

    – Is custom programming and checking whatever table the only way to know first if there is already an existin alert not confirmed before calling SALERT_CREATE?

    Thanks!

    (0) 
    1. Bhavesh Kantilal Post author
      Jorge,
      Don’t think such a option exists 🙁
      Until we want to write custom functionality for an already custom functionality – it would be difficult setting.

      Regards,
      bhavesh

      (0) 
  8. Abhishek Srivastava
    Hello,

    I am trying to implement the logic in the blog. However I have some doubts:
    1) Should I import any RFC into SAP PI?
    2) Should I maintain the details of SAP PI in the RFC receiver channel (or any other system)?
    3) I want the UDF to execute whenever my mapping is executed. Do I need to pass any parameters to the UDF & will the UDF give out any output?

    Thanks.

    (0) 

Leave a Reply