程序调用

程序调用 (★★★)

#program-structure #memory-mgmt

同步程序调用:概述

同步程序调用在返回控制权之前执行被调用程序。有两种模式:

模式 类比 对调用者的影响
插入(AND RETURN) 压入栈 调用者暂停,被调用程序结束后恢复
新启动(无 AND RETURN) 替换当前 调用者终止,被调用程序替换它

SUBMIT 语句

SUBMIT 变体比较

变体 行为 会话效果
SUBMIT prog AND RETURN 插入:被调用程序结束后调用者恢复 新的内部会话压入栈顶
SUBMIT prog 替换:调用者被终止 顶层内部会话被替换
SUBMIT ... VIA SELECTION-SCREEN 显示被调用程序的选择屏幕 与基本变体相同
1
2
3
4
5
" 插入 — 报表结束后调用者恢复
SUBMIT zreport AND RETURN.

" 替换 — 调用者终止,zreport 替换它
SUBMIT zreport.

使用 SUBMIT 传递数据

方法 语法 说明
单值 WITH p_param VALUE 传递值给参数
选择选项单值 WITH s_selopt EQ value 添加单条条件
选择选项范围 WITH s_selopt IN range_tab range_tab 必须为 TYPE RANGE
变式 USING VARIANT var_name 使用已保存的变式
💡选择选项的 RANGE 类型
要传递选择选项,声明一个范围表:
1
2
3
DATA: r_bukrs TYPE RANGE OF bkpf-bukrs.
r_bukrs = VALUE #( ( sign = 'I' option = 'EQ' low = '1000' ) ).
SUBMIT zreport WITH s_bukrs IN r_bukrs AND RETURN.

范围表必须包含字段:SIGN、OPTION、LOW、HIGH。

CALL TRANSACTION

语法和附加项

附加项 用途
AND SKIP FIRST SCREEN 如果必填字段已预填,则跳过初始屏幕
MODE mode 控制屏幕显示:A(全部)、E(仅错误)、N(不显示)
UPDATE upd 更新模式:A(异步)、S(同步)、L(本地更新)
USING bdc_tab 使用批输入表驱动事务
MESSAGES INTO itab 将所有消息收集到内表中
1
2
3
4
5
CALL TRANSACTION 'MM01'
USING lt_bdcdata
MODE 'N'
UPDATE 'S'
MESSAGES INTO lt_messages.

显示模式

模式 代码 描述
显示所有屏幕 A 每个屏幕都显示(默认)
仅显示错误 E 仅在出错时显示屏幕
不显示 N 后台处理,不显示任何屏幕

更新模式

模式 代码 行为
异步 A 不等待更新完成(默认)
同步 S 等待更新完成;可通过 sy-subrc 检查成功
本地 L 在当前 LUW 中更新(调试有用)
📌同步更新最安全
当需要确认事务成功时,始终使用 UPDATE 'S'。使用 UPDATE 'A' 时,sy-subrc 仅反映事务调用结果,而非数据库更新结果。

LEAVE TO TRANSACTION

1
LEAVE TO TRANSACTION 'MM01'.
方面 行为
会话效果 销毁整个内部会话栈
ABAP 内存 被清除 – 所有 EXPORT TO MEMORY 数据丢失
比较 CALL TRANSACTION(插入)不同,这是新启动
⚠️LEAVE TO TRANSACTION 清除 ABAP 内存
因为整个栈被销毁,ABAP 内存中所有数据(EXPORT/IMPORT)都会丢失。这是常见的考试陷阱。参见 [[_posts/SAP_MM/SCM500_采购流程/00-仪表盘/考试陷阱]]。

BDCDATA 结构

使用 CALL TRANSACTION ... USING bdc_tab 时,BDCDATA 表驱动屏幕字段:

字段 类型 描述
PROGRAM CHAR 40 ABAP 程序名
DYNPRO CHAR 4 屏幕编号
DYNBEGIN CHAR 1 X = 屏幕头行, = 字段行
FNAM CHAR 132 字段名(或 BDC_OKCODE 表示功能码)
FVAL CHAR 132 字段值

BDCDATA 表布局

1
2
3
4
5
6
7
8
+-------------------+--------+----------+------------------+------------------+
| PROGRAM | DYNPRO | DYNBEGIN | FNAM | FVAL |
+-------------------+--------+----------+------------------+------------------+
| SAPLMGMM | 0060 | X | | |
| | | | RMMG1-MATNR | MAT01 |
| | | | RMMG1-MBRSH | M |
| | | | BDC_OKCODE | =ENTR |
+-------------------+--------+----------+------------------+------------------+
💡BDCDATA 模式
每个屏幕以头行(DYNBEGIN = 'X')开始,包含 PROGRAM 和 DYNPRO。后续所有 DYNBEGIN = ' ' 的行设置字段值。使用 FNAM 中的 BDC_OKCODE 触发操作。

收集消息

1
2
3
4
5
6
7
8
9
10
DATA: lt_messages TYPE TABLE OF bdcmsgcoll.

CALL TRANSACTION 'MM01'
USING lt_bdcdata
MODE 'N'
MESSAGES INTO lt_messages.

LOOP AT lt_messages INTO DATA(ls_msg).
" ls_msg-MSGTYP, ls_msg-MSGID, ls_msg-MSGNR, ls_msg-MSGV1...
ENDLOOP.

会话栈图示

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
CALL TRANSACTION / SUBMIT AND RETURN(插入):
==============================================

外部会话
┌──────────────────────────────────┐
│ 内部会话栈 │
│ ┌────────────────────────────┐ │
│ │ 被调用程序(新栈顶) │ │
│ ├────────────────────────────┤ │
│ │ 调用者(已暂停) │ │
│ ├────────────────────────────┤ │
│ │ ... 更早的会话 ... │ │
│ └────────────────────────────┘ │
└──────────────────────────────────┘


LEAVE TO TRANSACTION(新启动):
=================================

外部会话
┌──────────────────────────────────┐
│ 内部会话栈 │
│ ┌────────────────────────────┐ │
│ │ 目标事务(唯一) │ │ ← 所有先前的会话被销毁
│ └────────────────────────────┘ │
└──────────────────────────────────┘


SUBMIT 不带 AND RETURN(替换):
=====================================

外部会话
┌──────────────────────────────────┐
│ 内部会话栈 │
│ ┌────────────────────────────┐ │
│ │ 被提交程序(栈顶) │ │ ← 替换了旧的栈顶会话
│ ├────────────────────────────┤ │
│ │ ... 更早的会话 ... │ │
│ └────────────────────────────┘ │
└──────────────────────────────────┘

考试/测试模式

关键词 / 模式 正确答案
SUBMIT … AND RETURN 插入 – 调用者恢复;新的内部会话压入栈
SUBMIT 不带 AND RETURN 替换 – 调用者终止;栈顶会话被替换
LEAVE TO TRANSACTION 销毁整个栈并清除 ABAP 内存
CALL TRANSACTION … MODE ‘N’ 不显示屏幕(后台)
CALL TRANSACTION … UPDATE ‘S’ 同步更新 – 等待数据库提交
BDCDATA DYNBEGIN = ‘X’ 标记屏幕头行(PROGRAM + DYNPRO)
WITH select-option IN range 范围表必须为 TYPE RANGE,包含 SIGN/OPTION/LOW/HIGH
MESSAGES INTO itab 将事务消息收集到 BDCMSGCOLL 表中
AND SKIP FIRST SCREEN 仅在必填字段已预填时跳过初始屏幕
区别:CALL TRANSACTION vs LEAVE TO TRANSACTION CALL 插入(栈增长),LEAVE 销毁(栈重置)

相关笔记

  • 运行时与内存管理 – 内部/外部会话、程序组、ABAP/SAP 内存
  • 共享对象 – 跨会话数据共享的替代方案
  • [[_posts/SAP_MM/SCM500_采购流程/00-仪表盘/考试陷阱]] – LEAVE TO TRANSACTION 清除 ABAP 内存
  • [[_posts/SAP_MM/SCM500_采购流程/00-仪表盘/快速参考]] – 程序调用汇总表