mirror of
https://github.com/abapGit/abapGit.git
synced 2025-04-30 20:03:20 +08:00
Adjust diff algorithm (#5251)
* Adjust diff algorithm This implements a workaround for the kernel issue when determining diffs (see https://github.com/abapGit/abapGit/issues/4395 for background). Here's an example of the change. Before: After: * Lint + check * Add test * Ignore new tests Co-authored-by: Lars Hvam <larshp@hotmail.com>
This commit is contained in:
parent
e74076c0bb
commit
269c7cb1e6
|
@ -78,6 +78,7 @@ CLASS zcl_abapgit_diff DEFINITION
|
|||
RETURNING
|
||||
VALUE(rt_diff) TYPE zif_abapgit_definitions=>ty_diffs_tt.
|
||||
METHODS calculate_stats.
|
||||
METHODS adjust_diff.
|
||||
ENDCLASS.
|
||||
|
||||
|
||||
|
@ -85,6 +86,85 @@ ENDCLASS.
|
|||
CLASS zcl_abapgit_diff IMPLEMENTATION.
|
||||
|
||||
|
||||
METHOD adjust_diff.
|
||||
|
||||
" ABAP kernel diff traverses files from bottom up which leads to odd display of diffs
|
||||
" SAP won't adjust this kernel service so we will do it here
|
||||
" https://github.com/abapGit/abapGit/issues/4395
|
||||
|
||||
TYPES:
|
||||
BEGIN OF ty_diff_block,
|
||||
start TYPE i,
|
||||
len TYPE i,
|
||||
END OF ty_diff_block.
|
||||
|
||||
DATA:
|
||||
lv_block_begin TYPE i,
|
||||
lv_block_end TYPE i,
|
||||
ls_diff_block TYPE ty_diff_block,
|
||||
lt_diff_block TYPE STANDARD TABLE OF ty_diff_block WITH DEFAULT KEY.
|
||||
|
||||
FIELD-SYMBOLS:
|
||||
<ls_diff> LIKE LINE OF mt_diff,
|
||||
<ls_diff_begin> LIKE LINE OF mt_diff,
|
||||
<ls_diff_end> LIKE LINE OF mt_diff.
|
||||
|
||||
" Determine start and length of diff blocks
|
||||
LOOP AT mt_diff ASSIGNING <ls_diff>.
|
||||
IF <ls_diff>-result = zif_abapgit_definitions=>c_diff-insert OR
|
||||
<ls_diff>-result = zif_abapgit_definitions=>c_diff-delete.
|
||||
IF ls_diff_block IS INITIAL.
|
||||
ls_diff_block-start = sy-tabix.
|
||||
ENDIF.
|
||||
ls_diff_block-len = ls_diff_block-len + 1.
|
||||
ELSEIF ls_diff_block-start IS NOT INITIAL.
|
||||
APPEND ls_diff_block TO lt_diff_block.
|
||||
CLEAR ls_diff_block.
|
||||
ENDIF.
|
||||
ENDLOOP.
|
||||
|
||||
" For each diff block, check if beginning is same as end of block
|
||||
" If yes, move diff block down
|
||||
LOOP AT lt_diff_block INTO ls_diff_block.
|
||||
DO ls_diff_block-len TIMES.
|
||||
lv_block_begin = ls_diff_block-start + sy-index - 1.
|
||||
READ TABLE mt_diff ASSIGNING <ls_diff_begin> INDEX lv_block_begin.
|
||||
IF sy-subrc <> 0.
|
||||
EXIT.
|
||||
ENDIF.
|
||||
lv_block_end = ls_diff_block-start + ls_diff_block-len + sy-index - 1.
|
||||
READ TABLE mt_diff ASSIGNING <ls_diff_end> INDEX lv_block_end.
|
||||
IF sy-subrc <> 0.
|
||||
EXIT.
|
||||
ENDIF.
|
||||
CASE <ls_diff_begin>-result.
|
||||
WHEN zif_abapgit_definitions=>c_diff-insert.
|
||||
IF <ls_diff_begin>-new = <ls_diff_end>-new.
|
||||
<ls_diff_begin>-old_num = <ls_diff_end>-old_num.
|
||||
<ls_diff_begin>-old = <ls_diff_end>-old.
|
||||
<ls_diff_end>-result = <ls_diff_begin>-result.
|
||||
CLEAR: <ls_diff_begin>-result, <ls_diff_end>-old_num, <ls_diff_end>-old.
|
||||
ELSE.
|
||||
EXIT.
|
||||
ENDIF.
|
||||
WHEN zif_abapgit_definitions=>c_diff-delete.
|
||||
IF <ls_diff_begin>-old = <ls_diff_end>-old.
|
||||
<ls_diff_begin>-new_num = <ls_diff_end>-new_num.
|
||||
<ls_diff_begin>-new = <ls_diff_end>-new.
|
||||
<ls_diff_end>-result = <ls_diff_begin>-result.
|
||||
CLEAR: <ls_diff_begin>-result, <ls_diff_end>-new_num, <ls_diff_end>-new.
|
||||
ELSE.
|
||||
EXIT.
|
||||
ENDIF.
|
||||
WHEN OTHERS.
|
||||
EXIT.
|
||||
ENDCASE.
|
||||
ENDDO.
|
||||
ENDLOOP.
|
||||
|
||||
ENDMETHOD.
|
||||
|
||||
|
||||
METHOD calculate_stats.
|
||||
|
||||
FIELD-SYMBOLS: <ls_diff> LIKE LINE OF mt_diff.
|
||||
|
@ -197,6 +277,8 @@ CLASS zcl_abapgit_diff IMPLEMENTATION.
|
|||
mt_diff = compute_and_render( it_new = lt_new
|
||||
it_old = lt_old ).
|
||||
|
||||
adjust_diff( ).
|
||||
|
||||
calculate_stats( ).
|
||||
map_beacons( ).
|
||||
shortlist( ).
|
||||
|
|
|
@ -15,7 +15,9 @@ CLASS ltcl_diff DEFINITION FOR TESTING
|
|||
iv_new TYPE zif_abapgit_definitions=>ty_diff-new
|
||||
iv_result TYPE zif_abapgit_definitions=>ty_diff-result
|
||||
iv_old_num TYPE zif_abapgit_definitions=>ty_diff-old_num
|
||||
iv_old TYPE zif_abapgit_definitions=>ty_diff-old.
|
||||
iv_old TYPE zif_abapgit_definitions=>ty_diff-old
|
||||
iv_beacon TYPE zif_abapgit_definitions=>ty_diff-beacon
|
||||
DEFAULT zcl_abapgit_diff=>co_starting_beacon.
|
||||
|
||||
METHODS: setup.
|
||||
|
||||
|
@ -36,7 +38,9 @@ CLASS ltcl_diff DEFINITION FOR TESTING
|
|||
diff08 FOR TESTING,
|
||||
diff09 FOR TESTING,
|
||||
diff10 FOR TESTING,
|
||||
diff11 FOR TESTING.
|
||||
diff11 FOR TESTING,
|
||||
diff12 FOR TESTING,
|
||||
diff13 FOR TESTING.
|
||||
|
||||
ENDCLASS.
|
||||
|
||||
|
@ -65,7 +69,7 @@ CLASS ltcl_diff IMPLEMENTATION.
|
|||
ls_expected-result = iv_result.
|
||||
ls_expected-old_num = iv_old_num.
|
||||
ls_expected-old = iv_old.
|
||||
ls_expected-beacon = zcl_abapgit_diff=>co_starting_beacon.
|
||||
ls_expected-beacon = iv_beacon.
|
||||
APPEND ls_expected TO mt_expected.
|
||||
ENDMETHOD.
|
||||
|
||||
|
@ -394,4 +398,114 @@ CLASS ltcl_diff IMPLEMENTATION.
|
|||
|
||||
ENDMETHOD.
|
||||
|
||||
METHOD diff12.
|
||||
|
||||
" adjusted diffs for insert (workaround for kernel issue)
|
||||
add_new( iv_new = `REPORT zprog_diff.` ).
|
||||
add_new( iv_new = `*` ).
|
||||
add_new( iv_new = `FORM t_1.` ).
|
||||
add_new( iv_new = `ENDFORM.` ).
|
||||
add_new( iv_new = `FORM t_2.` ).
|
||||
add_new( iv_new = `ENDFORM.` ).
|
||||
|
||||
add_old( iv_old = `REPORT zprog_diff.` ).
|
||||
add_old( iv_old = `FORM t_1.` ).
|
||||
add_old( iv_old = `ENDFORM.` ).
|
||||
|
||||
add_expected( iv_new_num = ' 1'
|
||||
iv_new = `REPORT zprog_diff.`
|
||||
iv_result = '' " no diff!
|
||||
iv_old_num = ' 1'
|
||||
iv_old = `REPORT zprog_diff.`
|
||||
iv_beacon = 1 ).
|
||||
add_expected( iv_new_num = ' 2'
|
||||
iv_new = `*`
|
||||
iv_result = 'I'
|
||||
iv_old_num = ' '
|
||||
iv_old = ``
|
||||
iv_beacon = 1 ).
|
||||
add_expected( iv_new_num = ' 3'
|
||||
iv_new = `FORM t_1.`
|
||||
iv_result = '' " no diff!
|
||||
iv_old_num = ' 2'
|
||||
iv_old = `FORM t_1.`
|
||||
iv_beacon = 2 ).
|
||||
add_expected( iv_new_num = ' 4'
|
||||
iv_new = `ENDFORM.`
|
||||
iv_result = '' " no diff!
|
||||
iv_old_num = ' 3'
|
||||
iv_old = `ENDFORM.`
|
||||
iv_beacon = 2 ).
|
||||
add_expected( iv_new_num = ' 5'
|
||||
iv_new = `FORM t_2.`
|
||||
iv_result = 'I'
|
||||
iv_old_num = ' '
|
||||
iv_old = ``
|
||||
iv_beacon = 3 ).
|
||||
add_expected( iv_new_num = ' 6'
|
||||
iv_new = `ENDFORM.`
|
||||
iv_result = 'I'
|
||||
iv_old_num = ' '
|
||||
iv_old = ``
|
||||
iv_beacon = 3 ).
|
||||
|
||||
test( ).
|
||||
|
||||
ENDMETHOD.
|
||||
|
||||
METHOD diff13.
|
||||
|
||||
" adjusted diffs for delete (workaround for kernel issue)
|
||||
add_old( iv_old = `REPORT zprog_diff.` ).
|
||||
add_old( iv_old = `*` ).
|
||||
add_old( iv_old = `FORM t_1.` ).
|
||||
add_old( iv_old = `ENDFORM.` ).
|
||||
add_old( iv_old = `FORM t_2.` ).
|
||||
add_old( iv_old = `ENDFORM.` ).
|
||||
|
||||
add_new( iv_new = `REPORT zprog_diff.` ).
|
||||
add_new( iv_new = `FORM t_1.` ).
|
||||
add_new( iv_new = `ENDFORM.` ).
|
||||
|
||||
add_expected( iv_old_num = ' 1'
|
||||
iv_old = `REPORT zprog_diff.`
|
||||
iv_result = '' " no diff!
|
||||
iv_new_num = ' 1'
|
||||
iv_new = `REPORT zprog_diff.`
|
||||
iv_beacon = 1 ).
|
||||
add_expected( iv_old_num = ' 2'
|
||||
iv_old = `*`
|
||||
iv_result = 'D'
|
||||
iv_new_num = ' '
|
||||
iv_new = ``
|
||||
iv_beacon = 1 ).
|
||||
add_expected( iv_old_num = ' 3'
|
||||
iv_old = `FORM t_1.`
|
||||
iv_result = '' " no diff!
|
||||
iv_new_num = ' 2'
|
||||
iv_new = `FORM t_1.`
|
||||
iv_beacon = 2 ).
|
||||
add_expected( iv_old_num = ' 4'
|
||||
iv_old = `ENDFORM.`
|
||||
iv_result = '' " no diff!
|
||||
iv_new_num = ' 3'
|
||||
iv_new = `ENDFORM.`
|
||||
iv_beacon = 2 ).
|
||||
add_expected( iv_old_num = ' 5'
|
||||
iv_old = `FORM t_2.`
|
||||
iv_result = 'D'
|
||||
iv_new_num = ' '
|
||||
iv_new = ``
|
||||
iv_beacon = 2 ).
|
||||
add_expected( iv_old_num = ' 6'
|
||||
iv_old = `ENDFORM.`
|
||||
iv_result = 'D'
|
||||
iv_new_num = ' '
|
||||
iv_new = ``
|
||||
iv_beacon = 2 ).
|
||||
|
||||
test( ).
|
||||
|
||||
ENDMETHOD.
|
||||
|
||||
ENDCLASS.
|
||||
|
|
|
@ -239,6 +239,8 @@
|
|||
{"object": "ZCL_ABAPGIT_DIFF", "class": "ltcl_diff", "method": "diff09", "note": "fm RS_CMP_COMPUTE_DELTA + Void type: RSWSOURCET"},
|
||||
{"object": "ZCL_ABAPGIT_DIFF", "class": "ltcl_diff", "method": "diff10", "note": "fm RS_CMP_COMPUTE_DELTA + Void type: RSWSOURCET"},
|
||||
{"object": "ZCL_ABAPGIT_DIFF", "class": "ltcl_diff", "method": "diff11", "note": "fm RS_CMP_COMPUTE_DELTA + Void type: RSWSOURCET"},
|
||||
{"object": "ZCL_ABAPGIT_DIFF", "class": "ltcl_diff", "method": "diff12", "note": "fm RS_CMP_COMPUTE_DELTA + Void type: RSWSOURCET"},
|
||||
{"object": "ZCL_ABAPGIT_DIFF", "class": "ltcl_diff", "method": "diff13", "note": "fm RS_CMP_COMPUTE_DELTA + Void type: RSWSOURCET"},
|
||||
{"object": "ZCL_ABAPGIT_USER_RECORD", "class": "ltcl_user_record", "method": "test_invalid_user", "note": "Void type: BAPIADDR3"},
|
||||
{"object": "ZCL_ABAPGIT_SERVICES_BASIS", "class": "ltcl_create_package", "method": "raise_error_if_package_exists", "note": "Void type: SCOMPKDTLN"},
|
||||
{"object": "ZCL_ABAPGIT_SERVICES_BASIS", "class": "ltcl_create_package", "method": "package_given_in_popup", "note": "Void type: SCOMPKDTLN"},
|
||||
|
|
Loading…
Reference in New Issue
Block a user