Patch: replace links with checkboxes #2673 (#2684)

* Patch: replace links with checkboxes

With this commit we replace the links on the patch page
with checkboxes.
This has several advantages:
- better performance
- simplified and less cluttered UI
- less and easier to understand code

* refactor

* refactoring: introduce new method add_checkbox

* fix linter

* enable link hint navigation

* Refactoring: remove duplication

* refactor: remove duplication

* fix: link hint activate section/lines
This commit is contained in:
Christian Günter 2019-05-20 17:44:49 +02:00 committed by Lars Hvam
parent c61b3f9138
commit 53dd60c07b
6 changed files with 128 additions and 252 deletions

View File

@ -10,6 +10,7 @@ CLASS zcl_abapgit_html DEFINITION
render FOR zif_abapgit_html~render,
is_empty FOR zif_abapgit_html~is_empty,
add_a FOR zif_abapgit_html~add_a,
add_checkbox FOR zif_abapgit_html~add_checkbox,
a FOR zif_abapgit_html~a,
icon FOR zif_abapgit_html~icon.
@ -23,6 +24,7 @@ CLASS zcl_abapgit_html DEFINITION
!iv_class TYPE string OPTIONAL .
PROTECTED SECTION.
PRIVATE SECTION.
CONSTANTS: co_span_link_hint TYPE string VALUE `<span class="tooltiptext hidden"></span>`.
CLASS-DATA: go_single_tags_re TYPE REF TO cl_abap_regex.
DATA: mt_buffer TYPE string_table.
@ -59,6 +61,11 @@ CLASS zcl_abapgit_html DEFINITION
is_context TYPE ty_indent_context
RETURNING
VALUE(rs_result) TYPE ty_study_result.
METHODS checkbox
IMPORTING
iv_id TYPE string
RETURNING
VALUE(rv_html) TYPE string.
ENDCLASS.
@ -197,8 +204,7 @@ CLASS ZCL_ABAPGIT_HTML IMPLEMENTATION.
lv_href TYPE string,
lv_click TYPE string,
lv_id TYPE string,
lv_style TYPE string,
lv_span TYPE string.
lv_style TYPE string.
lv_class = iv_class.
@ -239,9 +245,7 @@ CLASS ZCL_ABAPGIT_HTML IMPLEMENTATION.
lv_style = | style="{ iv_style }"|.
ENDIF.
lv_span = |<span class="tooltiptext hidden"></span>|.
rv_str = |<a{ lv_id }{ lv_class }{ lv_href }{ lv_click }{ lv_style }>{ iv_txt }{ lv_span }</a>|.
rv_str = |<a{ lv_id }{ lv_class }{ lv_href }{ lv_click }{ lv_style }>{ iv_txt }{ co_span_link_hint }</a>|.
ENDMETHOD.
@ -343,4 +347,19 @@ CLASS ZCL_ABAPGIT_HTML IMPLEMENTATION.
CONCATENATE LINES OF lt_temp INTO rv_html SEPARATED BY cl_abap_char_utilities=>newline.
ENDMETHOD.
METHOD zif_abapgit_html~add_checkbox.
add( checkbox( iv_id ) ).
ENDMETHOD.
METHOD checkbox.
rv_html = |<input type="checkbox" id="{ iv_id }">|
&& |{ co_span_link_hint }|.
ENDMETHOD.
ENDCLASS.

View File

@ -35,6 +35,9 @@ INTERFACE zif_abapgit_html PUBLIC.
!iv_class TYPE string OPTIONAL
!iv_id TYPE string OPTIONAL
!iv_style TYPE string OPTIONAL.
METHODS add_checkbox
IMPORTING
iv_id TYPE string.
CLASS-METHODS a
IMPORTING
!iv_txt TYPE string

View File

@ -531,7 +531,7 @@ table.diff_tab td.num, th.num {
}
table.diff_tab td.patch, th.patch {
width: 1%;
min-width: 6em;
min-width: 1.5em;
padding-right: 8px;
padding-left: 8px;
text-align: right !important;
@ -933,12 +933,6 @@ div.info-panel div.info-list td {
border-color: #555 transparent transparent transparent;
}
/* diff-patch */
.patch-active {
color: lightgrey !important;
}
/* HOTKEYS */
ul.hotkeys {
list-style-type: none;

View File

@ -730,7 +730,7 @@ function LinkHints(sLinkHintKey, sColor){
this.oTooltipMap = {};
this.bTooltipsOn = false;
this.sPending = "";
this.aTooltipElements = document.querySelectorAll("a span");
this.aTooltipElements = document.querySelectorAll("span.tooltiptext");
}
LinkHints.prototype.renderTooltip = function (oTooltip, iTooltipCounter) {
@ -829,7 +829,21 @@ LinkHints.prototype.tooltipActivate = function (oTooltip) {
// a tooltips was successfully specified, so we try to trigger the link
// and remove all tooltips
this.removeAllTooltips();
// we have technically 2 scenarios
// 1) hint to a checkbox: as input field cannot include tags
// we place the span after input
// 2) hint to a link: the span in included in the anchor tag
var elInput = oTooltip.parentElement.querySelector("input");
if (elInput) {
// case 1) toggle the checkbox
elInput.click();
} else {
// case 2) click the link
oTooltip.parentElement.click();
}
// in case it is a dropdownmenu we have to expand and focus it
this.activateDropDownMenu(oTooltip);
@ -1024,10 +1038,10 @@ Patch.prototype.escape = function(sFileName){
};
/*
We have three type of cascading links, each of them has two verbs, add and remove.
Which means that by clicking a file or section link all corresponding line links are clicked.
We have three type of cascading checkboxes.
Which means that by clicking a file or section checkbox all corresponding line checkboxes are checked.
The id of the link indicates its semantics and its membership.
The id of the checkbox indicates its semantics and its membership.
*/
@ -1036,163 +1050,90 @@ Patch.prototype.escape = function(sFileName){
example id of file link
patch_file_add_zcl_abapgit_user_exit.clas.abap
\________/ ^ \_____________________________/
| | |
| | |____ file name
patch_file_zcl_abapgit_user_exit.clas.abap
\________/ \_____________________________/
| |
| verb [add|remove]
| |____ file name
|
|
|
constant prefix
*/
function PatchFile(sId){
var oRegex = new RegExp("(" + this.ID.FILE + ")_(add|remove)_(.*$)");
var oRegex = new RegExp("(" + this.ID + ")_(.*$)");
var oMatch = sId.match(oRegex);
this.id = sId;
this.prefix = oMatch[1];
this.verb = oMatch[2];
this.file_name = oMatch[3];
this.file_name = oMatch[2];
}
PatchFile.prototype.ID = {
FILE: "patch_file",
ADD: "patch_file_add",
REMOVE: "patch_file_remove"
};
PatchFile.prototype.ID = "patch_file";
/*
2) section links within a file
example id of section link
patch_section_add_zcl_abapgit_user_exit.clas.abap_1
\___________/ ^ \_____________________________/ ^
| | | |
| | file name |
patch_section_zcl_abapgit_user_exit.clas.abap_1
\___________/ \_____________________________/ ^
| | |
| verb [add|remove] ------ section
| file name |
| |
| ------ section
|
constant prefix
*/
function PatchSection(sId){
var oRegex = new RegExp("(" + this.ID.SECTION + ")_(add|remove)_(.*)_(\\d+$)");
var oRegex = new RegExp("(" + this.ID + ")_(.*)_(\\d+$)");
var oMatch = sId.match(oRegex);
this.id = sId;
this.prefix = oMatch[1];
this.verb = oMatch[2];
this.file_name = oMatch[3];
this.section = oMatch[4];
this.file_name = oMatch[2];
this.section = oMatch[3];
}
PatchSection.prototype.ID = {
SECTION: "patch_section",
ADD: "patch_section_add",
REMOVE: "patch_section_remove"
};
PatchSection.prototype.ID = "patch_section";
/*
3) line links within a section
example id of line link
patch_line_add_zcl_abapgit_user_exit.clas.abap_1_25
\________/ ^ \_____________________________/ ^ ^
^ | ^ | |
| | | | ------- line number
| | file name |
| | section
| verb [add|remove]
patch_line_zcl_abapgit_user_exit.clas.abap_1_25
\________/ \_____________________________/ ^ ^
^ ^ | |
| | | ------- line number
| file name |
| section
|
|
constant prefix
*/
function PatchLine(sId){
var oRegex = new RegExp("(" + this.ID.LINE + ")_(add|remove)_(.*)_(\\d+)_(\\d+$)");
var oMatch = sId.match(oRegex);
this.id = sId;
this.prefix = oMatch[1];
this.verb = oMatch[2];
this.file_name = oMatch[3];
this.section = oMatch[4];
this.line = oMatch[5];
this.corresponding_verb = this.CORRESPONDING_VERBS[this.verb];
this.elem = document.querySelector("#" + Patch.prototype.escape(this.id));
this.correspondingLink = this.getCorrespodingLink();
function PatchLine(){
}
PatchLine.prototype.ID = {
LINE: "patch_line",
ADD: "patch_line_add",
REMOVE: "patch_line_remove"
};
PatchLine.prototype.CSS_CLASS = {
PATCH: "patch",
PATCH_ACTIVE: "patch-active"
};
PatchLine.prototype.CORRESPONDING_VERBS = {
add: "remove",
remove: "add"
};
PatchLine.prototype.getCorrespodingLinkId = function(){
// e.g.
//
// patch_line_add_z_test_git_add_p.prog.abap_3_28 => patch_line_remove_z_test_git_add_p.prog.abap_3_28
//
// and vice versa
var oRegexPatchIdPrefix = new RegExp("^" + this.ID.LINE + "_" + this.verb );
return this.id.replace(oRegexPatchIdPrefix, this.ID.LINE + "_" + this.corresponding_verb);
};
PatchLine.prototype.toggle = function(){
if (!this.elem.classList.contains(this.CSS_CLASS.PATCH_ACTIVE)){
this.elem.classList.toggle(this.CSS_CLASS.PATCH_ACTIVE);
this.correspondingLink.classList.toggle(this.CSS_CLASS.PATCH_ACTIVE);
}
};
PatchLine.prototype.getCorrespodingLink = function(){
var sCorrespondingLinkId = this.getCorrespodingLinkId();
return document.querySelector('[ID="' + Patch.prototype.escape(sCorrespondingLinkId) + '"]');
};
PatchLine.prototype.ID = "patch_line";
Patch.prototype.preparePatch = function(){
this.registerClickHandlerForFiles();
this.registerClickHandlerForSections();
this.registerClickHandlerForLines();
};
Patch.prototype.registerClickHandlerForFiles = function(){
// registers the link handlers for add and remove files
this.registerClickHandlerForPatchFile("a[id^='" + PatchFile.prototype.ID.ADD + "']");
this.registerClickHandlerForPatchFile("a[id^='" + PatchFile.prototype.ID.REMOVE + "']");
this.registerClickHandlerForSelector("input[id^='" + PatchFile.prototype.ID + "']", this.onClickFileCheckbox);
};
Patch.prototype.registerClickHandlerForSections = function(){
// registers the link handlers for add and remove sections
this.registerClickHandlerForPatchSection("a[id^='" + PatchSection.prototype.ID.ADD + "']");
this.registerClickHandlerForPatchSection("a[id^='" + PatchSection.prototype.ID.REMOVE + "']");
};
Patch.prototype.registerClickHandlerForLines = function(){
// registers the link handlers for add and remove lines
this.registerClickHandlerForPatchLine("a[id^='" + PatchLine.prototype.ID.ADD + "']");
this.registerClickHandlerForPatchLine("a[id^='" + PatchLine.prototype.ID.REMOVE + "']");
this.registerClickHandlerForSelector("input[id^='" + PatchSection.prototype.ID + "']", this.onClickSectionCheckbox);
};
Patch.prototype.registerClickHandlerForSelector = function(sSelector, fnCallback){
@ -1205,67 +1146,60 @@ Patch.prototype.registerClickHandlerForSelector = function(sSelector, fnCallback
};
Patch.prototype.registerClickHandlerForPatchFile = function(sSelector){
this.registerClickHandlerForSelector(sSelector, this.patchLinkClickFile);
Patch.prototype.getAllLineCheckboxesForFile = function(oFile){
return this.getAllLineCheckboxesForId(oFile.id, PatchFile.prototype.ID);
};
Patch.prototype.registerClickHandlerForPatchSection = function(sSelector){
this.registerClickHandlerForSelector(sSelector, this.patchLinkClickSection);
Patch.prototype.getAllSectionCheckboxesForFile = function(oFile){
return this.getAllSectionCheckboxesForId(oFile.id, PatchFile.prototype.ID);
};
Patch.prototype.registerClickHandlerForPatchLine = function(sSelector) {
this.registerClickHandlerForSelector(sSelector, this.patchLinkClickLine);
Patch.prototype.getAllLineCheckboxesForSection = function(oSection){
return this.getAllLineCheckboxesForId(oSection.id, PatchSection.prototype.ID);
};
Patch.prototype.patchLinkClickLine = function(oEvent){
this.togglePatchForElem(oEvent.srcElement);
oEvent.preventDefault();
Patch.prototype.getAllLineCheckboxesForId = function(sId, sIdPrefix){
return this.getAllCheckboxesForId(sId, sIdPrefix,PatchLine.prototype.ID);
};
Patch.prototype.togglePatchForElem = function(elLink) {
new PatchLine(elLink.id).toggle();
Patch.prototype.getAllSectionCheckboxesForId = function(sId, sIdPrefix){
return this.getAllCheckboxesForId(sId, sIdPrefix, PatchSection.prototype.ID);
};
Patch.prototype.getAllLineLinksForId = function(sId, sIdPrefix){
Patch.prototype.getAllCheckboxesForId = function(sId, sIdPrefix, sNewIdPrefix){
var oRegex = new RegExp("^" + sIdPrefix);
sId = sId.replace(oRegex, PatchLine.prototype.ID.LINE);
return document.querySelectorAll("a[id^='"+ this.escape(sId) + "']");
sId = sId.replace(oRegex, sNewIdPrefix);
return document.querySelectorAll("input[id^='"+ this.escape(sId) + "']");
};
Patch.prototype.getAllLineLinksForFile = function(oFile){
return this.getAllLineLinksForId(oFile.id, PatchFile.prototype.ID.FILE);
};
Patch.prototype.getAllLineLinksForSection = function(oSection){
return this.getAllLineLinksForId(oSection.id, PatchSection.prototype.ID.SECTION);
};
Patch.prototype.patchLinkClickFile = function(oEvent) {
Patch.prototype.onClickFileCheckbox = function(oEvent) {
var oFile = new PatchFile(oEvent.srcElement.id);
var elAllLineLinksOfFile = this.getAllLineLinksForFile(oFile);
var elAllLineCheckboxesOfFile = this.getAllLineCheckboxesForFile(oFile);
var elAllSectionCheckboxesOfFile = this.getAllSectionCheckboxesForFile(oFile);
[].forEach.call(elAllLineLinksOfFile,function(elem){
this.togglePatchForElem(elem);
[].forEach.call(elAllLineCheckboxesOfFile,function(elem){
elem.checked = oEvent.srcElement.checked;
}.bind(this));
[].forEach.call(elAllSectionCheckboxesOfFile,function(elem){
elem.checked = oEvent.srcElement.checked;
}.bind(this));
oEvent.preventDefault();
};
Patch.prototype.patchLinkClickSection = function(oEvent){
Patch.prototype.onClickSectionCheckbox = function(oEvent){
var oSection = new PatchSection(oEvent.srcElement.id);
this.clickAllLineLinksInSection(oEvent, oSection.section);
oEvent.preventDefault();
this.clickAllLineCheckboxesInSection(oEvent, oSection.section);
};
Patch.prototype.clickAllLineLinksInSection = function(oEvent){
Patch.prototype.clickAllLineCheckboxesInSection = function(oEvent){
var oSection = new PatchSection(oEvent.srcElement.id);
var elAllLineLinksOfSection = this.getAllLineLinksForSection(oSection);
var elAllLineCheckboxesOfSection = this.getAllLineCheckboxesForSection(oSection);
[].forEach.call(elAllLineLinksOfSection,function(elem){
this.togglePatchForElem(elem);
oEvent.preventDefault();
[].forEach.call(elAllLineCheckboxesOfSection,function(elem){
elem.checked = oEvent.srcElement.checked;
}.bind(this));
};
@ -1286,20 +1220,20 @@ Patch.prototype.stagePatch = function() {
// Collect add and remove info and submit to backend
var aAddPatch = this.collectActiveElementsForId( PatchLine.prototype.ID.ADD );
var aRemovePatch = this.collectActiveElementsForId( PatchLine.prototype.ID.REMOVE );
var aAddPatch = this.collectElementsForCheckboxId(PatchLine.prototype.ID, true);
var aRemovePatch = this.collectElementsForCheckboxId(PatchLine.prototype.ID, false);
submitSapeventForm({"add": aAddPatch, "remove": aRemovePatch}, this.ACTION.PATCH_STAGE, "post");
};
Patch.prototype.collectActiveElementsForId = function(sId){
Patch.prototype.collectElementsForCheckboxId = function(sId, bChecked){
var sSelector = "." + PatchLine.prototype.CSS_CLASS.PATCH + " a[id^='" + sId + "']";
var sSelector = "input[id^='" + sId + "']";
return [].slice.call(document.querySelectorAll(sSelector))
.filter(function(elem){
return elem.classList.contains(PatchLine.prototype.CSS_CLASS.PATCH_ACTIVE);
return (elem.checked === bChecked);
}).map(function(elem){
return elem.id;
});

View File

@ -120,7 +120,6 @@ CLASS zcl_abapgit_gui_page_diff DEFINITION
zcx_abapgit_exception .
METHODS apply_patch_all
IMPORTING
iv_action TYPE ty_patch_action
iv_patch TYPE string
iv_patch_flag TYPE abap_bool
RAISING
@ -154,7 +153,6 @@ CLASS zcl_abapgit_gui_page_diff DEFINITION
CLASS-METHODS get_patch_data
IMPORTING
iv_patch TYPE string
iv_action TYPE string
EXPORTING
ev_filename TYPE string
ev_line_index TYPE string
@ -164,7 +162,7 @@ ENDCLASS.
CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
CLASS zcl_abapgit_gui_page_diff IMPLEMENTATION.
METHOD add_to_stage.
@ -315,7 +313,6 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
get_patch_data(
EXPORTING
iv_patch = <lv_patch>
iv_action = iv_action
IMPORTING
ev_filename = lv_filename
ev_line_index = lv_line_index ).
@ -534,11 +531,7 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
CLEAR: ev_filename, ev_line_index.
IF iv_action <> c_patch_action-add AND iv_action <> c_patch_action-remove.
zcx_abapgit_exception=>raise( |Invalid action { iv_action }| ).
ENDIF.
FIND FIRST OCCURRENCE OF REGEX `patch_line_` && iv_action && `_(.*)_(\d)+_(\d+)`
FIND FIRST OCCURRENCE OF REGEX `patch_line` && `_(.*)_(\d)+_(\d+)`
IN iv_patch
SUBMATCHES ev_filename lv_section ev_line_index.
IF sy-subrc <> 0.
@ -609,19 +602,7 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
IF mv_patch_mode = abap_true.
ro_html->add( |<th class="patch">| ).
ro_html->add_a( iv_txt = |{ c_patch_action-add }|
iv_act = |patch_section_add('{ is_diff-filename }','{ mv_section_count }')|
iv_id = |patch_section_add_{ is_diff-filename }_{ mv_section_count }|
iv_class = |patch_section_add|
iv_typ = zif_abapgit_html=>c_action_type-dummy ).
ro_html->add_a( iv_txt = |{ c_patch_action-remove }|
iv_act = |patch_section_remove('{ is_diff-filename }', '{ mv_section_count }')|
iv_id = |patch_section_remove_{ is_diff-filename }_{ mv_section_count }|
iv_class = |patch_section_remove|
iv_typ = zif_abapgit_html=>c_action_type-dummy ).
ro_html->add_checkbox( iv_id = |patch_section_{ is_diff-filename }_{ mv_section_count }| ).
ro_html->add( '</th>' ).
ELSE.
@ -913,7 +894,6 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
CONSTANTS:
BEGIN OF c_css_class,
patch_active TYPE string VALUE `patch-active` ##NO_TEXT,
patch TYPE string VALUE `patch` ##NO_TEXT,
END OF c_css_class.
@ -929,24 +909,7 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
lv_id = |{ lv_object }_{ mv_section_count }_{ iv_index }|.
io_html->add( |<td class="{ c_css_class-patch }">| ).
IF is_diff_line-patch_flag = abap_true.
lv_left_class = c_css_class-patch_active.
ELSE.
lv_right_class = c_css_class-patch_active.
ENDIF.
io_html->add_a( iv_txt = |{ c_patch_action-add }|
iv_act = ||
iv_id = |patch_line_{ c_patch_action-add }_{ lv_id }|
iv_typ = zif_abapgit_html=>c_action_type-dummy
iv_class = lv_left_class ).
io_html->add_a( iv_txt = |{ c_patch_action-remove }|
iv_act = ||
iv_id = |patch_line_{ c_patch_action-remove }_{ lv_id }|
iv_typ = zif_abapgit_html=>c_action_type-dummy
iv_class = lv_right_class ).
io_html->add_checkbox( iv_id = |patch_line_{ lv_id }| ).
io_html->add( |</td>| ).
ELSE.
@ -962,19 +925,7 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
METHOD render_patch_head.
io_html->add( |<th class="patch">| ).
io_html->add_a( iv_txt = |{ c_patch_action-add }|
iv_act = |patch_file_add('{ is_diff-filename }')|
iv_id = |patch_file_add_{ is_diff-filename }|
iv_class = |patch_file_add|
iv_typ = zif_abapgit_html=>c_action_type-dummy ).
io_html->add_a( iv_txt = |{ c_patch_action-remove }|
iv_act = |patch_file_remove('{ is_diff-filename }')|
iv_id = |patch_file_remove_{ is_diff-filename }|
iv_class = |patch_file_remove|
iv_typ = zif_abapgit_html=>c_action_type-dummy ).
io_html->add_checkbox( iv_id = |patch_file_{ is_diff-filename }| ).
io_html->add( '</th>' ).
ENDMETHOD.
@ -1051,12 +1002,10 @@ CLASS ZCL_ABAPGIT_GUI_PAGE_DIFF IMPLEMENTATION.
it_field = lt_fields
CHANGING cg_field = lv_remove ).
apply_patch_all( iv_action = c_patch_action-add
iv_patch = lv_add
apply_patch_all( iv_patch = lv_add
iv_patch_flag = abap_true ).
apply_patch_all( iv_action = c_patch_action-remove
iv_patch = lv_remove
apply_patch_all( iv_patch = lv_remove
iv_patch_flag = abap_false ).
add_to_stage( ).

View File

@ -8,7 +8,6 @@ CLASS ltcl_patch DEFINITION FINAL FOR TESTING
METHODS:
get_patch_data_add FOR TESTING RAISING cx_static_check,
get_patch_data_remove FOR TESTING RAISING cx_static_check,
invalid_action FOR TESTING RAISING cx_static_check,
invalid_patch_missing_file FOR TESTING RAISING cx_static_check,
invalid_patch_missing_index FOR TESTING RAISING cx_static_check.
@ -25,8 +24,7 @@ CLASS ltcl_patch IMPLEMENTATION.
zcl_abapgit_gui_page_diff=>get_patch_data(
EXPORTING
iv_patch = |patch_line_add_zcl_test_git_add_p.clas.abap_0_19|
iv_action = |add|
iv_patch = |patch_line_zcl_test_git_add_p.clas.abap_0_19|
IMPORTING
ev_filename = lv_file_name
ev_line_index = lv_line_index ).
@ -48,8 +46,7 @@ CLASS ltcl_patch IMPLEMENTATION.
zcl_abapgit_gui_page_diff=>get_patch_data(
EXPORTING
iv_patch = |patch_line_remove_ztest_patch.prog.abap_0_39|
iv_action = |remove|
iv_patch = |patch_line_ztest_patch.prog.abap_0_39|
IMPORTING
ev_filename = lv_file_name
ev_line_index = lv_line_index ).
@ -64,24 +61,6 @@ CLASS ltcl_patch IMPLEMENTATION.
ENDMETHOD.
METHOD invalid_action.
DATA: lx_error TYPE REF TO zcx_abapgit_exception.
TRY.
zcl_abapgit_gui_page_diff=>get_patch_data(
iv_patch = |remove_patch_ztest_patch.prog.abap_39|
iv_action = |mix| ).
cl_abap_unit_assert=>fail( ).
CATCH zcx_abapgit_exception INTO lx_error.
cl_abap_unit_assert=>assert_equals(
exp = |Invalid action mix|
act = lx_error->get_text( ) ).
ENDTRY.
ENDMETHOD.
METHOD invalid_patch_missing_file.
@ -92,8 +71,7 @@ CLASS ltcl_patch IMPLEMENTATION.
TRY.
zcl_abapgit_gui_page_diff=>get_patch_data(
EXPORTING
iv_patch = |add_patch_39|
iv_action = |add|
iv_patch = |patch_39|
IMPORTING
ev_filename = lv_file_name
ev_line_index = lv_line_index ).
@ -117,8 +95,7 @@ CLASS ltcl_patch IMPLEMENTATION.
TRY.
zcl_abapgit_gui_page_diff=>get_patch_data(
EXPORTING
iv_patch = |remove_patch_ztest_patch.prog.abap|
iv_action = |remove|
iv_patch = |patch_ztest_patch.prog.abap|
IMPORTING
ev_filename = lv_file_name
ev_line_index = lv_line_index ).