Additional Blogs by SAP
cancel
Showing results for 
Search instead for 
Did you mean: 
former_member182779
Active Contributor

Yesterday...I was browsing another ABAP forum...Yeah..Shame on me -:( I browser another forums...It's was an Spanish forum by the way. Anyway, some guy tell us that he wanted to develop an "Dynamic INNER Join Function Module"...Of course, I was up to the challenge, an after some headaches and some Rich Heilman (http://tinyurl.com/y9akb5)'s posts...I came with this -:)


Dynamic_Inner_Join

FUNCTION zdynamic_inner_join.

*"----------------------------------------------------------------------

*"*"Interfase local

*"  IMPORTING

*"     VALUE(TAB1) TYPE  DD02L-TABNAME

*"     VALUE(TAB2) TYPE  DD02L-TABNAME

*"  TABLES

*"      FILTER STRUCTURE  RFC_DB_OPT

*"      WHERE_TABLE STRUCTURE  RFC_DB_OPT

*"      DATA STRUCTURE  TAB512

*"  EXCEPTIONS

*"      NOT_TABLE

*"----------------------------------------------------------------------

  DATA: descr_struct_ref TYPE REF TO cl_abap_structdescr,

        wa_fcat TYPE lvc_s_fcat,

        it_fieldcatalog TYPE lvc_t_fcat,

        dataref TYPE REF TO data,

        my_tab LIKE dd02l-tabname,

        tabname TYPE dd03l-tabname,

        fieldname TYPE dd03l-fieldname,

        position TYPE dd03l-position,

        inttype TYPE dd03l-inttype,

        tab_one TYPE string,

        tab_two TYPE string,

        campos TYPE string,

        inner_field TYPE string,

        where_condition TYPE string,

        where_string TYPE string,

        condition_one TYPE string,

        condition_two TYPE string,

        field TYPE string,

        l_date_extern(30) TYPE c,

        w_tabix TYPE sy-tabix,

        field_one TYPE string,

        field_two TYPE string,

        field_three TYPE string.

  DATA: BEGIN OF fields OCCURS 0,

        field TYPE dd03l-fieldname,

        END OF fields.

  DATA: BEGIN OF fields_box OCCURS 0,

        field TYPE dd03l-fieldname,

        END OF fields_box.

  DATA: BEGIN OF global_fields OCCURS 0,

        field TYPE dd03l-fieldname,

        END OF global_fields.

  DATA: fieldsym  TYPE TABLE OF rfieldlist WITH HEADER LINE,

        fieldlist TYPE TABLE OF rstrucinfo WITH HEADER LINE.

  TYPES: BEGIN OF type_data,

         data TYPE crmch4000,

         END OF type_data.

  DATA:  data_line TYPE type_data.

  DATA: fieldnames LIKE fieldlist-compname,

        l_type.

  FIELD-SYMBOLS: <row> TYPE ANY TABLE,

                 <fs_table> TYPE LINE OF lvc_t_fcat,

                 <table> TYPE STANDARD TABLE,

                 <aux_table> TYPE STANDARD TABLE,

                 <component> TYPE abap_compdescr,

                 <fs>  TYPE ANY,

                 <fs1> TYPE ANY.

  CREATE DATA dataref TYPE char3000.

  IF tab1 EQ space.

    RAISE not_table.

  ENDIF.

  tab_one = tab1.

  TRANSLATE tab_one TO UPPER CASE.

  SELECT tabname fieldname position inttype

  INTO (tabname,fieldname,position,inttype)

  FROM dd03l

  WHERE tabname EQ tab_one

  ORDER BY position.

    wa_fcat-fieldname     = fieldname.

    wa_fcat-ref_table     = tabname.

    wa_fcat-ref_field     = fieldname.

    wa_fcat-inttype       = inttype.

    fields_box-field = fieldname.

    APPEND wa_fcat TO it_fieldcatalog.

    APPEND fields_box.

  ENDSELECT.

  IF tab2 EQ space.

    RAISE not_table.

  ENDIF.

  tab_two = tab2.

  TRANSLATE tab_two TO UPPER CASE.

  SELECT tabname fieldname position inttype

  INTO (tabname,fieldname,position,inttype)

  FROM dd03l

  WHERE tabname EQ tab_two

  ORDER BY position.

    wa_fcat-fieldname     = fieldname.

    wa_fcat-ref_table     = tabname.

    wa_fcat-ref_field     = fieldname.

    wa_fcat-inttype       = inttype.

    READ TABLE it_fieldcatalog WITH KEY fieldname = wa_fcat-fieldname

    ASSIGNING <fs_table>.

    IF sy-subrc EQ 0.

      fields-field = wa_fcat-fieldname.

      APPEND fields.

    ELSE.

      fields_box-field = fieldname.

      APPEND wa_fcat TO it_fieldcatalog.

      APPEND fields_box.

    ENDIF.

  ENDSELECT.

  IF NOT filter[] IS INITIAL.

    LOOP AT fields_box.

      w_tabix = sy-tabix.

      READ TABLE filter WITH KEY text = fields_box-field.

      IF sy-subrc NE 0.

        DELETE fields_box INDEX w_tabix.

      ENDIF.

    ENDLOOP.

  ENDIF.

  global_fields[] = fields_box[].

  CALL METHOD cl_alv_table_create=>create_dynamic_table

    EXPORTING

      it_fieldcatalog           = it_fieldcatalog

    IMPORTING

      ep_table                  = dataref

    EXCEPTIONS

      generate_subpool_dir_full = 1

      OTHERS                    = 2.

  ASSIGN dataref->* TO <row>.

  LOOP AT fields.

    DELETE fields_box WHERE field EQ fields-field.

    CONCATENATE tab_one '~' fields-field

    INTO inner_field.

    CONCATENATE campos inner_field

    INTO campos SEPARATED BY space.

  ENDLOOP.

  LOOP AT fields_box.

    CONCATENATE campos fields_box-field

    INTO campos SEPARATED BY space.

  ENDLOOP.

  CONCATENATE '(' tab1 'inner join' tab2 'ON'

  INTO where_condition SEPARATED BY space.

  LOOP AT fields.

    CONCATENATE tab_one '~' fields-field

    INTO condition_one.

    CONCATENATE tab_two '~' fields-field

    INTO condition_two.

    CONCATENATE where_condition condition_one 'EQ'

    condition_two 'AND' INTO where_condition

    SEPARATED BY space.

  ENDLOOP.

  SHIFT where_condition RIGHT DELETING TRAILING 'AND'.

  CONDENSE where_condition.

  CONCATENATE where_condition ')'

  INTO where_condition

  SEPARATED BY space.

  IF NOT where_table[] IS INITIAL.

    LOOP AT where_table.

      SPLIT where_table-text AT space

      INTO field_one field_two field_three.

      READ TABLE fields WITH KEY field =  field_one.

      IF sy-subrc EQ 0.

        CONCATENATE tab1 '~' where_table-text

        INTO where_table-text.

      ENDIF.

      CONCATENATE where_string where_table-text 'AND'

      INTO where_string SEPARATED BY space.

    ENDLOOP.

  ENDIF.

  SHIFT where_string RIGHT DELETING TRAILING 'AND'.

  CONDENSE where_string.

  IF where_string NE space.

    SELECT (campos)

    INTO CORRESPONDING FIELDS OF TABLE <row>

    FROM (where_condition)

    WHERE (where_string).

  ELSE.

    SELECT (campos)

    INTO CORRESPONDING FIELDS OF TABLE <row>

    FROM (where_condition).

  ENDIF.

  ASSIGN <row> TO <table>.

  LOOP AT <table> ASSIGNING <fs>.

    LOOP AT global_fields.

      fieldnames = global_fields-field.

      ASSIGN COMPONENT fieldnames OF STRUCTURE <fs> TO <fs1>.

      DESCRIBE FIELD <fs1> TYPE l_type.

      IF l_type EQ 'I' OR l_type EQ 'b'.

        field = <fs1>.

        CONCATENATE data_line field INTO data_line

        SEPARATED BY '/'.

      ELSEIF l_type EQ 'P'.

        WRITE <fs1> TO l_date_extern.

        CONCATENATE data_line l_date_extern INTO data_line

        SEPARATED BY '/'.

      ELSEIF l_type EQ 'D'.

        CALL FUNCTION 'CONVERT_DATE_TO_EXTERNAL'

          EXPORTING

            date_internal = <fs1>

          IMPORTING

            date_external = l_date_extern

          EXCEPTIONS

            OTHERS        = 4.

        IF sy-subrc EQ 0.

          CONCATENATE data_line l_date_extern INTO data_line

          SEPARATED BY '/'.

        ENDIF.

      ELSE.

        CONCATENATE data_line <fs1> INTO data_line

        SEPARATED BY '/'.

      ENDIF.

      SHIFT data_line LEFT DELETING LEADING '/'.

      SHIFT data_line RIGHT DELETING TRAILING '/'.

    ENDLOOP.

    APPEND data_line TO data.

    CLEAR data_line.

  ENDLOOP.

ENDFUNCTION.

6 Comments