使用 IDoc 开发业务对象

可以在 SAP 中将 ABAP 扩展模块的 WebSphere 业务对象定义为 IDoc。IDoc 是 SAP 的 EDI 解决方案(称为 ALE,应用程序链接启用)的一部分。它们的定义存储在 SAP 的 BOR(业务对象资源库)中,且可以在 SAP 系统中在全局范围访问它。IBM WebSphere Business Integration mySAP.com 适配器实现 ALE 的定义部分以解释 SAP 应用程序中的 WebSphere 业务对象并对它们进行语法分析,以准备好供 SAP 本机 API 使用。适配器提供了一个 IDoc 处理程序,该 IDoc 处理程序支持使用 IDoc 开发的业务对象。

IDoc 处理程序由两个功能模块组成。其它 ABAP 处理程序(如“动态检索”和“动态事务”)仅为单个功能模块。

Y_XR_DO_VERB_NEXTGEN 将业务对象数据传递至 IDoc 处理程序 Y_XR_IDOC_HANDLER。根据特定于应用程序的信息,Y_XR_IDOC_HANDLER 将业务对象数据重新格式化为由特定于应用程序的信息指定的 IDoc 的结构。在重新格式化之后,业务对象数据被 传递至特定于对象的 IDoc 处理程序(基于业务对象的对象/查询描述组合),该过程处理与 SAP 本机 API 的集成。一旦特定于对象的 IDoc 处理程序完成对业务对象数据的处理,它以 IDoc 格式将业务对象数据返回至 Y_XR_IDOC_HANDLER。业务对象数据现在转换回其原始格式并返回至 Y_XR_DO_VERB_NEXTGEN

图 75 举例说明了 IDoc 处理程序的基本体系结构。

图 75. IDoc 处理程序体系结构


要使用适配器提供的 IDoc 处理程序,您必须在 SAP 应用程序中定义 IDoc。可以使用 SAP 交付的或客户构建的 IDoc。因为 IDoc 定义必须反映 SAP 的 WebSphere 业务对象的定义,所以适配器在 IBM WebSphere InterChange Server 连接器工具(事务 YXR1)中提供了一个工具,您可以使用该工具来基于 IDoc 生成 WebSphere 业务对象定义。

必须已在 SAP 应用程序中创建了 WebSphere 业务对象,然后才能生成业务对象定义。要基于 IDoc 创建业务对象定义:

  1. 转至“IBM WebSphere InterChange Server 连接器工具”窗口(事务 YXR1)。
  2. 从“定制”菜单,单击“维护对象”。
  3. 创建新的对象名。

有关如何将特定于应用程序的信息用于查询描述功能的更多信息,请参阅"传递至 ABAP 处理程序的业务对象数据"

在定义 IDoc 之后,为业务对象必须支持的每个查询描述创建一个功能模块。每个功能都应具有以下接口以确保 Y_XR_IDOC_HANDLER 可以调用它:

*"       IMPORTING
 *"          VALUE(OBJECT_KEY_IN) LIKE  YXR_EVENT-OBJ_KEY OPTIONAL
 *"          VALUE(INPUT_METHOD) LIKE  BDWFAP_PAR-INPUTMETHD
 *"                             OPTIONAL
 *"             VALUE(LOG_NUMBER) LIKE  YXR_LOG_H-LOG_NR OPTIONAL
 *"       EXPORTING
 *"             VALUE(OBJECT_KEY_OUT) LIKE  YXR_EVENT-OBJ_KEY
 *"             VALUE(RETURN_CODE) LIKE  YXR_RFCRC-YXR_RFCRC
 *"             VALUE(RETURN_TEXT) LIKE  YXR_EVENT-OBJ_KEY
 *"       TABLES
 *"              IDOC_DATA STRUCTURE  EDIDD
 

IDoc 处理程序和创建、更新和删除查询描述

支持创建、更新和删除操作的 IDoc 处理程序接收已格式化为 IDoc 的业务对象数据。这些操作的角色是将业务对象数据与 SAP 的“调用事务”API 集成在一起并生成对象键。仅会将对象键传递回 Y_XR_IDOC_HANDLER,而不会传递业务对象数据。Y_XR_IDOC_HANDLER 将业务对象数据存储在内存中,并将对象键插入父业务对象中标记为 isKey 的第一个属性中。然后,Y_XR_IDOC_HANDLER 将业务对象数据传递回连接器。

注:
当 InterChange Server(ICS)是集成代理程序时,因为映射基础结构需要保存 ObjectEventId 以进行动态交叉引用,所以维护业务对象数据非常重要。

下面的样本代码表示以下流:

  1. 初始化全局数据。
  2. 将 IDoc 解构到工作表中。
  3. 构建 BDC。使用 YXRIFRM0 中的表单来将数据从内部表传送至 IDoc 表以在对象之间获取一致的行为。
  4. 创建“调用事务”。
  5. 捕获对象键。

以下样本代码支持 SAP 销售报价创建:

*- Initialize working variables and internal tables
   PERFORM INITIALIZE_IN.
  
 *- I01(MF): Begin IDoc interpretation
   PERFORM LOG_UPDATE(SAPLYXR1) USING C_INFORMATION_LOG TEXT-I01
                                      SPACE SPACE SPACE.
  
 *- Interpret IDoc data structure
   IF NOT IDOC_DATA[] IS INITIAL.
  
 *- Move IDoc to internal tables
     PERFORM INTERPRET_IDOC.
  
 *- Check some of the input fields
     PERFORM CHECK_INPUT.
  
 *- If key values were missing, exit function
     IF RETURN_CODE NE 0.
       EXIT.
     ENDIF.
  
 *- E01(MF): No Idoc data lines sent for processing.
   ELSE.
  
     RETURN_CODE = 2.
     RETURN_TEXT = TEXT-E01.
     EXIT.
  
   ENDIF.
  
 *- Build the BDC session for transaction VA21.
   PERFORM BUILD_BDC_VA21.
  
 *- Call Transaction
   PERFORM LOG_UPDATE(SAPLYXR1) USING C_INFORMATION_LOG TEXT-I02
                                      'VA21' C_BLANK C_BLANK.
  
   CALL TRANSACTION 'VA21' USING BDCDATA
                            MODE INPUT_METHOD
                          UPDATE 'S'
                        MESSAGES INTO BDC_MESSAGES.
  
 *- Capture return code and object key from transaction
   PERFORM PREPARE_RETURNED_MESSAGE.
  
 ENDFUNCTION.
 

“创建”逻辑具有两个主要功能:

转换 IDOC 结构

“创建”逻辑的第一部分是执行转换任务,该任务将 IDoc 结构中的数据转换为工作数据结构。为此,您需要创建类似于下内容的代码:

loop at idoc_data.
  
     case idoc_data-segnam.
       when 'ZSQVBAK'.                  " Header Data
         move idoc_data-sdata to zsqvbak.
  
       when 'ZSQVBUK'.                  " Status Segment
         move idoc_data-sdata to zsqvbuk.
  
       when 'ZSQVBP0'.                  " Partner Header Level
         move idoc_data-sdata to zsqvbp0.
  
       when 'ZSQVBAP'.                  " Item Detail
         move idoc_data-sdata to zsqvbap.
  
       when 'ZSQVBA2'.                  " Item Detail Part 2
         move idoc_data-sdata to zsqvba2.
  
       when 'ZSQVBUP'.                  " Item Status
         move idoc_data-sdata to zsqvbup.
  
       when 'ZSQVBKD'.                  " Commerical data
         move idoc_data-sdata to zsqvbkd.
  
       when 'ZSQKONV'.                  " Condition
         move idoc_data-sdata to zsqkonv.
  
       when 'ZSQVBPA'.                  " Partner Item Level
         move idoc_data-sdata to zsqvbpa.
  
     endcase.
  
   endloop.
 

IDoc 处理程序和检索查询描述

支持“检索”查询描述的特定于对象的 IDoc 处理程序不接收来自初始 IDoc 处理程序的业务对象数据。Y_XR_IDOC_HANDLER 使用参数 OBJECT_KEY_IN 来传递业务对象数据中标记为 isKey 的第一个属性的值。IDoc 处理程序负责使用此键来使用 ABAP SQL 检索与对象的此实例相关的所有信息,并以适当的 IDoc 结构来格式化这些数据。

以下代码支持“销售报价”示例。“销售报价”对象必须从 表 VBAKVBUKVBPOVBAPVBUPVBKDKNOVVBPA 中检索数据。这些表遵循 IDoc 类型 ZSLSQUOT 的层次结构和基数。该代码执行下列操作:

  1. 初始化全局数据。
  2. 从 SAP 应用程序数据库返回业务对象数据。
  3. 根据返回的数据构建 IDoc 并将该数据返回至 Y_XR_IDOC_HANDLER

IDoc 类型 ZSLSQUOT 的代码如下:

*- Clear the interface structures.
   clear: g_text, object_key_out, return_code, return_text, idoc_data.
   refresh: idoc_data.
  
 *  If no key value is specified, log it as an error and exit.
   if object_key_in is initial or
      object_key_in = c_cxignore_const.
     perform log_update(saplyxr1) using c_error_log text-e02
                                        space space space.
     return_code = 1.
     return_text = text-e02.
     exit.
   endif.
  
   perform initialize_global_structures.
  
   perform fill_internal_tables.
   if not return_code is initial.
     exit.
   endif.
  
 * Build Idoc segments from internal tables
   perform fill_idoc_inttab.
  
   return_code = 0.
   return_text = text-s01.
  
   perform log_update(saplyxr1) using c_information_log text-s01
                                      space space space.
 endfunction.
 

两个最重要的参数是表示入站键的 OBJECT_KEY_IN 和表示出站数据的 IDOC_DATA。注意,OBJECT_KEY_IN 甚至可能是一个多键, 这取决于您定义的约定。

VBAK 表驱动子表的选择标准,因此将把每个表都装入工作表中。您可以使用 VBAK 表来检索具有其它键的子表。因此,对于“销售报价”示例,代码如下所示:

form fill_internal_tables.
  
   * Get information from VBAK, VBUK, VBAP, VBKD, KONV, VBPA
  
   select single * from vbak
          where vbeln = object_key_in.
  
   if sy-subrc <> 0.
     perform log_update(saplyxr1) using c_error_log text-e01
                                  object_key_out c_blank c_blank.
     return_code = '1'.
     g_text = text-e01.
     replace '&' with order_number into g_text.
     return_text = g_text.
  
     exit.
   endif.
  
   select single * from vbuk
          where vbeln = vbak-vbeln.
  
   select * from vbap into table t_vbap
          where vbeln = vbak-vbeln.
  
   * Continue for other tables
 

以下代码用来将请求的数据从应用程序数据库复制到内部表和工作变量。然后,该代码创建直接对应于 WebSphere 业务对象定义的段并将这些段放置在 SAP 段结构中。

在某些情况下,为了使 IDoc 类型和工作结构之间的字段紧密匹配,您可以执行对应于 ABAP 移动的命令。在其它情况下,执行从工作表至 IDoc 类型表的手工移动更可取,因为只需要移动相对较少的字段而不是移动结构中的所有字段。不过,它只用来将数据从工作数据结构转换为 IDoc 结构,然后转换为平面数据字段。

代码为:

form fill_idoc_inttab.
  
 perform fill_zsqvbak." Fill the Sales Quote Header
 perform fill_zsqvbuk." Fill the Sales Quote Status
 perform fill_zsqvbap." Fill Sales Quote Lines
  
 endform." FILL_IDOC_INTTAB
  
 *-- fill the Sales Quote Header
 form fill_zsqvbak.
  
   clear idoc_data.
   clear zsqvbak.
   idoc_data-segnam = 'ZSQVBAK'.
  
   move-corresponding vbak to zsqvbak.
   move zsqvbak to idoc_data-sdata.
   append idoc_data.
  
 endform." FILL_ZSQVBAK
  
 *-- fill the Sales Quote Header Status
 form fill_zsqvbuk.
  
   clear idoc_data.
   clear zsqvbuk.
   idoc_data-segnam = 'ZSQVBUK'.
  
   move-corresponding vbuk to zsqvbuk.
   move zsqvbuk to idoc_data-sdata.
   append idoc_data.
  
 endform." FILL_ZSQVBAK
  
 *-- fill the Sales Quote Line and the Line Child segments
 form fill_zsqvbap.
  
   loop at t_vbap.
     clear idoc_data.
     clear zsqvbap.
     idoc_data-segnam = 'ZSQVBAP'.
  
     move-corresponding t_vbap to zsqvbap.
     move zsqvbap to idoc_data-sdata.
     append idoc_data.
  
     perform fill_zsqvba2.
     perform fill_zsqvbup.
     perform fill_zsqvbkd.
     perform fill_zsqkonv.
     perform fill_zsqvbpa.
  
  
   endloop.
  
 endform.
  
 *-- fill second part of vbap
 form fill_zsqvba2.
 " etc.
 

Copyright IBM Corp. 1997, 2004