使用BAPI_GOODSMVT_CREATE以编程方式创建文档批次



问题摘要

通过自定义ABAP代码进行自动文档批量处理

我的雇主希望对来自外部供应商的一些产品执行自动文档批量处理,我正试图通过自定义和ABAP来设置这一点。

在我看来,Documentary Batches只能通过MIGO使用——在任何情况下,我都无法找到一个合适的解决方案来用程序分配它们,而我能想出的任何一个破解的解决方案似乎都是不够和不稳定的。

我有什么途径来解决这个问题?

增强BAPI_GOODSMVT_CREATE

我能通过BAPI_GOODSMVT_CREATE这样的东西来完成吗?

增强PPPI消息目的地

我还特别需要它来通过PPPI处理消费消息,我想在标准Message DestinationPI04、FMCOCI_CONFIRM_MATERIAL_CONS的基础上进行构建。

此FM创建一个材料文档,但不通过BAPI_GOODSMVT_CREATEFM。

但是,它确实使用MB_CREATE_GOODS_MOVEMENT

我已经尝试过的

MIGO基于快照的一次性破解解决方案

我为一个区域制定了破解解决方案,在那里我观察MIGO执行了哪些表更新以及使用了哪些数据(通过FM的VB_INSERT_BATCHVB_BATCH_WHERE_USED_LIST(,然后手动填写这些结构。

然而,提供所有所需的信息对于其他实现领域来说是不可行的,因为它们没有所有必要的可用值,而且它不包括可能需要其他参数的不可预见的情况。

读取BAPI_GOODSMVT_CREATE代码

我试过监视BAPI_GOODSMVT_CREATE是否执行相同的FM,但只发现它正在访问VB_BATCH_WHERE_USED_LIST

似乎可以通过控制内存IDDocumentary Batch #1Documentary Batch #2Documentary Batch #3Documentary Batch #5来激活此功能(请参见FMVBDBDM_DATA_POST_IM(,但这需要填写大量数据,包括名为DOCUBATCH_SCREEN_FIELDS的结构,这再次使其看起来可能不是正确的方法。

无论如何,这仍然不允许我通过表MCHA和MCH1来维护批处理。

基于MIGO快照的破解解决方案

以下是我的破解解决方案的外观。同样,这不是解决问题的可行方法,因为其他实施领域没有立即可用的材料文件:

FUNCTION zproxy_mdr_goodsreceipt.
*"----------------------------------------------------------------------
*"*"Local Interface:
*"  IMPORTING
*"     VALUE(IS_GOODSRECEIPT_HEAD) TYPE  ZPROXY_GOODSREC_HEAD
*"     VALUE(IT_GOODSRECEIPT_ITEM) TYPE  ZPROXY_GOODSREC_ITEM_T
*"     REFERENCE(I_CREATE_TO_FROM_REQUIREMENTS) TYPE  FLAG DEFAULT '-'
*"  EXPORTING
*"     REFERENCE(E_GOODSMVT_MSG_IDNO) TYPE  CHAR23
*"     REFERENCE(E_MBLNR) TYPE  MBLNR
*"     REFERENCE(E_TO_CREATION_SUBRC) TYPE  SY-SUBRC
*"     REFERENCE(E_LGNUM_ERROR) TYPE  LGNUM
*"     REFERENCE(E_TBNUM_ERROR) TYPE  TBNUM
*"     REFERENCE(E_DOCBATCH_SUBRC) TYPE  SY-SUBRC
*"     REFERENCE(E_DOCBATCH_MSG_IDNO) TYPE  CHAR23
*"     REFERENCE(E_CLASSNUM) TYPE  BAPI1003_KEY-CLASSNUM
*"     REFERENCE(E_OBJKEY) TYPE  BAPI1003_KEY-OBJECT
*"  EXCEPTIONS
*"      GOODSMVT_FAILED
*"      NO_TRANSFER_REQUIREMENTS
*"      TRANSFER_ORDER_CREATION_ERROR
*"----------------------------------------------------------------------
FIELD-SYMBOLS: <return>         TYPE bapiret2,
<goods_rec_item> TYPE zproxy_goodsrec_item,
<mseg>           TYPE mseg,
<char_char>      TYPE bapi1003_alloc_values_char,
<ltap_creat>     TYPE LTAP_CREAT.
DATA: ls_header   TYPE bapi2017_gm_head_01,
ls_code     TYPE bapi2017_gm_code,
ls_item     TYPE bapi2017_gm_item_create,
lt_item     TYPE STANDARD TABLE OF bapi2017_gm_item_create,
lt_return   TYPE STANDARD TABLE OF bapiret2,
ls_headret  TYPE bapi2017_gm_head_ret,
l_mblnr     LIKE bapi2017_gm_head_ret-mat_doc,
l_docubatch TYPE charg_d,
l_subrc     TYPE sy-subrc,
lt_mseg     TYPE STANDARD TABLE OF mseg.
CLEAR l_subrc.

*     ############################## Create goods movement ##############################
*     Build structures
MOVE-CORRESPONDING is_goodsreceipt_head TO ls_header.
ls_code-gm_code = '01'.
LOOP AT it_goodsreceipt_item ASSIGNING <goods_rec_item>.
MOVE-CORRESPONDING <goods_rec_item> TO ls_item.
APPEND ls_item TO lt_item.
ENDLOOP.
*     BAPI call
CALL FUNCTION 'BAPI_GOODSMVT_CREATE'
EXPORTING
goodsmvt_header  = ls_header
goodsmvt_code    = ls_code
IMPORTING
goodsmvt_headret = ls_headret
materialdocument = l_mblnr
TABLES
goodsmvt_item    = lt_item
return           = lt_return.
*     Check errors
READ TABLE lt_return ASSIGNING <return> WITH KEY type = 'E'.
IF sy-subrc = 0.
e_goodsmvt_msg_idno = <return>-id && <return>-number.
ROLLBACK WORK.
RAISE goodsmvt_failed.
ELSE.
e_mblnr = l_mblnr.
COMMIT WORK AND WAIT. "Wait for TO requirements to be created
ENDIF.
*     Only proceede if Material Document has been successfully posted
CHECK l_subrc = 0 AND l_mblnr IS NOT INITIAL.
*     ############################## Update with Documentary Batch ###################################
DATA: lt_chvw      TYPE STANDARD TABLE OF chvw,
ls_chvw      TYPE chvw,
lt_mch1      TYPE STANDARD TABLE OF mch1,
ls_mch1      TYPE mch1,
lt_mcha      TYPE STANDARD TABLE OF mcha,
ls_mcha      TYPE mcha,
lt_mchb      TYPE STANDARD TABLE OF mchb,
lt_mska      TYPE STANDARD TABLE OF mska,
lt_mspr      TYPE STANDARD TABLE OF mspr,
lt_char_num  TYPE STANDARD TABLE OF bapi1003_alloc_values_num,
lt_char_char TYPE STANDARD TABLE OF bapi1003_alloc_values_char,
lt_char_curr TYPE STANDARD TABLE OF bapi1003_alloc_values_curr,
l_objkey     TYPE bapi1003_key-object,
l_classnum   TYPE bapi1003_key-classnum,
l_atnam      TYPE atnam.
REFRESH lt_chvw.
*     Get material document items
SELECT *
FROM mseg
INTO TABLE lt_mseg
WHERE mblnr = l_mblnr.
*     Perpare docubatch registration data
LOOP AT it_goodsreceipt_item ASSIGNING <goods_rec_item>.
*       Generate class num and atnam from plant
CONCATENATE 'PI_' <goods_rec_item>-plant INTO l_classnum.
CONCATENATE 'Z_DOC_BATCH_' <goods_rec_item>-plant INTO l_atnam.
*       Get material docubatch usage characteristic
REFRESH: lt_return,
lt_char_num,
lt_char_char,
lt_char_curr.
l_objkey(18) = <goods_rec_item>-material.
CALL FUNCTION 'BAPI_OBJCL_GETDETAIL'
EXPORTING
objectkey       = l_objkey
objecttable     = 'MARA'
classnum        = l_classnum
classtype       = '001'
TABLES
allocvaluesnum  = lt_char_num
allocvalueschar = lt_char_char
allocvaluescurr = lt_char_curr
return          = lt_return.
LOOP AT lt_return ASSIGNING <return> WHERE type = 'E'. "Check for errors
*         Couldn't read characteristic, assume no docubatch handling
e_docbatch_subrc = '1'.
e_docbatch_msg_idno = <return>-id && <return>-number.
e_classnum = l_classnum.
e_objkey = l_objkey.
CONTINUE.
ENDLOOP.
READ TABLE lt_char_char ASSIGNING <char_char> WITH KEY charact = l_atnam.
IF sy-subrc <> 0 OR <char_char>-value_neutral = 0.
*         No docubatch value
CONTINUE.
ENDIF.

*       Get associated material document item
READ TABLE lt_mseg ASSIGNING <mseg>
WITH KEY mblnr = ls_headret-mat_doc
mjahr = ls_headret-doc_year
bwart = <goods_rec_item>-move_type
matnr = <goods_rec_item>-material
werks = <goods_rec_item>-plant
menge = <goods_rec_item>-entry_qnt
meins = <goods_rec_item>-entry_uom
hsdat = <goods_rec_item>-prod_date
kzbew = <goods_rec_item>-mvt_ind
lgort = <goods_rec_item>-stge_loc.
IF sy-subrc <> 0.
*         No associated material document item
CONTINUE.
ENDIF.
*       Check docubatch type
IF <char_char>-value_neutral <> 0.
*         Perform basic docubatch actions (MCHA and MCH1)
*         Verify that docubatch nr is assigned
IF <goods_rec_item>-vendrbatch IS INITIAL.
*            !!!!!!!!!!!!! Venderbatch not filled even though material is docubatch managed, what to do? !!!!!!!!!!!!!!!
CONTINUE.
ENDIF.
*         Prepare data for docubatch registration
CLEAR: ls_mch1,
ls_mcha.
ls_mch1-matnr = <goods_rec_item>-material.
ls_mch1-charg = <goods_rec_item>-vendrbatch.
ls_mch1-ersda = sy-datum.
ls_mch1-ernam = sy-uname.
ls_mch1-ersda_tmstp = sy-datum && sy-uzeit.
ls_mch1-ersda_tz_sys = sy-tzone.
ls_mch1-ersda_tz_usr = sy-zonlo.
MOVE-CORRESPONDING ls_mch1 TO ls_mcha. "Same fields from MCH1 are included in MCHA
ls_mcha-werks = <goods_rec_item>-plant.
APPEND: ls_mch1 TO lt_mch1,
ls_mcha TO lt_mcha.
ENDIF.
IF <char_char>-value_neutral = 2. "Also include batch where-used
*         Perpare data for batch where-used registration
CLEAR ls_chvw.
ls_chvw-matnr = <goods_rec_item>-material.
ls_chvw-werks = <goods_rec_item>-plant.
ls_chvw-charg = <goods_rec_item>-vendrbatch.
ls_chvw-ebeln = <goods_rec_item>-po_number.
ls_chvw-ebelp = <goods_rec_item>-po_item.
ls_chvw-mblnr = ls_headret-mat_doc.
ls_chvw-mjahr = ls_headret-doc_year.
ls_chvw-zeile = <mseg>-zeile.
ls_chvw-budat = is_goodsreceipt_head-pstng_date.
ls_chvw-shkzg = 'S'. "??? VALUE ???
ls_chvw-bwart = <goods_rec_item>-move_type.
ls_chvw-kzbew = <goods_rec_item>-mvt_ind. "Goods Movement for Purchase Order
ls_chvw-menge = <goods_rec_item>-entry_qnt.
ls_chvw-meins = <goods_rec_item>-entry_uom.
APPEND ls_chvw TO lt_chvw.
ENDIF.
ENDLOOP.
*     Perform batch registration
CALL FUNCTION 'VB_INSERT_BATCH'
TABLES
zmch1         = lt_mch1
zmcha         = lt_mcha
zmchb         = lt_mchb
zmska         = lt_mska
zmspr         = lt_mspr
.
*     Perform batch where-used registration
CALL FUNCTION 'VB_BATCH_WHERE_USED_LIST'
TABLES
xchvw = lt_chvw.

为什么这还不够好,以及我需要什么

这是MIGO的快照,配置了文档批处理,但不一定涵盖所有情况。

它只适用于采购文档的上下文,不包括其他情况,如订单和销售订单。

此外,我只有必要的日期,因为上面正在创建材料文件,这不可能适用于所有实施案例。

我想知道是否有一种从自定义代码执行跟单批量处理的方法。

引用文档:

如果您使用RFID或TRM功能,或调用IDocs/BAPI,则只能以文档形式预订通过调用支持RFC的功能模块VBDBDM_DATA_MAINTIN_RFC进行批处理预先或将其结合到过程中。

所以这个功能模块可能是关键?然而,你似乎不是第一个经历这种痛苦的人。对该文件的评论如下:

Documentary Batch有很多限制,它似乎是SAP的半成品,因为它缺少了真实批次的许多功能。

准备好进行大量自定义增强。。。

社区的附录:以下是在这个答案两天后从原始海报中获得的解决方案,远离了他的问题。

解决方案

采购订单收货调用示例

LOOP AT it_goodsreceipt_item ASSIGNING <goods_rec_item>.
CALL FUNCTION 'VBDBDM_DATA_MAINTAIN_RFC'
EXPORTING
i_matnr            = <goods_rec_item>-material
i_werks            = <goods_rec_item>-plant
i_quantity         = <goods_rec_item>-entry_qnt
i_uom              = <goods_rec_item>-entry_uom
i_docubatch_charg  = <goods_rec_item>-vendrbatch
*       IT_DOCUBATCHES     =
i_process_id       = '01' "Goods Receipt for External Procurement
*       I_REPLACE_EXISTING_DATA       =
i_ebeln            = <goods_rec_item>-po_number
i_ebelp            = <goods_rec_item>-po_item
*       I_AUFNR            =
*       I_AUFPS            =
*       I_RSNUM            =
*       I_RSPOS            =
*       I_RSART            =
*       I_VBELN            =
*       I_POSNR            =
*       IS_DOCUBATCH_COM   =
*       I_LINE_ID          =
*       I_LGNUM            =
*       I_TANUM            =
*       I_TAPOS            =
EXCEPTIONS
parameter_error    = 1
process_not_active = 2.
ENDLOOP.
* Follow up by creating Material Document, for example through BAPI_GOODSMVT_CREATE

相关内容

  • 没有找到相关文章

最新更新