10 Replies Latest reply: Oct 19, 2012 10:28 AM by Matthew Billingham RSS

dynamic method call over RFC function module

dominik langer
Currently Being Moderated

Hello!

this is my first post ever, so please be gentle with me

 

i have the following question:

i want to create a function module, which is RFC-able and all it should do is import the method name which i will call dynamically and the parameter table which is necessary to call the method with the correct parameters.

 

defining the method name as an importing parameter type string for the function module is possible, so whenever the user choses to e.g. press the button logon i will import the proper method name (e.g. LOGON).

2nd i need the parameters which is of type abap_parmbind_tab and here the system (in the SE37) cries that generic types are not allowed for RFC function modules and i have absoluteley no idea of how i can fix this matter.

 

so in short: is it in general possible to create such a RFC function module which will call dynamically the method + the correct parameters via abap_parmbind_tab?

 

thanks a lot in advance,

dominik

  • Re: dynamic method call over RFC function module
    Kumar Gaurav
    Currently Being Moderated

    Hi Dominik,

    I really liked your idea

     

    I think in your case it won't be possible to include abap_parmbind_tab type parameters.

    VALUE of the type REF TO DATA. And references are not allowed in RFC FMs.

     

    What I think can be done.

    1) get the list of all the methods which are wrapping in the RFC FM.

    2) add all the parameter of all the method in you FM interface ( Nor referecne type )

    3) In the FM based on the FM name passed populate the local variables ABAP_PARMBIND_TAB and make the dynamic call

    More on this here

    http://help.sap.com/saphelp_nw70/helpdata/en/08/d27c03b81011d194f60000e8353423/content.htm

  • Re: dynamic method call over RFC function module
    Matthew Billingham
    Currently Being Moderated

    I've done exactly what you required, and encountered the same problem. To resolve it I converted the value into hexadecimal before calling the RFC. Within the RFC, I convert the hex value back to whatever type the parameter requires.

    • Re: dynamic method call over RFC function module
      Matthew Billingham
      Currently Being Moderated

      I was wrong. This is what you need: cl_abap_container_utilities=>fill_container_c

      It returns a string, and then you have to convert that into a table of fixed length characters, so you can rebuild the string at the other end, and then use read_container_c to recover that data. Which could even be a structure or a table..

      • Re: dynamic method call over RFC function module
        Suhas Saha
        Currently Being Moderated

        Hello,

        I think this is a problem every developer has to face when he/she tries to use dynamic elements with RFC!

        Matthew Billingham wrote:

          ... you have to convert that into a table of fixed length characters, so you can rebuild the string at the other end ...

        Imo defining the return table of "fixed length characters" will always be a problem - something i faced a few weeks back

        BR,

        Suhas

        • Re: dynamic method call over RFC function module
          Matthew Billingham
          Currently Being Moderated

          Not a problem.

          You've converted your data into a string. You cut the string into, say, 256 character portions, so it'll fit into a table of CHAR256. For the last slice, you record how many bytes of the field are actually used.

          I.e. assume your string is 'abcdefghijklm', and your table is CHAR8. Then you end up with

          abcdefgh

          ijklm

          To recover the string, you just need the table with these chars, and 5, so you get the length of the string right. This is pretty much the same as what's done for sending binary data as MIME.

          Believe me, it works - I've done it! (I should say that using cl_abap_container_utilities was Otto Gold's idea.).

          matt

          • Re: dynamic method call over RFC function module
            Otto Gold
            Currently Being Moderated

            Hi Matthew Billingham, friends,

            I am afraid that I must confirm the problem with the fixed length. I learnt the hard way (one of the tools I`ve built does not work over RFC at one of our customers despite the fact it worked just fine on my internal systems). I am researching the problem now and to me the XML option (CALL TRANSFORMATION ID) sounds like the best thing we can do.

            I am sorry for misleading recommendation, Matt, the container operation thing is not safe.

            Hope this helps other people too, I have seen tons of questions about the topic in last hours.

             

            For further information about the XML option I recommend Durairaj Athavan Raja and the contribution and the feedback thread:

            http://scn.sap.com/thread/53916

            http://scn.sap.com/docs/DOC-10106

             

            I haven`t tested it in production environment yet, but originally used the string container for "any structure" and some structures just didn`t work out.

            Cheers Otto

            • Re: dynamic method call over RFC function module
              Matthew Billingham
              Currently Being Moderated

              So why doesn't it work at your customer? I've used the same technique with one of my clients and it is fine. I'm taking a standard table with records comprising flat fields. I don't know its structure until runttime, but need to pass the data to an RFC FM (along with the typing information).

               

              I've a container structure defined in the data dictionary:

              RECORD_NUMBER      INT4

              COMPONENT_NUMBER   INT4

              CHAR_REC_NUMBER    INT4

              CHAR_DATA          CHAR255

              RECORD_LENGTH      INT4

               

              Then I use this code where <t_data> is a generic table and <s_data> is type any, but is a non-deep structure:

              ls_container is type the container structure, and lt_container is a standard table of it.

               

              * Convert each line to a string, then convert into the container format
                LOOP AT <t_data> ASSIGNING <s_data>.
                  ls_container-record_number = sy-tabix.
                  DO.
                    ls_container-component_number = sy-index.

                    ASSIGN COMPONENT ls_container-component_number OF STRUCTURE <s_data> TO <field>.
                    IF sy-subrc IS NOT INITIAL.
                      EXIT.
                    ENDIF.
                    cl_abap_container_utilities=>fill_container_c( EXPORTING im_value = <field> IMPORTING ex_container = l_converted ).

                    DO.
                      ls_container-char_rec_number = sy-index.
                      l_len = STRLEN( l_converted ).
                      IF l_len LT c_container_width.
                        ls_container-record_length = l_len.
                        ls_container-char_data = l_converted.
                        INSERT ls_container INTO TABLE lt_container.
                        EXIT.
                      ENDIF.

                      ls_container-record_length = c_container_width.
                      ls_container-char_data = l_converted(c_container_width).
                      INSERT ls_container INTO TABLE lt_container.

                      l_converted = l_converted+c_container_width.
                      IF l_converted IS INITIAL.
                        EXIT.
                      ENDIF.
                    ENDDO.
                  ENDDO.
                ENDLOOP.

               

              At the receiving end, I decode it_data - which is my table of the container structure type. l_record is a string.

               

              * Convert the data from the interface into the right format
                sort it_data by record_number component_number char_rec_number.
                loop at it_data into ls_data.
                  if ls_data-record_length gt 0.
                    concatenate l_record ls_data-char_data(ls_data-record_length) into l_record.
                  endif.

                  at end of component_number. " New component
                    assign component ls_data-component_number of structure <s_outdata> to <field>.
                    cl_abap_container_utilities=>read_container_c( exporting im_container = l_record
                                                                   importing ex_value = <field> ).
                    clear l_record.
                  endat.

                  at end of record_number.
                    insert <s_outdata> into table <t_outdata>.
                  endat.

                endloop.

               

              <t_outdata> is a table of the same structure as <t_data>. (likewise <s_outdata> and <s_data> ).

               

  • Re: dynamic method call over RFC function module
    dominik langer
    Currently Being Moderated

    just wanted to finish my thread off. maybe it is helpful for others.

    what we have done is following:

    • created a RFC FM.
    • only purpose is to pass the import parameters through to another FM which is representing our 'Main' Function.
    • there we unwrap our import parameters and call the proper methods.

     

    it may sound a little bit 'dirty' but a big advantage is that we do not have to deploy the RFC all the time whenever we change something in it.

     

    i do not know how much performance we will lose with this - if you are interested i can set up some measurements (which i will be able to do in 2 weeks).

    • Re: dynamic method call over RFC function module
      Venkat Gowrishankar
      Currently Being Moderated

      Hello Dominik,

       

      I know its not nice to  re open a closed discussion. But,  since you are calling methods dynamically and your RFC is generic, how would you handle object instantiation?. Some objects might implement a singleton, others may not, would this not be an issue?.

       

      Please do correct me if I am getting wrong somewhere.

       

      Thanks,

      Venkat.

      • Re: dynamic method call over RFC function module
        Venkat Gowrishankar
        Currently Being Moderated

        only purpose is to pass the import parameters through to another FM which is representing our 'Main' Function.

         

        Ok , So I missed this point. So you would be creating another FM where the actual object instantiation and the method call would happen. This FM would be application specific I would assume. It would be more like "An Object - message interface".- Sort of theoretical OO programming,  where Objects listen and react to messages

         

         

        Thanks,

        Venkat.

Actions