********************************************************************
* 事务代码: *
* 程序名称: *
* 程序目的: *
* 设 计 人: *
* 开 发 人: *
* 设计时间:2022-09-26 *
* 程序类型: ABAP/4 程序 ,批导程序 *
* 应用类型: FI *
* 描 述: *
*(修改日志)--------------------------------------------------------*
* *
* 日志号 修改人 修改时间 修改说明 传输号码 *
* ---- ---- ------ -----------
********************************************************************
REPORT zfib002.
*----------------------------------------------------------------------*
* 数据库表声明/Database Table Declaration
*----------------------------------------------------------------------*
TABLES: sscrfields. " 选择屏幕上的字段
*&---------------------------------------------------------------------*
*& ALV TYPE/ALV 类型定义
*&---------------------------------------------------------------------*
*&---ALV数据组,类型池
TYPE-POOLS:slis,
vrm.
*----------------------------------------------------------------------*
* 结构声明类型/Structure Type Declaration
*----------------------------------------------------------------------*
*&--- 全局结构体与内表声明
*&---Excel导入数据
TYPES:BEGIN OF ty_excel,
light TYPE c LENGTH 4, " 信号灯
msg TYPE string , " 导入结果
" 项目
vbukr TYPE proj-vbukr , " 项目的公司代码
werks TYPE proj-werks , " 工厂
pspnr TYPE proj-pspid , " 项目定义
post1 TYPE proj-post1 , " 项目描述
profl TYPE proj-profl , " 项目参数文件
plfaz TYPE proj-plfaz , " 项目计划开始日期
plsez TYPE proj-plsez , " 项目计划完成日期
" WBS元素
level TYPE c LENGTH 1 , " 层级
posid1 TYPE prps-posid , " 一层WBS
posid2 TYPE prps-posid , " 二层WBS
posid3 TYPE prps-posid , " 三层WBS
prart TYPE prps-prart , " WBS类型
post2 TYPE prps-post1 , " WBS描述
poski TYPE prps-poski , " 短标识
END OF ty_excel.
*----------------------------------------------------------------------*
* CONSTANTS/(全局)常量 *
*----------------------------------------------------------------------*
*----------------------------------------------------------------------*
* 全局变量定义/Global variable definition
*----------------------------------------------------------------------*
*&---全局内表定义
DATA:gt_excel TYPE STANDARD TABLE OF ty_excel. " Excel导入表
*&---全局结构定义
DATA:gs_excel TYPE ty_excel. " Excel导入结构
*&---------------------------------------------------------------------*
*& 字段串定义/Field-symbols *
*&---------------------------------------------------------------------*
FIELD-SYMBOLS:<fs_excel> TYPE ty_excel.
*&---------------------------------------------------------------------*
*& ALV TYPE/ALV 类型定义
*&---------------------------------------------------------------------*
*&---ALV数据组,类型池
TYPE-POOLS:slis,
vrm.
DATA:gt_fieldcat TYPE STANDARD TABLE OF lvc_s_fcat, " ALV 控制: 字段目录
gs_fieldcat TYPE lvc_s_fcat, " ALV 控制: 字段目录
gs_layout TYPE lvc_s_layo. " ALV 控制: 布局结构
DATA:gs_functxt TYPE smp_dyntxt .
*----------------------------------------------------------------------*
* Excel 导入所需传入与接收参数定义 *
*----------------------------------------------------------------------*
DATA: gv_filepath TYPE string. " 保存文件路径
FIELD-SYMBOLS: <fs_unit> LIKE alsmex_tabline. " Excel 单元格
FIELD-SYMBOLS: <fs_value> TYPE any.
DATA: gv_lines LIKE sy-index VALUE 2. " Excel 数据的行数
DATA: gv_index LIKE sy-index VALUE 1. " Message 表的序号
DATA: gv_sign TYPE c. " Excel 一行是否写入成功的标志
DATA: gv_succ LIKE sy-index. " 成功更新条数
DATA: gv_fail TYPE i VALUE 0. " 失败的行数
DATA: gv_flag TYPE char1. " 标记
DATA: gt_xlstmp TYPE alsmex_tabline OCCURS 0. " 保存 Excel 中读取的记录
DATA: gs_xlstmp TYPE alsmex_tabline. " 保存 Excel 中读取的记录
*&---------------------------------------------------------------------*
*& Macro 宏定义
*&---------------------------------------------------------------------*
DEFINE mcr_set_catalog.
gs_fieldcat-fieldname = &1. " 字段技术名称
gs_fieldcat-coltext = &2. " 显示名称
gs_fieldcat-ref_table = &3. " 参照表
gs_fieldcat-ref_field = &4. " 参照表字段
gs_fieldcat-qfieldname = &5. " 参考计量单位的字段名称
gs_fieldcat-key = &6. " key 值
gs_fieldcat-edit = &7. " 可编辑
APPEND gs_fieldcat TO gt_fieldcat.
CLEAR gs_fieldcat.
END-OF-DEFINITION.
*&---------------------------------------------------------------------*
*& SELECTION SCREEN/选择屏幕 *
*&---------------------------------------------------------------------*
*&--- 选择屏幕块
SELECTION-SCREEN BEGIN OF BLOCK block0 WITH FRAME TITLE TEXT-101. " 上传文件
SELECTION-SCREEN: FUNCTION KEY 1. "菜单栏下载模板
PARAMETERS: p_fname LIKE rlgrap-filename. " 输入文件路径
SELECTION-SCREEN END OF BLOCK block0.
*&---------------------------------------------------------------------*
*& INITIALIZATION/选择屏幕前初始化 *
*&---------------------------------------------------------------------*
INITIALIZATION.
*&---设置选择屏幕菜单栏按钮--下载模板
gs_functxt = VALUE #(
icon_id = icon_export
quickinfo = TEXT-001 " 下载模板
icon_text = TEXT-001 " 下载模板
).
sscrfields-functxt_01 = gs_functxt.
*&---------------------------------------------------------------------*
*& at selection-screen/选择屏幕开始 *
*&---------------------------------------------------------------------*
AT SELECTION-SCREEN.
CASE sy-ucomm.
WHEN 'FC01'. " 下载模板
PERFORM frm_download_template.
WHEN OTHERS.
ENDCASE.
*&---------------------------------------------------------------------*
*& AT SELECTION-SCREEN ON VALUE-REQUEST/F4 Search Help *
*&---------------------------------------------------------------------*
*&--- 上传文件 F4 路径帮助
AT SELECTION-SCREEN ON VALUE-REQUEST FOR p_fname.
CALL FUNCTION 'F4_FILENAME'
EXPORTING
program_name = sy-cprog
dynpro_number = sy-dynnr
IMPORTING
file_name = p_fname.
CLEAR gv_filepath.
gv_filepath = p_fname.
" 判断是否为 XLS文件
SEARCH gv_filepath FOR '.xls'.
IF sy-subrc <> 0.
MESSAGE s006(zfico01) DISPLAY LIKE 'E'. " 上传文件类型错误,请选择XLS文件
STOP.
ENDIF.
*&---------------------------------------------------------------------*
*& START-OF-SELECTION/开始选择屏幕 *
*&---------------------------------------------------------------------*
START-OF-SELECTION.
PERFORM frm_check_excel. " Excel 是否上传校验
*&---------------------------------------------------------------------*
*& END-OF-SELECTION/结束选择屏幕(程序结束处理,输出等) *
*&---------------------------------------------------------------------*
END-OF-SELECTION.
IF gt_excel IS NOT INITIAL.
PERFORM frm_display_data. " ALV 数据展示
ELSE.
MESSAGE s007(zfico01) DISPLAY LIKE 'E'. " 导入文件为空,请检查
ENDIF.
*&---------------------------------------------------------------------*
*& Form FRM_CHECK_EXCEL
*&---------------------------------------------------------------------*
*& Excel 是否上传校验
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_check_excel .
DATA lv_flag(1).
IF p_fname IS INITIAL.
MESSAGE s008(zfico01) DISPLAY LIKE 'E'. " 文件路径不能为空
LEAVE LIST-PROCESSING.
ENDIF.
PERFORM frm_read_excel. " 读取 Excel 文件数据
* PERFORM frm_read_excel_new. " 读取 Excel 文件数据
ENDFORM. " FRM_CHECK_EXCEL
*&---------------------------------------------------------------------*
*& Form FRM_READ_EXCEL
*&---------------------------------------------------------------------*
*& 读取 Excel 文件数据
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_read_excel .
DATA lv_value(255) TYPE c.
DATA lv_flag TYPE char1.
DATA lv_count LIKE sy-subrc.
DATA lv_message TYPE string.
REFRESH gt_xlstmp.
" 读取 EXCEL 文件数据
CALL FUNCTION 'ALSM_EXCEL_TO_INTERNAL_TABLE'
EXPORTING
filename = p_fname
i_begin_col = 1
i_begin_row = 2 " 从第 4 行开始 读取
i_end_col = 14 " 结束列
i_end_row = 65536 " 结束行
TABLES
intern = gt_xlstmp " 存储读取的记录 行、列、值
EXCEPTIONS
inconsistent_parameters = 1
upload_ole = 2
OTHERS = 3.
IF sy-subrc <> 0 .
MESSAGE ID sy-msgid TYPE 'S' NUMBER sy-msgno DISPLAY LIKE sy-msgty
WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4.
STOP.
ENDIF.
*&--- 将读取到的记录存储到 gt_excel 内表中
CLEAR gt_excel.
SORT gt_xlstmp BY row col .
" 循环赋值
LOOP AT gt_xlstmp ASSIGNING <fs_unit>.
ASSIGN COMPONENT <fs_unit>-col OF STRUCTURE <fs_unit> TO <fs_value> .
lv_value = <fs_unit>-value .
CONDENSE lv_value.
CASE <fs_unit>-col. " 判断当前列,并赋值到对应技术字段
WHEN 1.
gs_excel-vbukr = lv_value. " 项目公司代码
WHEN 2.
gs_excel-werks = lv_value. " 工厂
WHEN 3.
gs_excel-pspnr = lv_value. " 项目定义
WHEN 4.
gs_excel-post1 = lv_value. " 短描述
WHEN 5.
gs_excel-profl = lv_value. " 项目参数文件
WHEN 6.
CALL FUNCTION 'CONVERT_DATE_TO_INTERNAL'
EXPORTING
date_external = lv_value "当前用户日期格式:YYYY.MM.DD
IMPORTING
date_internal = lv_value.
gs_excel-plfaz = lv_value. " 项目计划开始日期
WHEN 7.
CALL FUNCTION 'CONVERT_DATE_TO_INTERNAL'
EXPORTING
date_external = lv_value "当前用户日期格式:YYYY.MM.DD
IMPORTING
date_internal = lv_value.
gs_excel-plsez = lv_value. " 项目计划结束日期
WHEN 8.
gs_excel-level = lv_value. " 层级
WHEN 9.
gs_excel-posid1 = lv_value. " 一层WBS
WHEN 10.
gs_excel-posid2 = lv_value. " 二层WBS
WHEN 11.
gs_excel-posid3 = lv_value. " 三层WBS
WHEN 12.
gs_excel-prart = lv_value. " WBS类型
WHEN 13.
gs_excel-post2 = lv_value. " WBS描述
WHEN 14.
gs_excel-poski = lv_value. " 短标识
ENDCASE.
AT END OF row.
gs_excel-light = icon_light_out. " 熄灯
APPEND gs_excel TO gt_excel.
CLEAR gs_excel.
ENDAT.
ENDLOOP.
SORT gt_excel BY pspnr.
ENDFORM. " FRM_READ_EXCEL
*&---------------------------------------------------------------------*
*& Form FRM_DISPLAY_DATA
*&---------------------------------------------------------------------*
*& ALV 展示数据
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_display_data .
PERFORM frm_build_fieldcat. " 配置 ALV 字段目录
PERFORM frm_build_layout. " 构建 ALV 布局样式
*&--- 调用 ALV 展示数据
CALL FUNCTION 'REUSE_ALV_GRID_DISPLAY_LVC'
EXPORTING
i_callback_program = sy-repid
i_callback_pf_status_set = 'FRM_PF_STATUS'
i_callback_user_command = 'FRM_USER_COMMAND'
is_layout_lvc = gs_layout
it_fieldcat_lvc = gt_fieldcat
i_save = 'A' " 标准保存模式
TABLES
t_outtab = gt_excel " 内表数据
EXCEPTIONS
program_error = 1
OTHERS = 2.
IF sy-subrc <> 0.
MESSAGE ID sy-msgid TYPE 'S' NUMBER sy-msgno DISPLAY LIKE sy-msgty
WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4.
ENDIF.
ENDFORM. " FRM_DISPLAY_DATA
*&---------------------------------------------------------------------*
*& Form FRM_PF_STATUS
*&---------------------------------------------------------------------*
*& ALV 工具栏状态
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_pf_status USING ps_extab TYPE slis_t_extab.
SET PF-STATUS 'STATUS_1000'.
ENDFORM. " FRM_PF_STATUS
*&---------------------------------------------------------------------*
*& Form frm_user_command
*&---------------------------------------------------------------------*
* 菜单栏事件
*----------------------------------------------------------------------*
* --> pv_ucomm 触发的功能码
* <-- p2 text
*----------------------------------------------------------------------*
FORM frm_user_command USING pv_ucomm LIKE sy-ucomm "user_command
pv_selfield TYPE slis_selfield.
DATA: lr_grid TYPE REF TO cl_gui_alv_grid.
CALL FUNCTION 'GET_GLOBALS_FROM_SLVC_FULLSCR'
IMPORTING
e_grid = lr_grid.
CALL METHOD lr_grid->check_changed_data. "将更新后的数据传到alv所对应的内表
pv_selfield-refresh = 'X'. "刷新数据
CASE pv_ucomm.
WHEN 'IMPORT'.
PERFORM frm_value_check.
PERFORM frm_import.
ENDCASE.
ENDFORM. " FRM_USER_COMMAND
*&---------------------------------------------------------------------*
*& Form frm_import
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_import .
DATA: lt_head TYPE STANDARD TABLE OF ty_excel.
" 筛选项目
lt_head = gt_excel.
SORT lt_head BY pspnr.
DELETE ADJACENT DUPLICATES FROM lt_head COMPARING pspnr.
SELECT
pspid
FROM proj
FOR ALL ENTRIES IN @gt_excel
WHERE
pspid = @gt_excel-pspnr
INTO TABLE @DATA(lt_proj).
SORT lt_proj BY pspid.
" 项目导入
LOOP AT lt_head INTO gs_excel WHERE light = icon_light_out. " 导入熄灯项目
READ TABLE lt_proj TRANSPORTING NO FIELDS WITH KEY gs_excel-pspnr BINARY SEARCH.
IF sy-subrc = 0. " 项目已创建
gs_excel-light = icon_yellow_light. " 黄灯
gs_excel-msg = TEXT-m01. " 项目已创建;
MODIFY gt_excel FROM gs_excel TRANSPORTING light msg WHERE pspnr = gs_excel-pspnr.
ELSE. " 项目未创建
PERFORM frm_porj_create.
MODIFY gt_excel FROM gs_excel TRANSPORTING light msg WHERE pspnr = gs_excel-pspnr.
CLEAR gs_excel.
ENDIF.
ENDLOOP.
" WBS导入
PERFORM frm_wbs_create.
" 检查是否有导入失败行项目
SORT gt_excel BY light.
READ TABLE gt_excel TRANSPORTING NO FIELDS WITH KEY light = icon_red_light.
IF sy-subrc = 0.
MESSAGE s012(zfico01) DISPLAY LIKE 'E'. " 存在导入失败的行项目,请检查数据
ENDIF.
SORT gt_excel BY pspnr level light.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form frm_download_template
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_download_template .
DATA: lv_filename TYPE string,
lv_fullpath TYPE string,
lv_path TYPE string,
lv_objid TYPE wwwdatatab-objid,
ls_objdata TYPE wwwdatatab,
lv_destination TYPE rlgrap-filename,
lv_rc TYPE i.
lv_objid = 'ZFIB008'.
lv_filename = TEXT-002 && '.xls'. " 项目&WBS元素批导模板
SELECT SINGLE relid objid INTO CORRESPONDING FIELDS OF ls_objdata
FROM wwwdata
WHERE srtf2 = 0 AND relid = 'MI' AND objid = lv_objid.
IF sy-subrc <> 0.
MESSAGE e009(zfico01). " 模板不存在,请联系管理员导入
ENDIF.
CALL METHOD cl_gui_frontend_services=>file_save_dialog
EXPORTING
default_extension = 'XLS'
default_file_name = lv_filename
file_filter = 'EXCEL'
CHANGING
filename = lv_filename
path = lv_path
fullpath = lv_fullpath
EXCEPTIONS
OTHERS = 1.
IF lv_fullpath = ''.
MESSAGE e010(zfico01). " 没有选择文件
ENDIF.
IF strlen( lv_fullpath ) > 128.
MESSAGE s011(zfico01) DISPLAY LIKE 'E'. " 文件名长度超过128位,请重新选择文件
STOP.
ENDIF.
lv_destination = lv_fullpath.
CALL FUNCTION 'DOWNLOAD_WEB_OBJECT'
EXPORTING
key = ls_objdata
destination = lv_destination
IMPORTING
rc = lv_rc.
IF lv_rc <> 0.
MESSAGE e007(zfico01). " 导入文件为空,请检查
ENDIF.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_BUILD_FIELDCAT
*&---------------------------------------------------------------------*
*& 配置 ALV 字段目录
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_build_fieldcat .
mcr_set_catalog: 'LIGHT' TEXT-a01 '' 'LIGHT' '' 'X' '', " 信号灯
'MSG' TEXT-a02 '' 'MSG' '' 'X' '', " 导入结果
'VBUKR' TEXT-a03 'PROJ' 'VBUKR' '' '' '', " 项目的公司代码
'WERKS' TEXT-a04 'PROJ' 'WERKS' '' '' '', " 工厂
'PSPNR' TEXT-a05 'PROJ' 'PSPID' '' '' '', " 项目定义
'POST1' TEXT-a06 'PROJ' 'POST1' '' '' '', " 项目描述
'PROFL' TEXT-a07 'PROJ' 'PROFL' '' '' '', " 项目参数文件
'PLFAZ' TEXT-a08 'PROJ' 'PLFAZ' '' '' '', " 项目计划开始日期
'PLSEZ' TEXT-a09 'PROJ' 'PLSEZ' '' '' '', " 项目计划完成日期
'LEVEL' TEXT-a15 '' '' '' '' '', " 层级
'POSID1' TEXT-a19 'PRPS' 'POSID' '' '' '', " 一层WBS
'POSID2' TEXT-a10 'PRPS' 'POSID' '' '' '', " 二层WBS
'POSID3' TEXT-a11 'PRPS' 'POSID' '' '' '', " 三层WBS
'PRART' TEXT-a12 'PRPS' 'PRART' '' '' '', " WBS类型
'POST2' TEXT-a13 'PRPS' 'POST1' '' '' '', " WBS描述
'POSKI' TEXT-a14 'PRPS' 'POSKI' '' '' ''. " 短标识
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_BUILD_LAYOUT
*&---------------------------------------------------------------------*
*& 构建 ALV 样式布局
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_build_layout .
CLEAR: gs_layout.
gs_layout = VALUE #( zebra = 'X' " ALV 控制: 可选行颜色 (带) - 斑马条纹 - 美观
cwidth_opt = 'X' " 自动调整ALVL列宽
no_toolbar = 'X' ). " ALV 控制: 隐藏工具栏
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_PORJ_CREATE
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_porj_create .
DATA:
lv_seqno(6) TYPE n VALUE '000000',
lt_message TYPE TABLE OF bapi_meth_message,
ls_message TYPE bapi_meth_message,
ls_return TYPE bapireturn1,
lt_method_project TYPE TABLE OF bapi_method_project,
ls_method_project TYPE bapi_method_project,
ls_project_definition LIKE bapi_project_definition,
ls_project_definition_upd LIKE bapi_project_definition_up.
"项目定义
ls_project_definition-project_definition = gs_excel-pspnr. "项目定义
ls_project_definition-description = gs_excel-post1. "描述
ls_project_definition-project_profile = gs_excel-profl. "项目参数文件
ls_project_definition-comp_code = gs_excel-vbukr. "项目的公司代码
ls_project_definition-plant = gs_excel-werks. "工厂
ls_project_definition-start = gs_excel-plfaz. "项目计划开始日期
ls_project_definition-finish = gs_excel-plsez. "项目计划完成日期
"项目定义(更新字段)
ls_project_definition_upd-project_definition = 'X'. "项目定义
ls_project_definition_upd-description = 'X'. "描述
ls_project_definition_upd-project_profile = 'X'. "项目参数文件
ls_project_definition_upd-comp_code = 'X'. "项目的公司代码
ls_project_definition_upd-plant = 'X'. "工厂
ls_project_definition_upd-start = 'X'. "项目计划开始日期
ls_project_definition_upd-finish = 'X'. "项目计划完成日期
"项目处理方法创建
lv_seqno = lv_seqno + 1.
ls_method_project-refnumber = lv_seqno. "参考号
ls_method_project-objecttype = co1_type-project_definition. "对象类型
ls_method_project-method = co1_meth-create. "项目创建
ls_method_project-objectkey = gs_excel-pspnr. "项目定义
APPEND ls_method_project TO lt_method_project.
CLEAR ls_method_project.
"项目处理方法保存
ls_method_project-method = co1_meth-save.
APPEND ls_method_project TO lt_method_project.
CLEAR: ls_method_project.
* SET UPDATE TASK LOCAL. "同步执行项目创建
CALL FUNCTION 'BAPI_PROJECT_MAINTAIN'
EXPORTING
i_project_definition = ls_project_definition
i_project_definition_upd = ls_project_definition_upd
IMPORTING
return = ls_return
TABLES
i_method_project = lt_method_project
e_message_table = lt_message.
"回写至ALV每行导入结果
IF ls_return-type EQ 'E' OR ls_return EQ 'A'. " 项目创建失败
CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.
" 更新消息
LOOP AT lt_message INTO ls_message.
gs_excel-msg = gs_excel-msg && ls_message-message_text && ';'.
ENDLOOP.
gs_excel-light = icon_red_light. " 红灯
ELSE.
CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'
EXPORTING
wait = 'X'.
" 更新日志信息
gs_excel-msg = TEXT-m02. " 项目创建成功;
gs_excel-light = icon_green_light. " 绿灯
ENDIF.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_WBS_CREATE
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_wbs_create .
DATA: lv_tabix TYPE i,
lt_head TYPE STANDARD TABLE OF ty_excel.
DATA:
lv_project TYPE bapi_bus2001_new-project_definition,
lt_wbs_import TYPE STANDARD TABLE OF bapi_bus2054_new,
ls_wbs_import LIKE LINE OF lt_wbs_import,
lt_wbs_element TYPE STANDARD TABLE OF bapi_bus2054_detail,
ls_wbs_element LIKE LINE OF lt_wbs_element,
lt_return TYPE STANDARD TABLE OF bapiret2,
ls_return LIKE LINE OF lt_return.
DATA:
lv_seqno(6) TYPE n VALUE '000000',
lt_message TYPE TABLE OF bapi_meth_message,
ls_message TYPE bapi_meth_message,
ls_return1 TYPE bapireturn1,
lt_method_project TYPE TABLE OF bapi_method_project,
ls_method_project TYPE bapi_method_project,
ls_project_definition LIKE bapi_project_definition,
ls_project_definition_upd LIKE bapi_project_definition_up,
lt_wbs_update TYPE STANDARD TABLE OF BAPI_WBS_ELEMENT,
lt_wbs_updatex TYPE STANDARD TABLE OF BAPI_WBS_ELEMENT_UPDATE,
ls_wbs_update LIKE BAPI_WBS_ELEMENT,
ls_wbs_updatex LIKE BAPI_WBS_ELEMENT_UPDATE.
" 筛选项目
lt_head = gt_excel.
SORT lt_head BY pspnr level light.
DELETE ADJACENT DUPLICATES FROM lt_head COMPARING pspnr level.
DELETE lt_head WHERE light = icon_red_light.
SORT gt_excel BY pspnr level posid3.
LOOP AT lt_head INTO DATA(ls_head).
CLEAR:lv_project,lt_wbs_element,lt_return.
" 项目号
lv_project = ls_head-pspnr.
" 获取项目WBS信息
CALL FUNCTION 'BAPI_BUS2054_GETDATA'
EXPORTING
i_project_definition = lv_project
TABLES
et_wbs_element = lt_wbs_element
et_return = lt_return.
" 按项目号,层级,依次创建WBS元素
READ TABLE gt_excel TRANSPORTING NO FIELDS WITH KEY pspnr = ls_head-pspnr level = ls_head-level BINARY SEARCH.
IF sy-subrc = 0.
lv_tabix = sy-tabix.
" 按层级汇总WBS元素
CLEAR: lt_wbs_import,lt_method_project,lt_wbs_update,lt_wbs_updatex.
LOOP AT gt_excel INTO gs_excel FROM lv_tabix.
IF gs_excel-pspnr <> ls_head-pspnr OR gs_excel-level <> ls_head-level.
EXIT.
ENDIF.
CLEAR ls_wbs_element.
IF gs_excel-level = '1'. " 第一层
ls_wbs_import-wbs_element = gs_excel-posid1. " WBS元素
ELSEIF gs_excel-level = '2'. " 第二层
ls_wbs_import-wbs_up = gs_excel-posid1. " 上层元素
ls_wbs_import-wbs_element = gs_excel-posid1 && '/' && gs_excel-posid2. " WBS元素
ELSEIF gs_excel-level = '3'. " 第三层
ls_wbs_import-wbs_up = gs_excel-posid1 && '/' && gs_excel-posid2. " 上层元素
ls_wbs_import-wbs_element = gs_excel-posid1 && '/' && gs_excel-posid2 && '/' && gs_excel-posid3. " WBS元素
ENDIF.
ls_wbs_import-description = gs_excel-post2. " WBS描述
ls_wbs_import-PROJ_TYPE = gs_excel-prart. " WBS类型
APPEND ls_wbs_import TO lt_wbs_import.
" WBS创建后修改简明ID(WBS元素)
ls_project_definition-project_definition = gs_excel-pspnr. "项目定义
ls_project_definition_upd-project_definition = 'X'. "项目定义
"项目处理方法更新
lv_seqno = lv_seqno + 1.
ls_method_project-refnumber = lv_seqno. "参考号
ls_method_project-objecttype = co1_type-wbs_element. "对象类型
ls_method_project-method = co1_meth-update. "项目更新
ls_method_project-objectkey = gs_excel-pspnr. "项目定义
APPEND ls_method_project TO lt_method_project.
CLEAR ls_method_project.
"项目处理方法保存
ls_method_project-method = co1_meth-save.
APPEND ls_method_project TO lt_method_project.
CLEAR: ls_method_project.
ls_wbs_update-wbs_element = ls_wbs_import-wbs_element.
ls_wbs_update-project_definition = gs_excel-pspnr.
ls_wbs_update-short_id = gs_excel-poski.
APPEND ls_wbs_update TO lt_wbs_update.
ls_wbs_updatex-short_id = 'X'.
APPEND ls_wbs_updatex TO lt_wbs_updatex.
ENDLOOP.
" 初始化
CHECK lt_wbs_import IS NOT INITIAL.
REFRESH lt_return.
CALL FUNCTION 'BAPI_PS_INITIALIZATION'.
" 创建WBS
CALL FUNCTION 'BAPI_BUS2054_CREATE_MULTI'
EXPORTING
i_project_definition = lv_project
TABLES
it_wbs_element = lt_wbs_import
et_return = lt_return.
SORT lt_return BY type message_v1 message_v2.
READ TABLE lt_return TRANSPORTING NO FIELDS WITH KEY type = 'E' BINARY SEARCH.
IF sy-subrc <> 0.
CLEAR:lt_return.
" 提交\
SET UPDATE TASK LOCAL. "同步执行WBS创建
CALL FUNCTION 'BAPI_PS_PRECOMMIT'
TABLES
et_return = lt_return.
READ TABLE lt_return TRANSPORTING NO FIELDS WITH KEY type = 'E' BINARY SEARCH.
IF sy-subrc <> 0.
CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'.
" 更新日志信息
gs_excel-msg = gs_excel-msg && TEXT-m03. " WBS创建成功
gs_excel-light = icon_green_light.
MODIFY gt_excel FROM gs_excel TRANSPORTING msg light WHERE pspnr = ls_head-pspnr AND level = ls_head-level.
* " 更新简明ID(WBS元素)
* SET UPDATE TASK LOCAL. "同步执行WBS创建
* CALL FUNCTION 'BAPI_PROJECT_MAINTAIN'
* EXPORTING
* i_project_definition = ls_project_definition
* i_project_definition_upd = ls_project_definition_upd
* IMPORTING
* return = ls_return1
* TABLES
* i_method_project = lt_method_project
* e_message_table = lt_message
* I_WBS_ELEMENT_TABLE = lt_wbs_update
* I_WBS_ELEMENT_TABLE_UPDATE = lt_wbs_updatex.
* IF ls_return1-type <> 'E'.
* CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'.
* ELSE.
* CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.
* ENDIF.
ELSE.
CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.
" 更新日志信息
gs_excel-msg = gs_excel-msg && TEXT-m04. " WBS创建失败
gs_excel-light = icon_red_light.
LOOP AT lt_return INTO ls_return WHERE type = 'E'.
gs_excel-msg = gs_excel-msg && ls_return-message.
ENDLOOP.
MODIFY gt_excel FROM gs_excel TRANSPORTING msg light WHERE pspnr = ls_head-pspnr AND level = ls_head-level.
ENDIF.
ELSE.
CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.
" 更新日志信息
gs_excel-msg = gs_excel-msg && TEXT-m04. " WBS创建失败
gs_excel-light = icon_red_light.
LOOP AT lt_return INTO ls_return WHERE type = 'E'.
gs_excel-msg = gs_excel-msg && ls_return-message.
ENDLOOP.
MODIFY gt_excel FROM gs_excel TRANSPORTING msg light WHERE pspnr = ls_head-pspnr AND level = ls_head-level.
ENDIF.
ENDIF.
ENDLOOP.
" 筛选项目
lt_head = gt_excel.
SORT lt_head BY pspnr level light.
DELETE lt_head WHERE light = icon_red_light.
DELETE ADJACENT DUPLICATES FROM lt_head COMPARING pspnr level.
SORT gt_excel BY pspnr level posid3.
LOOP AT lt_head INTO ls_head.
CLEAR:lv_project,lt_wbs_element,lt_return.
" 按项目号,层级,依次更新wbs元素短标识
READ TABLE gt_excel TRANSPORTING NO FIELDS WITH KEY pspnr = ls_head-pspnr level = ls_head-level BINARY SEARCH.
IF sy-subrc = 0.
lv_tabix = sy-tabix.
" 按层级汇总WBS元素
CLEAR: lt_wbs_import,lt_method_project,lt_wbs_update,lt_wbs_updatex.
lv_seqno = '000000'.
LOOP AT gt_excel INTO gs_excel FROM lv_tabix.
IF gs_excel-pspnr <> ls_head-pspnr OR gs_excel-level <> ls_head-level.
EXIT.
ENDIF.
IF gs_excel-light = icon_red_light.
CONTINUE.
ENDIF.
CLEAR ls_wbs_element.
IF gs_excel-level = '1'. " 第一层
ls_wbs_import-wbs_element = gs_excel-posid1. " WBS元素
ELSEIF gs_excel-level = '2'. " 第二层
ls_wbs_import-wbs_element = gs_excel-posid1 && '/' && gs_excel-posid2. " WBS元素
ELSEIF gs_excel-level = '3'. " 第三层
ls_wbs_import-wbs_element = gs_excel-posid1 && '/' && gs_excel-posid2 && '/' && gs_excel-posid3. " WBS元素
ENDIF.
" WBS创建后修改简明ID(WBS元素)
ls_project_definition-project_definition = gs_excel-pspnr. "项目定义
ls_project_definition_upd-project_definition = 'X'. "项目定义
"项目处理方法更新
lv_seqno = lv_seqno + 1.
ls_method_project-refnumber = lv_seqno. "参考号
ls_method_project-objecttype = co1_type-wbs_element. "对象类型
ls_method_project-method = co1_meth-update. "项目更新
ls_method_project-objectkey = ls_wbs_import-wbs_element. "项目定义
APPEND ls_method_project TO lt_method_project.
CLEAR ls_method_project.
ls_wbs_update-wbs_element = ls_wbs_import-wbs_element.
ls_wbs_update-project_definition = gs_excel-pspnr.
ls_wbs_update-short_id = gs_excel-poski.
APPEND ls_wbs_update TO lt_wbs_update.
ls_wbs_updatex-short_id = 'X'.
APPEND ls_wbs_updatex TO lt_wbs_updatex.
ENDLOOP.
"项目处理方法保存
ls_method_project-method = co1_meth-save.
APPEND ls_method_project TO lt_method_project.
CLEAR: ls_method_project.
" 初始化
CHECK lt_wbs_update IS NOT INITIAL.
REFRESH lt_return.
" 更新简明ID(WBS元素)\
CALL FUNCTION 'BAPI_PROJECT_MAINTAIN'
EXPORTING
i_project_definition = ls_project_definition
i_project_definition_upd = ls_project_definition_upd
IMPORTING
return = ls_return1
TABLES
i_method_project = lt_method_project
e_message_table = lt_message
I_WBS_ELEMENT_TABLE = lt_wbs_update
I_WBS_ELEMENT_TABLE_UPDATE = lt_wbs_updatex.
IF ls_return1-type <> 'E'.
CALL FUNCTION 'BAPI_TRANSACTION_COMMIT'.
ELSE.
CALL FUNCTION 'BAPI_TRANSACTION_ROLLBACK'.
ENDIF.
ENDIF.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_VALUE_CHECK
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_value_check .
SORT gt_excel BY pspnr level.
LOOP AT gt_excel ASSIGNING <fs_excel>.
IF <fs_excel>-level = '1'.
IF <fs_excel>-posid1 IS INITIAL OR
<fs_excel>-posid2 IS NOT INITIAL OR
<fs_excel>-posid3 IS NOT INITIAL.
<fs_excel>-light = icon_red_light.
<fs_excel>-msg = TEXT-m06. " 请检查层级与WBS元素层级关系是否一致
ENDIF.
ELSEIF <fs_excel>-level = '2'.
IF <fs_excel>-posid1 IS INITIAL OR
<fs_excel>-posid2 IS INITIAL OR
<fs_excel>-posid3 IS NOT INITIAL.
<fs_excel>-light = icon_red_light.
<fs_excel>-msg = TEXT-m06. " 请检查层级与WBS元素层级关系是否一致
ENDIF.
ELSEIF <fs_excel>-level = '3'.
IF <fs_excel>-posid1 IS INITIAL OR
<fs_excel>-posid2 IS INITIAL OR
<fs_excel>-posid3 IS INITIAL.
<fs_excel>-light = icon_red_light.
<fs_excel>-msg = TEXT-m06. " 请检查层级与WBS元素层级关系是否一致
ENDIF.
ELSE.
<fs_excel>-light = icon_red_light.
<fs_excel>-msg = TEXT-m05. " 层级只能为1,2,3其中一种
ENDIF.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_READ_EXCEL_NEW
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> p1 text
*& <-- p2 text
*&---------------------------------------------------------------------*
FORM frm_read_excel_new .
DATA lv_value(255) TYPE c.
DATA lv_flag TYPE char1.
DATA lv_count LIKE sy-subrc.
DATA lv_message TYPE string.
DATA lv_index TYPE i.
FIELD-SYMBOLS: <fs_value>.
REFRESH gt_xlstmp.
" 读取 EXCEL 文件数据
CALL FUNCTION 'ALSM_EXCEL_TO_INTERNAL_TABLE'
EXPORTING
filename = p_fname
i_begin_col = 1
i_begin_row = 2 " 从第 4 行开始 读取
i_end_col = 14 " 结束列
i_end_row = 65536 " 结束行
TABLES
intern = gt_xlstmp " 存储读取的记录 行、列、值
EXCEPTIONS
inconsistent_parameters = 1
upload_ole = 2
OTHERS = 3.
IF sy-subrc <> 0 .
MESSAGE ID sy-msgid TYPE 'S' NUMBER sy-msgno DISPLAY LIKE sy-msgty
WITH sy-msgv1 sy-msgv2 sy-msgv3 sy-msgv4.
STOP.
ENDIF.
"将gt_xlstmp的数据遍历到gt_alv内表中
"gt_xlstmp 中按行列的顺序将每个单元格值放在value中
LOOP AT gt_xlstmp INTO gs_xlstmp. " 按先行后列遍历每个单元格
lv_index = gs_xlstmp-col. " 获取当前列数
ASSIGN COMPONENT lv_index OF STRUCTURE gs_excel TO <fs_value>. " 将内表第index列的字段地址复制给指针<fs_value>
" 对特殊类型字段可以用case语句单独处理,比如单位字段或者需要加前导零的字段
" 用数字其实后期不好维护,中间插入字段就会导致index变更
* CASE lv_index.
* WHEN 11. " 单位字段需要外码转内码
* PERFORM frm_meins_in USING gs_xlstmp-value.
* WHEN 12. " 物料号需要加前导0
* PERFORM frm_add_zero USING gs_xlstmp-value.
* WHEN 14. " wbs元素需要外码转内码
* PERFORM frm_pspnr_in USING gs_xlstmp-value.
* WHEN 15. " 外部日期yyyy*MM*dd转内部yyyyMMdd才可导入
* REPLACE ALL OCCURRENCES OF REGEX '[^0-9]' IN gs_xlstmp-value WITH ''.
* WHEN OTHERS.
* ENDCASE.
MOVE gs_xlstmp-value TO <fs_value>. " 将单元格值赋值给指向结构中字段的指针
CLEAR gs_xlstmp.
AT END OF row. " 遍历至当行的最后一列时,将整行append至内表中
APPEND gs_excel TO gt_excel.
CLEAR gs_excel.
ENDAT.
ENDLOOP.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form frm_meins_in
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> GS_OUT_MEINS
*&---------------------------------------------------------------------*
FORM frm_meins_in USING p1.
CALL FUNCTION 'CONVERSION_EXIT_CUNIT_INPUT'
EXPORTING
input = p1
language = sy-langu
IMPORTING
output = p1
EXCEPTIONS
unit_not_found = 1
OTHERS = 2.
IF sy-subrc <> 0.
* Implement suitable error handling here
ENDIF.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form FRM_ADD_ZERO
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> P1
*&---------------------------------------------------------------------*
FORM frm_add_zero USING p1.
CALL FUNCTION 'CONVERSION_EXIT_ALPHA_INPUT'
EXPORTING
input = p1
IMPORTING
output = p1.
ENDFORM.
*&---------------------------------------------------------------------*
*& Form frm_pspnr_in
*&---------------------------------------------------------------------*
*& text
*&---------------------------------------------------------------------*
*& --> GS_OUT_PS_PSP_PNR
*&---------------------------------------------------------------------*
FORM frm_pspnr_in USING p1.
CALL FUNCTION 'CONVERSION_EXIT_ABPSP_INPUT'
EXPORTING
input = p1
IMPORTING
output = p1
EXCEPTIONS
not_found = 1
OTHERS = 2.
IF sy-subrc <> 0.
* Implement suitable error handling here
ENDIF.
ENDFORM.
ABAP 批导模板(项目+WBS)
于 2023-03-31 09:59:25 首次发布
该ABAP程序用于读取Excel文件中的项目和WBS元素数据,进行数据验证,然后在ALV表格中展示。程序包括Excel文件上传、数据读取、字段映射、ALV控制台配置以及项目和WBS元素的创建或更新操作。
摘要由CSDN通过智能技术生成