SALV 状态栏 quot ABC 分析 quot 点击报错问题处理

作者:ABAP三叔 约 6 分钟阅读 更新日期:2025-03-02 1 年前更新 标签:ABAP, 开发
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图

前言

在SAP官方社区上一同学发帖求助,SALV状态栏上的"ABC 分析"按钮点击之后程序报错,如何解决?本文将一探究竟,深入分析原因,并给出解决方案。

问题还原

程序代码如下:

*&---------------------------------------------------------------------**& Report zyxstest01*&---------------------------------------------------------------------**&*&---------------------------------------------------------------------*REPORT zyxstest01."Declared Table TypeTYPES: BEGIN OF ty_data, lifnr TYPE ekko-lifnr, bedat TYPE ekko-bedat, ebeln TYPE ekko-ebeln, netwr TYPE ekpo-netwr, name1 TYPE lfa1-name1, END OF ty_data.

"For ALVDATA: gt_data TYPE TABLE OF ty_data, gs_data TYPE ty_data.

START-OF-SELECTION. SELECT a~lifnr,a~bedat,a~ebeln,b~netwr,c~name1 FROM ekko AS a JOIN ekpo AS b ON b~ebeln = a~ebeln JOIN lfa1 AS c ON c~lifnr = a~lifnr UP TO 100 ROWS INTO CORRESPONDING FIELDS OF TABLE @gt_data.

PERFORM display.

*&---------------------------------------------------------------------**& Form display*&---------------------------------------------------------------------**& text*&---------------------------------------------------------------------**& --> p1 text*& <-- p2 text*&---------------------------------------------------------------------*FORM display . DATA: go_salv TYPE REF TO cl_salv_table, lo_gr_functions TYPE REF TO cl_salv_functions_list.

DATA: lo_column TYPE REF TO cl_salv_column_table. *Create alv object. TRY. CALL METHOD cl_salv_table=>factory IMPORTING r_salv_table = go_salv CHANGING t_table = gt_data. CATCH cx_salv_msg. ENDTRY.* Enabling the ABC Analysis go_salv->set_screen_status( pfstatus = 'STANDARD_FULLSCREEN' report = 'SAPLSLVC_FULLSCREEN' ). * 显示SALV所有标准功能. DATA(lo_functions) = go_salv->get_functions( ). lo_functions->set_all( abap_true ). * 获取所有列 DATA(lo_columns) = go_salv->get_columns( ).* 设置列宽自适应 lo_columns->set_optimize( abap_true ).*设置斑马线 DATA(lo_dspset) = go_salv->get_display_settings( ). lo_dspset->set_striped_pattern( abap_true ).
DATA: lr_layout TYPE REF TO cl_salv_layout, ls_key TYPE salv_s_layout_key. lr_layout = go_salv->get_layout( ). ls_key-report = sy-repid. ls_key-handle = '1000'. lr_layout->set_key( ls_key ). lr_layout->set_default( abap_true ). lr_layout->set_save_restriction( if_salv_c_layout=>restrict_none ).

• Display alv go_salv->display( ).

ENDFORM.

执行后选中"订单净值"这一列,然后点击"ABC 分析"按钮后程序报错如下

SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图

问题分析

对报错的消息号设置断点,然后DEBUG,点击"ABC 分析"按钮后,程序停在了如下 634行 位置。

SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图

l_message又是在622行动态生成报表时,产生了错误,点开lt_source后,很清楚的看出问题了。

SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图

数据定义时,"-"前没有数据库表名或结构名,导致动态生成报表时报错。继续往上分析,在381行最终发现了问题出现的端倪了。

SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图

ls_fieldcat的参考字段REF_FIELDNAME有值,但是参考表REF_TABNAME却是空的,所以最终就导致了最终的错误。

问题处理

因为该示例用了我们自定义的结构,导致SALV在处理时,没有取到对应的参考表。

TYPES: BEGIN OF ty_data, lifnr TYPE ekko-lifnr, bedat TYPE ekko-bedat, ebeln TYPE ekko-ebeln, netwr TYPE ekpo-netwr, name1 TYPE lfa1-name1, END OF ty_data.

设置参考表的方法在类cl_salv_column_list的set_ddic_reference方法中。于是在程序display之前增加以下代码,最终问题解决

DATA: lo_column_list TYPE REF TO cl_salv_column_list. TRY. lo_column_list ?= lo_columns->get_column( 'LIFNR' ). lo_column_list->set_ddic_reference( value = VALUE #( table = 'EKKO' field = 'LIFNR' ) ). lo_column_list ?= lo_columns->get_column( 'EBELN' ). lo_column_list->set_ddic_reference( value = VALUE #( table = 'EKKO' field = 'EBELN' ) ). lo_column_list ?= lo_columns->get_column( 'BEDAT' ). lo_column_list->set_ddic_reference( value = VALUE #( table = 'EKKO' field = 'BEDAT' ) ). lo_column_list ?= lo_columns->get_column( 'NETWR' ). lo_column_list->set_ddic_reference( value = VALUE #( table = 'EKPO' field = 'NETWR' ) ). lo_column_list ?= lo_columns->get_column( 'NAME1' ). lo_column_list->set_ddic_reference( value = VALUE #( table = 'LFA1' field = 'NAME1' ) ). CATCH cx_salv_not_found. "#EC NO_HANDLER ENDTRY.
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图

问题延伸

为什么使用标准的 sflight表,对数据进行"ABC 分析"就不报错呢?

对两种定义内表方式的报表进行DEBUG发现,在类CL_SALV_DATA_DESCR的GET_TABLE_DESCRIPTOR_INFO方法中会获取内表的字段定义,如果内表是参照的数据库表或结构,满足r_structdescr->is_ddic_type(

) =

abap_true条件,字段的定义中ref_tabname就会自动的赋值为内表参考的数据库表或结构;如果内表参照的是程序中自定义的结构,并且没有显式的指定ref_tabname的话,这个字段就是空的,所以进行"ABC

分析"的时候就会报错。

SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
SALV 状态栏 quot ABC 分析 quot 点击报错问题处理 - 封面图
ABAP三叔

关于作者:ABAP三叔

企业信息化与 SAP 技术顾问,长期专注 SAP ABAP、FI/CO、MM、SD 等模块的技术分享与实战经验总结。查看更多介绍

来源说明:本文内容由「SALV状态栏quotABC分析quot点击报错问题处理.md」整理生成,仅用于内部技术分享与学习交流。