ABAP Open Checks 是一个开源项目,旨在增强 SAP Code Inspector 和 ABAP Test Cockpit (ATC) 的功能。它为 ABAP 代码提供了广泛的附加检查,超出了 SAP 环境中可用的标准检查范围。这些检查涵盖 ABAP 编程最佳实践、代码清洁、性能优化等各个方面,旨在提高 ABAP 代码库的质量和可维护性。
安装
该项目允许您通过 abapGit 进行安装和配置,其设计旨在无需在客户系统中创建新对象即可进行单元测试。或将源代码手动复制到系统中。通过 abapGit 安装需要创建一个空软件包,例如 $AOC
SCI 设置
- 在事务 SCI 中激活检查(取决于版本)
- 转到 -> 管理 -> 测试
- 代码检查器 -> 管理 -> 测试
- 代码检查器 -> 管理 -> 检查
将这些检查全部勾选上,你也可以选择你需要的。
- 配置检查变量
更新
使用 upDOWNci 备份变量。
运行 abapGit,点击 "pull"。请注意,该选项只有在新代码已添加到版本库时才会显示。
如果使用 abapGit 的离线项目功能,也可点击 "导入 zip"。
卸载
运行 abapGit,点击 "卸载"。
它仅支持英语,适用于 SAP 系统 7.40 SP02 或更高版本。检查范围从验证 IF 条件、循环、TRY-CATCH 块的使用,到执行命名约定、检查过时语句等等。
您可以在其文档网站上找到 ABAP Open Checks 所提供的具体检查的完整列表,包括行长检查、ASCII 合规性检查、漂亮的打印机使用、CALL METHOD 的功能性书写风格以及其他许多旨在执行编码标准和提高代码质量的检查。
Check if 存在多层嵌套
通过这个工具,可以将两层嵌套:
erlang
IF condition1.
IF condition2.
...
ENDIF.
ENDIF.
可缩减为:
erlang
IF ( condition1 ) AND ( condition2 ).
...
ENDIF.
或者将:
erlang
ELSE.
IF condition.
...
ENDIF.
ENDIF.
可缩减为:
erlang
ELSEIF condition.
...
ENDIF.
源码:
ABAP
CLASS zcl_aoc_check_01 DEFINITION
PUBLIC
INHERITING FROM zcl_aoc_super
CREATE PUBLIC.
PUBLIC SECTION.
METHODS constructor.
METHODS check
REDEFINITION.
PROTECTED SECTION.
METHODS contains_else
IMPORTING
!io_structure TYPE REF TO zcl_aoc_structure
RETURNING
VALUE(rv_bool) TYPE abap_bool.
METHODS run_check
IMPORTING
!io_structure TYPE REF TO zcl_aoc_structure
!io_scan TYPE REF TO zcl_aoc_scan.
PRIVATE SECTION.
ENDCLASS.
CLASS zcl_aoc_check_01 IMPLEMENTATION.
METHOD check.
* abapOpenChecks
* https://github.com/larshp/abapOpenChecks
* MIT License
DATA: lo_structure TYPE REF TO zcl_aoc_structure.
lo_structure = zcl_aoc_structure=>build(
it_tokens = io_scan->tokens
it_statements = io_scan->statements
it_structures = io_scan->structures ).
run_check(
io_structure = lo_structure
io_scan = io_scan ).
ENDMETHOD.
METHOD constructor.
super->constructor( ).
version = '001'.
position = '001'.
has_attributes = abap_true.
attributes_ok = abap_true.
enable_rfc( ).
enable_checksum( ).
insert_scimessage(
iv_code = '001'
iv_text = 'IF in IF, can easily be reduced'(m01) ).
ENDMETHOD.
METHOD contains_else.
DATA: lo_structure TYPE REF TO zcl_aoc_structure.
LOOP AT io_structure->get_structure( ) INTO lo_structure.
IF lo_structure->get_type( ) = zcl_aoc_scan=>gc_structure_statement-else
OR lo_structure->get_type( ) = zcl_aoc_scan=>gc_structure_statement-elseif.
rv_bool = abap_true.
RETURN.
ENDIF.
ENDLOOP.
ENDMETHOD.
METHOD run_check.
DATA: lo_structure TYPE REF TO zcl_aoc_structure,
lo_then TYPE REF TO zcl_aoc_structure,
lv_include TYPE program,
lv_if TYPE i,
lv_other TYPE i,
lv_row TYPE token_row,
lv_position LIKE sy-tabix.
IF io_structure->get_type( ) = zcl_aoc_scan=>gc_structure_statement-if
OR io_structure->get_type( ) = zcl_aoc_scan=>gc_structure_statement-else.
IF io_structure->get_type( ) = zcl_aoc_scan=>gc_structure_statement-if.
READ TABLE io_structure->get_structure( ) INDEX 1 INTO lo_then.
ASSERT sy-subrc = 0.
LOOP AT io_structure->get_structure( ) INTO lo_structure.
CASE lo_structure->get_type( ).
WHEN zcl_aoc_scan=>gc_structure_statement-elseif
OR zcl_aoc_scan=>gc_structure_statement-else.
lv_if = lv_if + 2.
ENDCASE.
ENDLOOP.
ELSE.
lo_then = io_structure.
ENDIF.
LOOP AT lo_then->get_structure( ) INTO lo_structure.
CASE lo_structure->get_type( ).
WHEN zcl_aoc_scan=>gc_structure_statement-if.
IF contains_else( lo_structure ) = abap_true
AND io_structure->get_type( ) = zcl_aoc_scan=>gc_structure_statement-if.
lv_if = lv_if + 1.
ENDIF.
lv_if = lv_if + 1.
WHEN OTHERS.
lv_other = lv_other + 1.
ENDCASE.
ENDLOOP.
ENDIF.
IF lv_if = 1 AND lv_other = 0.
lv_include = io_scan->get_include( io_structure->get_statement( )-level ).
lv_row = io_structure->get_statement( )-row.
READ TABLE io_scan->statements WITH KEY trow = lv_row TRANSPORTING NO FIELDS.
lv_position = sy-tabix.
inform( p_sub_obj_name = lv_include
p_position = lv_position
p_line = lv_row
p_kind = mv_errty
p_test = myname
p_code = '001' ).
ELSE.
LOOP AT io_structure->get_structure( ) INTO lo_structure.
run_check( io_structure = lo_structure
io_scan = io_scan ).
ENDLOOP.
ENDIF.
ENDMETHOD.
ENDCLASS.
测试代码
dart
*&---------------------------------------------------------------------*
*& Report ZCHECK01
*&---------------------------------------------------------------------*
*&
*&---------------------------------------------------------------------*
REPORT zcheck01.
DATA: num TYPE i.
num = 1.
IF num <= 2.
IF num MOD 2 <> 0.
WRITE: num.
ENDIF.
ENDIF.
Open Checks 检查结果:
- 嵌套循环
- 不应该声明字段 num 为全局变量
- 不好的命名方式,全局变量应该
gv_
开头,但是我们只命名了num
其他检查结果,大家可以结合实际进行探索。
开源地址:larshp/abapOpenChecks: Open source checks for SAP Code Inspector / ABAP Test Cockpit (github.com)