You are on page 1of 11

*&---------------------------------------------------------------------*

*& Report YDR_TABLE_UPDATE


*&
*&---------------------------------------------------------------------*
*&
*&
*&---------------------------------------------------------------------*

REPORT ydr_table_update.

FIELD-SYMBOLS: <fs_table> TYPE STANDARD TABLE ##NEEDED,


<fs_struc> TYPE any ##NEEDED,
<fs_1> TYPE any ##NEEDED,
<fs_2> TYPE any ##NEEDED.

CONSTANTS : gc_s TYPE c VALUE 'S',


gc_e TYPE c VALUE 'E',
gc_eq TYPE string VALUE 'EQ'.

SELECTION-SCREEN : BEGIN OF BLOCK main WITH FRAME TITLE text-scr.


PARAMETERS : p_fpath TYPE ibipparms-path,
p_table TYPE tabname,
p_mode TYPE damodus.
* p_intr TYPE i.
SELECTION-SCREEN : END OF BLOCK main.

**--At Selection Screen


AT SELECTION-SCREEN ON VALUE-REQUEST FOR p_fpath.
"F4-Help to browse file path
PERFORM f4_filename.

START-OF-SELECTION.
"Start Processing
PERFORM start_processing.

*&---------------------------------------------------------------------*
*& Form F4_FILENAME
*&---------------------------------------------------------------------*
* F4 filename search help
*----------------------------------------------------------------------*
FORM f4_filename.

DATA: lv_rc TYPE i,


lt_ftab TYPE filetable.

* CONSTANTS : lc_window TYPE string VALUE 'Select a file'.

"F4 help for filename


CALL METHOD cl_gui_frontend_services=>file_open_dialog
* EXPORTING
* window_title = lc_window
* default_extension =
* default_filename =
* file_filter =
* with_encoding =
* initial_directory =
* multiselection =
CHANGING
file_table = lt_ftab
rc = lv_rc
EXCEPTIONS
file_open_dialog_failed = 1
cntl_error = 2
error_no_gui = 3
not_supported_by_gui = 4
OTHERS = 5.
IF sy-subrc EQ 0.
READ TABLE lt_ftab ASSIGNING FIELD-SYMBOL(<fs_file>) INDEX 1.
IF sy-subrc EQ 0.
p_fpath = <fs_file>-filename.
ENDIF.
ENDIF.

IF p_fpath IS INITIAL.
"'Unable to fetch file path'
MESSAGE text-fpt TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.

ENDFORM. " F4_FILENAME

*&---------------------------------------------------------------------*
*& Form START_PROCESSING
*&---------------------------------------------------------------------*
* Start Processing
*----------------------------------------------------------------------*
FORM start_processing .

DATA : lt_dftab TYPE STANDARD TABLE OF dd03p,


lt_dyntab TYPE REF TO data,
lw_dyntab TYPE REF TO data,
lv_eflag TYPE boolean.

"Validate Table Name


PERFORM validate_table_name.

"Create Dynamic table and structure


PERFORM create_dyntab CHANGING lt_dftab
lt_dyntab.

IF lt_dyntab IS BOUND AND


lt_dyntab IS NOT INITIAL.
ASSIGN lt_dyntab->* TO <fs_table>.
CREATE DATA lw_dyntab LIKE LINE OF <fs_table>.
ASSIGN lw_dyntab->* TO <fs_struc>.

PERFORM convert_excel USING lt_dftab.

IF <fs_table> IS ASSIGNED AND


<fs_table> IS NOT INITIAL.
SORT <fs_table>.
PERFORM table_action USING lt_dftab
CHANGING <fs_table>
lv_eflag.
IF lv_eflag IS NOT INITIAL.
ROLLBACK WORK.
"'Unable to perform table action'
MESSAGE text-upt TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.
ENDIF.
ENDIF.
ENDFORM. " START_PROCESSING

*&---------------------------------------------------------------------*
*& Form VALIDATE_TABLE_NAME
*&---------------------------------------------------------------------*
* Validate Table Name
*----------------------------------------------------------------------*
FORM validate_table_name .

DATA : lv_tabname TYPE tabname.

CONSTANTS : lc_act TYPE c VALUE 'A',


lc_ver TYPE as4vers VALUE '0000'.

SELECT SINGLE tabname


FROM dd02l
INTO lv_tabname
WHERE tabname EQ p_table
AND as4local EQ lc_act
AND as4vers EQ lc_ver.
IF sy-subrc NE 0 OR
lv_tabname IS INITIAL.
"'Invalid Table name'
MESSAGE text-ifn TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.

ENDFORM. " VALIDATE_TABLE_NAME

*&---------------------------------------------------------------------*
*& Form CREATE_DYNTAB
*&---------------------------------------------------------------------*
* Create Dynamic table and structures
*----------------------------------------------------------------------*
FORM create_dyntab CHANGING y_dftab TYPE dd03ptab
y_dyntab TYPE REF TO data.

DATA : lt_fieldcat TYPE lvc_t_fcat.

CALL FUNCTION 'DDIF_TABL_GET'


EXPORTING
name = p_table
* STATE = 'A'
* LANGU = ' '
* IMPORTING
* GOTSTATE =
* DD02V_WA =
* DD09L_WA =
TABLES
dd03p_tab = y_dftab
* DD05M_TAB =
* DD08V_TAB =
* DD12V_TAB =
* DD17V_TAB =
* DD35V_TAB =
* DD36M_TAB =
EXCEPTIONS
illegal_input = 1
OTHERS = 2.
IF sy-subrc EQ 0.
SORT y_dftab BY position.
LOOP AT y_dftab ASSIGNING FIELD-SYMBOL(<fs_dftab>).
APPEND INITIAL LINE TO lt_fieldcat ASSIGNING FIELD-SYMBOL(<fs_fieldcat>).
CASE <fs_dftab>-inttype.
WHEN 'C'.
<fs_fieldcat>-datatype = 'CHAR'.
WHEN 'N'.
<fs_fieldcat>-datatype = 'NUMC'.
WHEN 'D'.
<fs_fieldcat>-datatype = 'DATE'.
WHEN 'P'.
<fs_fieldcat>-datatype = 'PACK'.
WHEN OTHERS.
<fs_fieldcat>-datatype = <fs_dftab>-datatype.
ENDCASE.
<fs_fieldcat>-tabname = p_table.
<fs_fieldcat>-fieldname = <fs_dftab>-fieldname.
<fs_fieldcat>-inttype = <fs_dftab>-inttype.
<fs_fieldcat>-intlen = <fs_dftab>-intlen.
<fs_fieldcat>-decimals = <fs_dftab>-decimals.
UNASSIGN : <fs_fieldcat>.
ENDLOOP.
ELSE.
"'Unable to create dynamic table'
MESSAGE text-ucd TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.

IF lt_fieldcat IS NOT INITIAL.


CALL METHOD cl_alv_table_create=>create_dynamic_table
EXPORTING
* i_style_table =
it_fieldcatalog = lt_fieldcat
i_length_in_byte = abap_true
IMPORTING
ep_table = y_dyntab
* e_style_fname =
EXCEPTIONS
generate_subpool_dir_full = 1
OTHERS = 2.
IF sy-subrc NE 0.
"'Unable to create dynamic table'
MESSAGE text-ucd TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.
ENDIF.

ENDFORM. " CREATE_DYNTAB

*&---------------------------------------------------------------------*
*& Form CONVERT_EXCEL
*&---------------------------------------------------------------------*
* Convert Excel to Internal Table
*----------------------------------------------------------------------*
FORM convert_excel USING x_dftab TYPE dd03ptab.

DATA : lt_ttab TYPE STANDARD TABLE OF alsmex_tabline,


lt_ttmp TYPE STANDARD TABLE OF alsmex_tabline.

"Declaration of global constants


CONSTANTS : lc_1 TYPE i VALUE 1,
lc_cmax TYPE i VALUE 256,
lc_rmax TYPE i VALUE 100000.

"Convert excel to internal table


CALL FUNCTION 'ALSM_EXCEL_TO_INTERNAL_TABLE'
EXPORTING
filename = p_fpath
i_begin_col = lc_1
i_begin_row = lc_1
i_end_col = lc_cmax
i_end_row = lc_rmax
TABLES
intern = lt_ttab
EXCEPTIONS
inconsistent_parameters = 1
upload_ole = 2
OTHERS = 3.
IF sy-subrc EQ 0.
SORT lt_ttab BY row col.
lt_ttmp[] = lt_ttab[].
DELETE ADJACENT DUPLICATES FROM lt_ttmp COMPARING row.

LOOP AT lt_ttmp ASSIGNING FIELD-SYMBOL(<fs_row>).


READ TABLE lt_ttab TRANSPORTING NO FIELDS
WITH KEY row = <fs_row>-row BINARY SEARCH.
IF sy-subrc EQ 0.
LOOP AT lt_ttab ASSIGNING FIELD-SYMBOL(<fs_col>)
FROM sy-tabix.
IF <fs_col>-row NE <fs_row>-row.
EXIT.
ENDIF.
READ TABLE x_dftab ASSIGNING FIELD-SYMBOL(<fs_dftab>)
WITH KEY position = <fs_col>-col BINARY SEARCH.
IF sy-subrc EQ 0.
IF p_mode EQ 'D' AND
<fs_dftab>-keyflag IS INITIAL.
CONTINUE.
ENDIF.
PERFORM populate_final_table USING <fs_col>
<fs_dftab>
CHANGING <fs_struc>.
ENDIF.
ENDLOOP.
APPEND <fs_struc> TO <fs_table>.
CLEAR : <fs_struc>.
ENDIF.
ENDLOOP.
ELSE.
"'Unable to read excel file'
MESSAGE text-ure TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.

ENDFORM. " CONVERT_EXCEL

*&---------------------------------------------------------------------*
*& Form POPULATE_FINAL_TABLE
*&---------------------------------------------------------------------*
* Populate Final Table
*----------------------------------------------------------------------*
FORM populate_final_table USING x_col TYPE alsmex_tabline
x_dftab TYPE dd03p
CHANGING x_struc TYPE any.

CONSTANTS : lc_erdat TYPE name_feld VALUE 'ERDAT',


lc_ernam TYPE name_feld VALUE 'ERNAM',
lc_aedat TYPE name_feld VALUE 'AEDAT',
lc_aenam TYPE name_feld VALUE 'AENAM',
lc_ertim TYPE name_feld VALUE 'ERTIM',
lc_aetim TYPE name_feld VALUE 'AETIM',
lc_mandt TYPE name_feld VALUE 'MANDT',
lc_change_tim TYPE name_feld VALUE 'CHANGE_TIME',
lc_value TYPE name_feld VALUE 'VALUE'.

ASSIGN COMPONENT lc_value OF STRUCTURE x_col TO <fs_1>.


ASSIGN COMPONENT x_dftab-fieldname OF STRUCTURE x_struc TO <fs_2>.

CASE x_dftab-inttype.
WHEN 'D'.
IF ( <fs_1> IS INITIAL AND
x_dftab-fieldname EQ lc_erdat ) OR
x_dftab-fieldname EQ lc_aedat.
<fs_2> = sy-datum.
ELSE.
<fs_2> = <fs_1>+6(4) && <fs_1>+3(2) && <fs_1>+0(2).
ENDIF.
* CALL FUNCTION 'DATE_CHECK_PLAUSIBILITY'
* EXPORTING
* date = <fs_2>
* EXCEPTIONS
* plausibility_check_failed = 1
* OTHERS = 2.
* IF sy-subrc NE 0.
* <fs_2> = sy-datum.
* ENDIF.
WHEN 'T'.
IF x_dftab-fieldname EQ lc_aetim OR
x_dftab-fieldname EQ lc_change_tim OR
( <fs_1> IS INITIAL AND
x_dftab-fieldname EQ lc_ertim ).
<fs_2> = sy-uzeit.
ELSE.
<fs_2> = <fs_1>+0(2) && <fs_1>+3(2) && <fs_1>+6(2) .
CALL FUNCTION 'TIME_CHECK_PLAUSIBILITY'
EXPORTING
time = <fs_2>
EXCEPTIONS
plausibility_check_failed = 1
OTHERS = 2.
IF sy-subrc NE 0.
<fs_2> = sy-uzeit.
ENDIF.
ENDIF.
WHEN 'C'.
IF x_dftab-fieldname EQ lc_aenam OR
( x_dftab-fieldname EQ lc_ernam AND
<fs_1> IS INITIAL ).
<fs_2> = sy-uname.
ELSEIF x_dftab-fieldname EQ lc_mandt.
<fs_2> = sy-mandt.
ELSE.
<fs_2> = <fs_1>.
ENDIF.
WHEN OTHERS.
<fs_2> = <fs_1>.
ENDCASE.

ENDFORM. " POPULATE_FINAL_TABLE

*&---------------------------------------------------------------------*
*& Form TABLE_ACTION
*&---------------------------------------------------------------------*
* Table Actions
*----------------------------------------------------------------------*
FORM table_action USING x_dftab TYPE dd03ptab
CHANGING y_tabdata TYPE ANY TABLE
y_eflag TYPE boolean.

DATA : lt_tabdata TYPE REF TO data,


lt_tfields TYPE dd03ptab,

lt_where TYPE TABLE OF edpline,


lw_where TYPE edpline,

lv_string TYPE string,


lv_count TYPE i.

*** lv_ref_tabname TYPE REF TO cl_abap_structdescr,


*** lv_ref_table TYPE REF TO cl_abap_structdescr.

FIELD-SYMBOLS : <fs_tabdata> TYPE ANY TABLE.

CONSTANTS : lc_mandt TYPE name_feld VALUE 'MANDT',


lc_hyphen TYPE c VALUE '-',
lc_tmptab TYPE string VALUE 'Y_TABDATA',
lc_and TYPE string VALUE 'AND'.

CREATE DATA lt_tabdata TYPE TABLE OF (p_table).


ASSIGN lt_tabdata->* TO <fs_tabdata>.
* <fs_tabdata> = Y_TABDATA.

IF x_dftab IS NOT INITIAL.


lt_tfields[] = x_dftab[].
ENDIF.

*---INSERT Operation for one or more records into Database Table


IF p_mode = zif_x_common_types_and_const=>gc_mode_insert.

LOOP AT x_dftab ASSIGNING FIELD-SYMBOL(<fs_dftab>)


WHERE keyflag EQ abap_true
AND fieldname NE lc_mandt.
CLEAR : lw_where, lv_string.

CONCATENATE lc_tmptab lc_hyphen <fs_dftab>-fieldname INTO lv_string.

IF lv_count IS INITIAL.
"'FIELDNAME EQ Y_TABDATA-FIELDNAME'
CONCATENATE <fs_dftab>-fieldname gc_eq lv_string
INTO lw_where SEPARATED BY space.
ELSE.
"'AND FIELDNAME EQ Y_TABDATA-FIELDNAME'
CONCATENATE lc_and <fs_dftab>-fieldname gc_eq lv_string
INTO lw_where SEPARATED BY space.
ENDIF.

lv_count = lv_count + 1.
APPEND lw_where TO lt_where.

ENDLOOP.

SELECT *
FROM (p_table)
INTO TABLE <fs_tabdata>
FOR ALL ENTRIES IN y_tabdata
WHERE (lt_where).
IF sy-subrc EQ 0.
IF 1 = 2.
* LOOP AT y_tabdata ASSIGNING FIELD-SYMBOL(<fs_tdata>).
* READ TABLE <fs_tdata> TRANSPORTING NO FIELDS
* WITH TABLE KEY
* ENDLOOP.
ENDIF.
PERFORM user_decision USING y_tabdata
CHANGING lt_tfields
y_eflag.
ELSE.
INSERT (p_table) FROM TABLE y_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
y_eflag = abap_true.
ENDIF.
ENDIF.
*---UPDATE Operation for one or more records into Database Table
ELSEIF p_mode = zif_x_common_types_and_const=>gc_mode_update.
PERFORM enqueue USING y_tabdata
CHANGING lt_tfields.
UPDATE (p_table) FROM TABLE y_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
y_eflag = abap_true.
ENDIF.
PERFORM dequeue USING y_tabdata
lt_tfields.
*---MODIFY Operation for one or more records into Database Table
ELSEIF p_mode = zif_x_common_types_and_const=>gc_mode_modify.
PERFORM enqueue USING y_tabdata
CHANGING lt_tfields.
MODIFY (p_table) FROM TABLE y_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
y_eflag = abap_true.
ENDIF.
PERFORM dequeue USING y_tabdata
lt_tfields.
*---DELETE Operation for one or more records into Database Table
ELSEIF p_mode = zif_x_common_types_and_const=>gc_mode_delete.
PERFORM enqueue USING y_tabdata
CHANGING lt_tfields.
DELETE (p_table) FROM TABLE y_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
y_eflag = abap_true.
ENDIF.
PERFORM dequeue USING y_tabdata
lt_tfields.
ENDIF.

ENDFORM. " TABLE_ACTION

*&---------------------------------------------------------------------*
*& Form ENQUEUE
*&---------------------------------------------------------------------*
* Enqueue Table Data
*----------------------------------------------------------------------*
FORM enqueue USING x_tabdata TYPE ANY TABLE
CHANGING y_tfields TYPE dd03ptab.

DATA : lv_varkey TYPE vim_enqkey,


lv_string TYPE string.

DELETE y_tfields WHERE keyflag IS INITIAL.


SORT y_tfields BY position.

LOOP AT x_tabdata ASSIGNING FIELD-SYMBOL(<fs_record>).


DO lines( y_tfields[] ) TIMES.
ASSIGN COMPONENT sy-index OF STRUCTURE <fs_record> TO FIELD-SYMBOL(<fs_varkey>).
lv_string = <fs_varkey>.
lv_varkey = lv_varkey && lv_string.
ENDDO.
CALL FUNCTION 'ENQUEUE_E_TABLEE'
EXPORTING
mode_rstable = gc_e
tabname = p_table
varkey = lv_varkey
_wait = abap_true
_collect = abap_true
EXCEPTIONS
foreign_lock = 1
system_failure = 2
OTHERS = 3.
IF sy-subrc EQ 0.
CLEAR : lv_varkey.
ENDIF.
ENDLOOP.

ENDFORM. " ENQUEUE

*&---------------------------------------------------------------------*
*& Form DEQUEUE
*&---------------------------------------------------------------------*
* Dequeue table data
*----------------------------------------------------------------------*
FORM dequeue USING x_tabdata TYPE ANY TABLE
x_tfields TYPE dd03ptab.

DATA : lv_varkey TYPE vim_enqkey,


lv_string TYPE string.

LOOP AT x_tabdata ASSIGNING FIELD-SYMBOL(<fs_record>).


CLEAR : lv_varkey.
DO lines( x_tfields[] ) TIMES.
ASSIGN COMPONENT sy-index OF STRUCTURE <fs_record> TO FIELD-SYMBOL(<fs_varkey>).
lv_string = <fs_varkey>.
lv_varkey = lv_varkey && lv_string.
ENDDO.
CALL FUNCTION 'DEQUEUE_E_TABLEE'
EXPORTING
mode_rstable = gc_e
tabname = p_table
varkey = lv_varkey
_collect = abap_true.
ENDLOOP.

ENDFORM. " DEQUEUE

*&---------------------------------------------------------------------*
*& Form USER_DECISION
*&---------------------------------------------------------------------*
* User Decision to proceed if records to are already present
*----------------------------------------------------------------------*
FORM user_decision USING x_tabdata TYPE ANY TABLE
CHANGING y_tfields TYPE dd03ptab
y_eflag TYPE boolean.

DATA : lt_spoplist TYPE STANDARD TABLE OF spopli,

lv_answer TYPE i.

DO 3 TIMES.
APPEND INITIAL LINE TO lt_spoplist ASSIGNING FIELD-SYMBOL(<fs_spoplist>).
CASE sy-index.
WHEN 1.
"'Delete existing records and insert'
<fs_spoplist>-varoption = text-del.
WHEN 2.
"'Modify/Update existing records'
<fs_spoplist>-varoption = text-mod.
WHEN OTHERS.
"'Cancel'
<fs_spoplist>-varoption = text-can.
ENDCASE.
UNASSIGN : <fs_spoplist>.
ENDDO.

CALL FUNCTION 'POPUP_TO_DECIDE_LIST'


EXPORTING
* CURSORLINE = 1
* MARK_FLAG = ' '
* MARK_MAX = 1
* START_COL = 0
* START_ROW = 0
textline1 = text-srp "'Some of the records are already present'
textline2 = text-pro "'Please select to proceed'
* textline3 = 'MayBe'
titel = text-opt "'Options'
* DISPLAY_ONLY = ' '
IMPORTING
answer = lv_answer
TABLES
t_spopli = lt_spoplist
EXCEPTIONS
not_enough_answers = 1
too_much_answers = 2
too_much_marks = 3
OTHERS = 4.
IF sy-subrc EQ 0.
IF lv_answer EQ 1.
"Enqueue Delete and Deque
PERFORM enqueue USING x_tabdata
CHANGING y_tfields.
DELETE (p_table) FROM TABLE x_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT. "Commit
ELSE.
y_eflag = abap_true.
ENDIF.
PERFORM dequeue USING x_tabdata
y_tfields.

IF y_eflag IS INITIAL.
"Insert Records and Commit
INSERT (p_table) FROM TABLE x_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT. "Commit
ELSE.
y_eflag = abap_true.
ENDIF.
ENDIF.

ELSEIF lv_answer EQ 2.
"Enqueue Modify and Deque
PERFORM enqueue USING x_tabdata
CHANGING y_tfields.
MODIFY (p_table) FROM TABLE x_tabdata.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
y_eflag = abap_true.
ENDIF.
PERFORM dequeue USING x_tabdata
y_tfields.
ELSE.
"'Cancelled by User'
MESSAGE text-cbu TYPE gc_s DISPLAY LIKE gc_e.
RETURN.
ENDIF.
ELSE.
y_eflag = abap_true.
ENDIF.

ENDFORM. " USER_DECISION

You might also like