很多年没有写代码了,很多语法都忘记了,我就用入门级语法做一个示例。
言归正传,首先把采购订单是由于什么原因创建的(基于MRP逻辑的都可以追溯,手工创建的可能没有源头),把需求的来源记录起来(当然也可以通过事务码:MD09查询单个需求来源)。
当发现有呆料时,根据呆料的批次,找到相关的采购订单(采购订单收货时产生批次),再根据采购订单找到相关的需求(独立需求 或 销售订单 或预留单等)。
我只是简单的做个例子,希望能起到抛转引玉,谢谢!
先封装一个RFC接口(Z_RFC_POINREQTABLE),
在接口Z_RFC_POINREQTABLE的源代码中写入:
FUNCTION z_rfc_poinreqtable.
*"----------------------------------------------------------------------
*"*"本地接口:
*" IMPORTING
*" VALUE(T_TCODE) TYPE TCODE OPTIONAL
*" VALUE(T_PONUMBER) TYPE EKKO-EBELN OPTIONAL
*"----------------------------------------------------------------------
WAIT UP TO 6 SECONDS."等创建PO结束
* * 采购订单保存后保存追溯信息 solin 2021-10-16
DATA:BEGIN OF gs_imdrqx,"追溯结构定义
ebeln TYPE mdbs-ebeln,
ebelp TYPE mdbs-ebelp,
etenr TYPE mdbs-etenr,
zmatnr TYPE mdbs-matnr,
zwerks TYPE mdbs-werks,
menge TYPE ekpo-menge,
iporg TYPE msxxlist-hostadr, "
hostip(20) TYPE c, "
host(18) TYPE c, "
aenam TYPE sy-uname, "
laeda TYPE sy-datum, "
times TYPE sy-uzeit, "
mandt TYPE zmmt022a-mandt.
INCLUDE TYPE mdrq.
DATA:END OF gs_imdrqx.
TYPES: BEGIN OF md_po,"根据采购订单号 获取采购订单明细主资料
ebeln TYPE mdbs-ebeln,
ebelp TYPE mdbs-ebelp,
etenr TYPE mdbs-etenr,
matnr TYPE mdbs-matnr,
werks TYPE mdbs-werks,
menge TYPE mdbs-menge,
END OF md_po.
DATA :
lt_imdrqx TYPE TABLE OF mdrq, "系统追溯结构
lv_edelps TYPE mdps-delps, " 采购订单行号 MD_PEGGING_NODIALOG方法 要求参数类型必需一样
lv_edelnr TYPE mdps-del12, " 采购订单号 MD_PEGGING_NODIALOG方法 要求参数类型必需一样
lv_edelet TYPE mdps-delet, " 计划行号 MD_PEGGING_NODIALOG方法 要求参数类型必需一样
lt_mdpo TYPE TABLE OF md_po, "追溯订单信息
gs_mdpo TYPE md_po, "追溯订单信息
gt_zmmt022a TYPE TABLE OF zmmt022a, "采购订单追溯 创建后不变更
gs_zmmt022a TYPE zmmt022a, "采购订单追溯
gt_zmmt022b TYPE TABLE OF zmmt022b, "采购订单追溯 创建可修改
gs_zmmt022b TYPE zmmt022b. "采购订单追溯
"查询采购订单明细
SELECT ebeln ebelp etenr matnr werks menge
INTO TABLE lt_mdpo
FROM mdbs
WHERE ebeln = T_PONUMBER.
IF sy-subrc EQ 0 .
LOOP AT lt_mdpo INTO gs_mdpo.
lv_edelnr = gs_mdpo-ebeln.
lv_edelps = gs_mdpo-ebelp.
lv_edelet = gs_mdpo-etenr.
CALL FUNCTION 'MD_PEGGING_NODIALOG' "与事务码:MD09功能一样
EXPORTING
ewerks = gs_mdpo-werks "工厂
ematnr = gs_mdpo-matnr "料号
eberid = '' "
edelkz = 'BE' "采购订单单
edelnr = lv_edelnr "采购订单号
edelps = lv_edelps "采购订单行号
edelet = lv_edelet "采购订单计划行号
TABLES
imdrqx = lt_imdrqx
EXCEPTIONS
error = 1
no_requirements_found = 2
order_not_found = 3
OTHERS = 4.
IF lt_imdrqx IS NOT INITIAL.
LOOP AT lt_imdrqx INTO DATA(ls_imdrqx).
MOVE-CORRESPONDING ls_imdrqx TO gs_imdrqx.
"保存追溯源条件
gs_imdrqx-ebeln = gs_mdpo-ebeln.
gs_imdrqx-ebelp = gs_mdpo-ebelp.
gs_imdrqx-etenr = gs_mdpo-etenr.
gs_imdrqx-zmatnr = gs_mdpo-matnr.
gs_imdrqx-zwerks = gs_mdpo-werks.
gs_imdrqx-menge = gs_mdpo-menge.
"以下 保存时间、用户名、IP等信息
gs_imdrqx-mandt = sy-mandt.
gs_imdrqx-aenam = sy-uname.
gs_imdrqx-laeda = sy-datum.
gs_imdrqx-times = sy-uzeit.
CALL FUNCTION 'TH_USER_INFO' " Get user IP,hostname
EXPORTING
client = sy-mandt
user = sy-uname
IMPORTING
hostaddr = gs_imdrqx-iporg
terminal = gs_imdrqx-host
EXCEPTIONS
OTHERS = 1.
* *"Conv.IP addr to format "xxx.xxx.xxx.xxx" 获取IP地址
CALL FUNCTION 'GWY_IPADR2STRING' "Conv.IP addr
EXPORTING
ipadr = gs_imdrqx-iporg
IMPORTING
string = gs_imdrqx-hostip.
MOVE-CORRESPONDING gs_imdrqx TO gs_zmmt022a.
MOVE-CORRESPONDING gs_imdrqx TO gs_zmmt022b.
APPEND gs_zmmt022a TO gt_zmmt022a.
APPEND gs_zmmt022b TO gt_zmmt022b.
* MODIFY zmmt022A FROM gs_zmmt022A.
* MODIFY zmmt022A FROM TABLE gt_zmmt022A.
CLEAR:gs_imdrqx,ls_imdrqx,gs_zmmt022a,gs_zmmt022b,lv_edelnr,lv_edelps,lv_edelet."清空临时工作表和变量
ENDLOOP.
IF gt_zmmt022a IS NOT INITIAL AND T_TCODE = 'ME21N'."创建时保存需求相关数据
MODIFY zmmt022a FROM TABLE gt_zmmt022a.
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
ROLLBACK WORK.
ENDIF.
ENDIF.
IF gt_zmmt022b IS NOT INITIAL.
MODIFY zmmt022b FROM TABLE gt_zmmt022b."创建变更时都保存相关数据
IF sy-subrc EQ 0.
COMMIT WORK AND WAIT.
ELSE.
ROLLBACK WORK.
ENDIF.
ENDIF.
CLEAR : lt_imdrqx , gt_zmmt022a, gt_zmmt022b."清空暂时表
ENDIF.
CLEAR : gs_mdpo.
ENDLOOP.
CLEAR : lt_mdpo.
ENDIF.
ENDFUNCTION.
再做一个接口Z_RFC_POINREQTABLE1,本地调用,封装上面一个接口(Z_RFC_POINREQTABLE),形成多线程调用(可能叫法不对)。
接口原代码Z_RFC_POINREQTABLE1:
FUNCTION Z_RFC_POINREQTABLE1.
*"----------------------------------------------------------------------
*"*"本地接口:
*" IMPORTING
*" REFERENCE(T_TCODE) TYPE TCODE
*" REFERENCE(T_PONUMBER) TYPE EKPO-EBELN
*"----------------------------------------------------------------------
data: l_taskname type char30.
l_taskname = T_PONUMBER && sy-uname.
CALL FUNCTION 'Z_RFC_POINREQTABLE' starting new task l_taskname
EXPORTING
T_TCODE = T_TCODE
T_PONUMBER = T_PONUMBER.
ENDFUNCTION.
通过在程序LMEGUICJI 的SAVE方法做一个增强(不要放到最后,不然影响提示信息),代码如下:
*{ INSERT S4DK909122 1
** 采购订单保存后保存追溯信息 solin 2021-10-16
if ( sy-tcode ='ME21N' or sy-tcode = 'ME22N' or sy-tcode = 'ME23N' AND sy-tcode ='ME29N').
DAta : l_ebeln type ekpo-ebeln.
l_ebeln = l_po->po_number.
CALL FUNCTION 'Z_RFC_POINREQTABLE1'
EXPORTING
T_TCODE = sy-tcode
T_PONUMBER = l_ebeln.
ENDIF.
*} INSERT
最终查询出来,一个采购订单来源三张独立需求: