自动生成abap数据元素

REPORT z_dtel_bulk_import_final NO STANDARD PAGE HEADING.

---------------------------------------------------------------------

  • 批量导入/更新 数据元素(最后版)
  • 模板列(1…16):
  • 1 MODE, 2 NEW_DE_NAME, 3 REF_DE_NAME, 4 TABLE_NAME, 5 FIELD_NAME,
  • 6 DATA_TYPE, 7 LENGTH, 8 DECIMALS, 9 SHORT_TEXT, 10 MED_TEXT,
  • 11 LONG_TEXT, 12 XLONG_TEXT, 13 IS_CURRENCY, 14 IS_QUANTITY,
  • 15 REF_TABLE (可选覆盖), 16 REF_FIELD (可选覆盖)
    ---------------------------------------------------------------------

" 选择屏幕:下载模板按钮放在执行按钮旁
SELECTION-SCREEN PUSHBUTTON /1(20) btn_download USER-COMMAND download.
PARAMETERS: p_file TYPE rlgrap-filename OBLIGATORY, " 本地 Excel 文件
p_req TYPE trkorr OBLIGATORY. " 传输请求 ($TMP 表示本地)

INITIALIZATION.
btn_download = ‘下载模板’.

AT SELECTION-SCREEN.
CASE sy-ucomm.
WHEN ‘DOWNLOAD’.
PERFORM download_template.
LEAVE PROGRAM. " 点击下载模板后退出,不执行导入
ENDCASE.

---------------------------------------------------------------------

  • 类型定义
    ---------------------------------------------------------------------
    TYPES: BEGIN OF ty_input,
    mode TYPE string,
    new_de_name TYPE rollname,
    ref_de_name TYPE rollname,
    table_name TYPE tabname,
    field_name TYPE fieldname,
    data_type TYPE dd01v-datatype,
    length TYPE dd01v-leng,
    decimals TYPE dd01v-decimals,
    short_text TYPE dd04t-ddtext,
    med_text TYPE dd04t-ddtext,
    long_text TYPE dd04t-ddtext,
    xlong_text TYPE dd04t-ddtext,
    is_currency TYPE c LENGTH 1,
    is_quantity TYPE c LENGTH 1,
    ref_table TYPE tabname,
    ref_field TYPE fieldname,
    END OF ty_input.

TYPES: BEGIN OF ty_excel,
row TYPE i,
col TYPE i,
value TYPE char255,
END OF ty_excel.

TYPES: BEGIN OF ty_log,
rowno TYPE i,
de_name TYPE rollname,
mode TYPE string,
status TYPE string, " OK / ERROR / SKIP / WARN
msg TYPE string,
END OF ty_log.

---------------------------------------------------------------------

  • 数据区
    ---------------------------------------------------------------------
    DATA: gt_excel TYPE STANDARD TABLE OF ty_excel,
    gs_excel TYPE ty_excel,
    gt_input TYPE STANDARD TABLE OF ty_input,
    gs_input TYPE ty_input,
    gt_existing TYPE STANDARD TABLE OF rollname,
    lt_log TYPE STANDARD TABLE OF ty_log,
    ls_log TYPE ty_log,
    gv_choice TYPE c LENGTH 1,
    lv_idx TYPE i.

---------------------------------------------------------------------

  • 主流程
    ---------------------------------------------------------------------
    START-OF-SELECTION.
    PERFORM upload_excel.
    PERFORM parse_excel_to_input.
    PERFORM prescan_existing.
    PERFORM ask_global_choice.
    PERFORM create_or_update_all.
    PERFORM export_log_csv.
    PERFORM show_log.

---------------------------------------------------------------------

  • 下载模板(XLSX,3行:表头/描述/示例)
    ---------------------------------------------------------------------
    FORM download_template .
    DATA: lo_xl TYPE REF TO cl_fdt_xl_spreadsheet,
    lo_writer TYPE REF TO cl_fdt_xl_writer_2007,
    lt_table TYPE STANDARD TABLE OF string_table WITH EMPTY KEY,
    row_cells TYPE string_table,
    lv_xstring TYPE xstring,
    lt_solix TYPE solix_tab,
    lv_size TYPE i,
    lv_path TYPE string,
    lv_rc TYPE i.

    " 构造三行:第一行表头(与程序解析顺序一致)
    row_cells = VALUE string_table( ( ‘MODE’ ) ( ‘NEW_DE_NAME’ ) ( ‘REF_DE_NAME’ ) ( ‘TABLE_NAME’ )
    ( ‘FIELD_NAME’ ) ( ‘DATA_TYPE’ ) ( ‘LENGTH’ ) ( ‘DECIMALS’ )
    ( ‘SHORT_TEXT’ ) ( ‘MED_TEXT’ ) ( ‘LONG_TEXT’ ) ( ‘XLONG_TEXT’ )
    ( ‘IS_CURRENCY’ ) ( ‘IS_QUANTITY’ ) ( ‘REF_TABLE’ ) ( ‘REF_FIELD’ ) ).
    APPEND row_cells TO lt_table.

    " 第二行:字段描述
    row_cells = VALUE string_table( ( ‘创建模式’ ) ( ‘新数据元素技术名’ ) ( ‘参考数据元素’ ) ( ‘参考表名’ )
    ( ‘参考字段名’ ) ( ‘数据类型’ ) ( ‘长度’ ) ( ‘小数位’ )
    ( ‘短描述’ ) ( ‘中描述’ ) ( ‘长描述’ ) ( ‘更长描述’ )
    ( ‘是否金额字段(X/空)’ ) ( ‘是否数量字段(X/空)’ ) ( ‘可选覆盖REF_TABLE’ ) ( ‘可选覆盖REF_FIELD’ ) ).
    APPEND row_cells TO lt_table.

    " 第三行:示例
    row_cells = VALUE string_table( ( ‘DEFINE’ ) ( ‘ZAMOUNT’ ) ( ‘’ ) ( ‘’ )
    ( ‘’ ) ( ‘CURR’ ) ( ‘13’ ) ( ‘2’ )
    ( ‘金额’ ) ( ‘金额字段’ ) ( ‘金额字段描述’ ) ( ‘用于存储金额的字段’ )
    ( ‘X’ ) ( ‘’ ) ( ‘’ ) ( ‘’ ) ).
    APPEND row_cells TO lt_table.

    " 生成 XLSX 文档
    CREATE OBJECT lo_xl.
    lo_xl->set_data( it_data = lt_table iv_has_header = abap_false ).
    lo_writer = NEW cl_fdt_xl_writer_2007( ).
    lv_xstring = lo_writer->write_file( lo_xl ).
    lt_solix = cl_bcs_convert=>xstring_to_solix( lv_xstring ).
    lv_size = xstrlen( lv_xstring ).

    " 弹出保存对话框
    cl_gui_frontend_services=>file_save_dialog(
    EXPORTING
    default_extension = ‘xlsx’
    default_file_name = ‘Data_Element_Template.xlsx’
    CHANGING
    filename = lv_path
    rc = lv_rc
    ).

    IF lv_rc = 0 AND lv_path IS NOT INITIAL.
    CALL METHOD cl_gui_frontend_services=>gui_download
    EXPORTING
    filename = lv_path
    filetype = ‘BIN’
    bin_filesize = lv_size
    CHANGING
    data_tab = lt_solix
    EXCEPTIONS
    file_write_error = 1
    no_batch = 2
    gui_refuse_filetransfer = 3
    invalid_type = 4
    no_authority = 5
    unknown_error = 6
    OTHERS = 7.
    IF sy-subrc = 0.
    MESSAGE ‘Excel 模板已成功下载’ TYPE ‘S’.
    ELSE.
    MESSAGE ‘Excel 模板下载失败’ TYPE ‘E’.
    ENDIF.
    ELSE.
    MESSAGE ‘取消下载模板’ TYPE ‘I’.
    ENDIF.
    ENDFORM.

---------------------------------------------------------------------

  • upload_excel: 使用 ALSM 将 Excel -> gt_excel
    ---------------------------------------------------------------------
    FORM upload_excel .
    CLEAR gt_excel.
    CALL FUNCTION ‘ALSM_EXCEL_TO_INTERNAL_TABLE’
    EXPORTING
    filename = p_file
    i_begin_col = 1
    i_begin_row = 2
    i_end_col = 16
    i_end_row = 9999
    TABLES
    intern = gt_excel
    EXCEPTIONS
    inconsistent_parameters = 1
    upload_ole = 2
    OTHERS = 3.
    IF sy-subrc <> 0.
    MESSAGE ‘Excel 上传失败:请确认客户端支持 Excel/OLE,并检查文件路径’ TYPE ‘E’.
    ENDIF.
    ENDFORM.

---------------------------------------------------------------------

  • parse_excel_to_input: 将 gt_excel 解析为 gt_input(每行一条)
    ---------------------------------------------------------------------
    FORM parse_excel_to_input .
    CLEAR gt_input.
    DATA lv_row TYPE i VALUE 0.
    SORT gt_excel BY row col.

    LOOP AT gt_excel INTO gs_excel.
    IF gs_excel-row <> lv_row.
    IF lv_row <> 0.
    " 已经构造行,下一行初始化
    ENDIF.
    lv_row = gs_excel-row.
    " 确保 gt_input 有该索引行
    IF lines( gt_input ) < lv_row.
    APPEND INITIAL LINE TO gt_input.
    ENDIF.
    ENDIF.

    " 读取该单元格到对应字段(列号与模板顺序保持一致)
    READ TABLE gt_input INTO gs_input INDEX lv_row.
    CASE gs_excel-col.
    WHEN 1. gs_input-mode = gs_excel-value.
    WHEN 2. gs_input-new_de_name = gs_excel-value.
    WHEN 3. gs_input-ref_de_name = gs_excel-value.
    WHEN 4. gs_input-table_name = gs_excel-value.
    WHEN 5. gs_input-field_name = gs_excel-value.
    WHEN 6. gs_input-data_type = gs_excel-value.
    WHEN 7. gs_input-length = gs_excel-value.
    WHEN 8. gs_input-decimals = gs_excel-value.
    WHEN 9. gs_input-short_text = gs_excel-value.
    WHEN 10. gs_input-med_text = gs_excel-value.
    WHEN 11. gs_input-long_text = gs_excel-value.
    WHEN 12. gs_input-xlong_text = gs_excel-value.
    WHEN 13. gs_input-is_currency = gs_excel-value.
    WHEN 14. gs_input-is_quantity = gs_excel-value.
    WHEN 15. gs_input-ref_table = gs_excel-value.
    WHEN 16. gs_input-ref_field = gs_excel-value.
    ENDCASE.
    MODIFY gt_input FROM gs_input INDEX lv_row TRANSPORTING ALL FIELDS.
    ENDLOOP.

    IF gt_input IS INITIAL.
    MESSAGE ‘未解析到任何数据,请检查 Excel 模板’ TYPE ‘E’.
    ENDIF.
    ENDFORM.

---------------------------------------------------------------------

  • prescan_existing: 预扫描导入列表中已存在的 DE(去重)
    ---------------------------------------------------------------------
    FORM prescan_existing .
    CLEAR gt_existing.
    LOOP AT gt_input INTO gs_input.
    IF gs_input-new_de_name IS INITIAL.
    CONTINUE.
    ENDIF.
    CALL FUNCTION ‘DDIF_DTEL_GET’
    EXPORTING name = gs_input-new_de_name
    IMPORTING dd04v_wa = DATA(ls_tmp)
    EXCEPTIONS OTHERS = 1.
    IF sy-subrc = 0.
    IF gs_input-new_de_name NOT IN gt_existing.
    APPEND gs_input-new_de_name TO gt_existing.
    ENDIF.
    ENDIF.
    ENDLOOP.
    ENDFORM.

---------------------------------------------------------------------

  • ask_global_choice: 若有已存在对象,询问一次总体策略
    ---------------------------------------------------------------------
    FORM ask_global_choice .
    IF gt_existing IS INITIAL.
    gv_choice = ‘1’. " 无已存在项,默认覆盖(即创建)
    RETURN.
    ENDIF.

    DATA(lv_cnt) = lines( gt_existing ).
    CALL FUNCTION ‘POPUP_TO_CONFIRM’
    EXPORTING
    titlebar = |检测到已存在对象|
    text_question = |检测到 { lv_cnt } 个目标数据元素已存在系统。请选择:确定=全部覆盖;取消=全部跳过;帮助=按行询问。|
    button1 = ‘全部覆盖’
    button2 = ‘全部跳过’
    button3 = ‘按行询问’
    default_button= ‘3’
    IMPORTING
    answer = DATA(lv_ans).
    gv_choice = lv_ans.
    ENDFORM.

---------------------------------------------------------------------

  • create_or_update_all: 主循环,构造 DDIF 结构并调用 DDIF_DTEL_PUT
    ---------------------------------------------------------------------
    FORM create_or_update_all .
    DATA: lt_dfies TYPE STANDARD TABLE OF dfies,
    ls_dfies TYPE dfies,
    lt_dd04t TYPE STANDARD TABLE OF dd04t,
    ls_dd04t TYPE dd04t,
    ls_dd04v TYPE dd04v,
    lv_rc TYPE i,
    lv_prompt TYPE c LENGTH 1,
    lv_rowno TYPE i.

    lv_rowno = 0.
    LOOP AT gt_input INTO gs_input.
    ADD 1 TO lv_rowno.
    CLEAR ls_dd04v. CLEAR lt_dd04t. CLEAR ls_dd04t. CLEAR ls_log.

    " 基本校验
    IF gs_input-new_de_name IS INITIAL.
    ls_log-rowno = lv_rowno. ls_log-de_name = ‘(空)’. ls_log-mode = gs_input-mode.
    ls_log-status = ‘SKIP’. ls_log-msg = ‘NEW_DE_NAME 为空’. APPEND ls_log TO lt_log. CONTINUE.
    ENDIF.

    " 可选的命名校验(示例:强制 Z/Y 前缀)
    IF gs_input-new_de_name+0(1) NOT IN VALUE string_table( ( ‘Z’ ) ( ‘Y’ ) ).
    ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
    ls_log-status = ‘SKIP’. ls_log-msg = ‘NEW_DE_NAME 非 Z/Y 前缀(跳过)’. APPEND ls_log TO lt_log. CONTINUE.
    ENDIF.

    " 如果模板标记了金额/数量但没有显式 ref_table/ref_field,则设默认引用
    IF gs_input-is_currency = ‘X’ AND gs_input-ref_table IS INITIAL AND gs_input-ref_field IS INITIAL.
    gs_input-ref_table = ‘EKKO’.
    gs_input-ref_field = ‘WAERS’.
    ENDIF.
    IF gs_input-is_quantity = ‘X’ AND gs_input-ref_table IS INITIAL AND gs_input-ref_field IS INITIAL.
    gs_input-ref_table = ‘EKPO’.
    gs_input-ref_field = ‘MEINS’.
    ENDIF.

    " 检查是否已存在
    CALL FUNCTION ‘DDIF_DTEL_GET’
    EXPORTING name = gs_input-new_de_name
    IMPORTING dd04v_wa = DATA(ls_exist_dd04v)
    EXCEPTIONS OTHERS = 1.
    lv_rc = sy-subrc.

    IF lv_rc = 0.
    " 已存在,根据全局策略或逐条询问决定是否覆盖
    IF gv_choice = ‘2’.
    ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
    ls_log-status = ‘SKIP’. ls_log-msg = ‘用户选择:全部跳过’. APPEND ls_log TO lt_log. CONTINUE.
    ELSEIF gv_choice = ‘3’.
    CALL FUNCTION ‘POPUP_TO_CONFIRM’
    EXPORTING
    titlebar = ‘覆盖确认’
    text_question = |数据元素 { gs_input-new_de_name } 已存在,是否覆盖?|
    button1 = ‘覆盖’
    button2 = ‘跳过’
    default_button= ‘2’
    IMPORTING
    answer = lv_prompt.
    IF lv_prompt = ‘2’.
    ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
    ls_log-status = ‘SKIP’. ls_log-msg = ‘用户逐条选择:跳过’. APPEND ls_log TO lt_log. CONTINUE.
    ENDIF.
    ENDIF.
    " 若 gv_choice=‘1’ 则继续覆盖
    ENDIF.

    " 构造 DD04V(数据元素元数据) 及 DD04T(描述)
    CLEAR ls_dd04v.
    DATA(lv_mode) = to_upper( gs_input-mode ).

    CASE lv_mode.
    WHEN ‘REF_DE’.
    " 读取参考数据元素并以其为模板
    IF gs_input-ref_de_name IS INITIAL.
    ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
    ls_log-status = ‘ERROR’. ls_log-msg = ‘REF_DE 模式缺少 REF_DE_NAME’; APPEND ls_log TO lt_log. CONTINUE.
    ENDIF.
    CALL FUNCTION ‘DDIF_DTEL_GET’
    EXPORTING name = gs_input-ref_de_name
    IMPORTING dd04v_wa = ls_dd04v
    TABLES dd04t_tab = lt_dd04t
    EXCEPTIONS OTHERS = 1.
    IF sy-subrc <> 0.
    ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
    ls_log-status = ‘ERROR’. ls_log-msg = |读取参考数据元素失败: { gs_input-ref_de_name }|. APPEND ls_log TO lt_log. CONTINUE.
    ENDIF.
    ls_dd04v-rollname = gs_input-new_de_name.
    ls_dd04v-ddlanguage = sy-langu.

    WHEN 'REF_TABLE'.
      " 以表字段为模板
      IF gs_input-table_name IS INITIAL OR gs_input-field_name IS INITIAL.
        ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
        ls_log-status = 'ERROR'. ls_log-msg = 'REF_TABLE 模式缺 TABLE_NAME 或 FIELD_NAME'; APPEND ls_log TO lt_log. CONTINUE.
      ENDIF.
    
      CLEAR lt_dfies.
      CALL FUNCTION 'DDIF_FIELDINFO_GET'
        EXPORTING tabname = gs_input-table_name fieldname = gs_input-field_name langu = sy-langu
        TABLES dfies_tab = lt_dfies
        EXCEPTIONS OTHERS = 1.
      IF sy-subrc <> 0 OR lt_dfies IS INITIAL.
        ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
        ls_log-status = 'ERROR'. ls_log-msg = |读取表字段失败: { gs_input-table_name } - { gs_input-field_name }|. APPEND ls_log TO lt_log. CONTINUE.
      ENDIF.
    
      READ TABLE lt_dfies INTO ls_dfies INDEX 1.
      IF sy-subrc <> 0.
        ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
        ls_log-status = 'ERROR'. ls_log-msg = '读取 dfies 失败'; APPEND ls_log TO lt_log. CONTINUE.
      ENDIF.
    
      ls_dd04v-datatype = ls_dfies-datatype.
      ls_dd04v-leng     = ls_dfies-leng.
      ls_dd04v-decimals = ls_dfies-decimals.
    
      " 优先使用表字段自身的引用(若有)
      IF ls_dfies-reftable IS NOT INITIAL AND ls_dfies-reffield IS NOT INITIAL.
        ls_dd04v-reftable = ls_dfies-reftable.
        ls_dd04v-reffield = ls_dfies-reffield.
      ELSE.
        " 否则使用模板覆盖引用(若提供),否则上面已根据标志设置默认 gs_input-ref_*
        IF gs_input-ref_table IS NOT INITIAL AND gs_input-ref_field IS NOT INITIAL.
          ls_dd04v-reftable = gs_input-ref_table.
          ls_dd04v-reffield = gs_input-ref_field.
        ELSE.
          ls_dd04v-reftable = gs_input-ref_table.
          ls_dd04v-reffield = gs_input-ref_field.
        ENDIF.
      ENDIF.
    
      ls_dd04v-rollname = gs_input-new_de_name.
      ls_dd04v-ddlanguage = sy-langu.
    
    WHEN 'DEFINE'.
      " 直接定义(必须提供 data_type & length)
      IF gs_input-data_type IS INITIAL OR gs_input-length IS INITIAL.
        ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
        ls_log-status = 'ERROR'. ls_log-msg = 'DEFINE 模式需指定 DATA_TYPE 与 LENGTH'; APPEND ls_log TO lt_log. CONTINUE.
      ENDIF.
    
      ls_dd04v-datatype = gs_input-data_type.
      ls_dd04v-leng     = gs_input-length.
      ls_dd04v-decimals = gs_input-decimals.
    
      " 若为 CURR/QUAN 则需要引用(模板15/16或默认标志)
      IF ls_dd04v-datatype = 'CURR' OR ls_dd04v-datatype = 'QUAN'.
        IF gs_input-ref_table IS NOT INITIAL AND gs_input-ref_field IS NOT INITIAL.
          ls_dd04v-reftable = gs_input-ref_table.
          ls_dd04v-reffield = gs_input-ref_field.
        ELSE.
          IF ls_dd04v-datatype = 'CURR' AND gs_input-is_currency = 'X'.
            ls_dd04v-reftable = 'EKKO'. ls_dd04v-reffield = 'WAERS'.
          ELSEIF ls_dd04v-datatype = 'QUAN' AND gs_input-is_quantity = 'X'.
            ls_dd04v-reftable = 'EKPO'. ls_dd04v-reffield = 'MEINS'.
          ELSE.
            ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
            ls_log-status = 'ERROR'. ls_log-msg = 'DEFINE 的 CURR/QUAN 必须提供 REF_TABLE/REF_FIELD 或在标志中填 X'; APPEND ls_log TO lt_log. CONTINUE.
          ENDIF.
        ENDIF.
      ENDIF.
    
      ls_dd04v-rollname = gs_input-new_de_name.
      ls_dd04v-ddlanguage = sy-langu.
    
    WHEN OTHERS.
      ls_log-rowno = lv_rowno. ls_log-de_name = gs_input-new_de_name. ls_log-mode = gs_input-mode.
      ls_log-status = 'ERROR'. ls_log-msg = |未知 MODE: { gs_input-mode }|. APPEND ls_log TO lt_log. CONTINUE.
    

    ENDCASE.

    " 组织 dd04t 描述(当前语言)
    CLEAR ls_dd04t.
    ls_dd04t-rollname = ls_dd04v-rollname.
    ls_dd04t-ddlanguage = sy-langu.
    ls_dd04t-scrtext_s = gs_input-short_text.
    ls_dd04t-scrtext_m = gs_input-med_text.
    ls_dd04t-scrtext_l = gs_input-long_text.
    ls_dd04t-ddtext = gs_input-xlong_text.
    APPEND ls_dd04t TO lt_dd04t.

    " 调用 DDIF_DTEL_PUT 创建/更新(order = p_req)
    CALL FUNCTION ‘DDIF_DTEL_PUT’
    EXPORTING
    name = ls_dd04v-rollname
    dd04v_wa = ls_dd04v
    order = p_req
    TABLES
    dd04t_tab = lt_dd04t
    EXCEPTIONS
    illegal_input = 1
    OTHERS = 2.
    lv_rc = sy-subrc.

    IF lv_rc = 0.
    " 激活
    CALL FUNCTION ‘DDIF_DTEL_ACTIVATE’
    EXPORTING name = ls_dd04v-rollname
    EXCEPTIONS OTHERS = 1.
    IF sy-subrc = 0.
    ls_log-rowno = lv_rowno. ls_log-de_name = ls_dd04v-rollname. ls_log-mode = gs_input-mode.
    ls_log-status = ‘OK’. ls_log-msg = ‘创建并激活成功’; APPEND ls_log TO lt_log.
    ELSE.
    ls_log-rowno = lv_rowno. ls_log-de_name = ls_dd04v-rollname. ls_log-mode = gs_input-mode.
    ls_log-status = ‘WARN’. ls_log-msg = ‘创建成功但激活失败’; APPEND ls_log TO lt_log.
    ENDIF.
    ELSE.
    ls_log-rowno = lv_rowno. ls_log-de_name = ls_dd04v-rollname. ls_log-mode = gs_input-mode.
    ls_log-status = ‘ERROR’. ls_log-msg = |DDIF_DTEL_PUT 失败 RC={ lv_rc }|; APPEND ls_log TO lt_log.
    ENDIF.

    ENDLOOP.
    ENDFORM.

---------------------------------------------------------------------

  • export_log_csv: 将 lt_log 导出为 CSV(前端下载)
    ---------------------------------------------------------------------
    FORM export_log_csv .
    DATA: lt_lines TYPE TABLE OF string,
    lv_line TYPE string,
    lv_fname TYPE string,
    lv_path TYPE string,
    lv_rc TYPE i,
    lv_stamp TYPE string.

    APPEND |rowno,de_name,mode,status,message| TO lt_lines.

    LOOP AT lt_log INTO ls_log.
    REPLACE ALL OCCURRENCES OF ‘"’ IN ls_log-msg WITH ‘""’.
    lv_line = |{ ls_log-rowno },"{ ls_log-de_name }",{ ls_log-mode },"{ ls_log-status }","{ ls_log-msg }"|.
    APPEND lv_line TO lt_lines.
    ENDLOOP.

    lv_stamp = |{ sy-datum+0(4) }{ sy-datum+5(2) }{ sy-datum+8(2) }{ sy-uzeit+0(2) }{ sy-uzeit+3(2) }{ sy-uzeit+6(2) }|.
    lv_fname = |DTEL_IMPORT_LOG
    { lv_stamp }.csv|.

    cl_gui_frontend_services=>file_save_dialog(
    EXPORTING
    default_extension = ‘csv’
    default_file_name = lv_fname
    CHANGING
    filename = lv_path
    rc = lv_rc
    ).

    IF lv_rc = 0 AND lv_path IS NOT INITIAL.
    CALL METHOD cl_gui_frontend_services=>gui_download
    EXPORTING
    filename = lv_path
    filetype = ‘ASC’
    CHANGING
    data_tab = lt_lines
    EXCEPTIONS OTHERS = 1.
    IF sy-subrc = 0.
    MESSAGE |日志已导出到本机: { lv_path }| TYPE ‘S’.
    ELSE.
    MESSAGE ‘日志导出失败’ TYPE ‘W’.
    ENDIF.
    ELSE.
    MESSAGE ‘取消导出日志’ TYPE ‘I’.
    ENDIF.
    ENDFORM.

---------------------------------------------------------------------

  • show_log: 在屏幕输出日志摘要
    ---------------------------------------------------------------------
    FORM show_log .
    IF lt_log IS INITIAL.
    WRITE: / ‘无操作记录’.
    RETURN.
    ENDIF.
    WRITE: / ‘导入日志(行号, 数据元素, 模式, 状态, 说明)’.
    LOOP AT lt_log INTO ls_log.
    WRITE: / ls_log-rowno, ls_log-de_name, ls_log-mode, ls_log-status, ls_log-msg.
    ENDLOOP.
    ENDFORM.
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值