d5-testing-library 1.8.0-alpha.2 → 1.8.0-alpha.21
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/FormEdit-GTZISTTI.mjs +7 -0
- package/dist/ListForm-EM7E4ZMM.mjs +7 -0
- package/dist/TreeView-F2XF44N2.mjs +8 -0
- package/dist/chunk-LMFYREYI.mjs +22 -0
- package/dist/{chunk-ZT3B7BQ2.mjs → chunk-MV63JF3H.mjs} +261 -79
- package/dist/{chunk-LTHDA5XH.mjs → chunk-PMZQRKUZ.mjs} +363 -75
- package/dist/{chunk-H3M6VBPP.mjs → chunk-WDYVVF7O.mjs} +16 -7
- package/dist/cjs/d5-testing-library.cjs +786 -216
- package/dist/d5-testing-library.d.ts +188 -21
- package/dist/d5-testing-library.legacy-esm.js +29 -13
- package/dist/d5-testing-library.mjs +29 -13
- package/package.json +18 -6
- package/dist/FormEdit-PRX4TB67.mjs +0 -7
- package/dist/ListForm-N6QNZXQE.mjs +0 -7
- package/dist/TreeView-JOHAYS2S.mjs +0 -8
- package/dist/chunk-4PUDCQM6.mjs +0 -17
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
import {
|
|
2
|
+
ListForm
|
|
3
|
+
} from "./chunk-PMZQRKUZ.mjs";
|
|
4
|
+
|
|
5
|
+
// src/pageObjects/elements/Forms/TreeView.ts
|
|
6
|
+
var TREELIST_HEADER_CSS_SELECTOR = ".dx-treelist-headers .dx-treelist-content:not(.dx-datagrid-content-fixed)";
|
|
7
|
+
var TREELIST_CONTENT_CSS_SELECTOR = ".dx-treelist-content:not(.dx-datagrid-content-fixed)";
|
|
8
|
+
var FIXED_TREELIST_CONTENT_CSS_SELECTOR = ".dx-fixed-columns .dx-treelist-content.dx-treelist-content-fixed";
|
|
9
|
+
var TreeView = class extends ListForm {
|
|
10
|
+
constructor(driver) {
|
|
11
|
+
super(driver);
|
|
12
|
+
this.popupContainerCssSelector = `.popup.tree-view-${this.formName}`;
|
|
13
|
+
this.headerCssSelector = TREELIST_HEADER_CSS_SELECTOR;
|
|
14
|
+
this.fixedTableContentCssSelector = FIXED_TREELIST_CONTENT_CSS_SELECTOR;
|
|
15
|
+
this.contextMenuCssSelector = ".dx-treelist-container";
|
|
16
|
+
this.tableContentCssSelector = TREELIST_CONTENT_CSS_SELECTOR;
|
|
17
|
+
}
|
|
18
|
+
};
|
|
19
|
+
|
|
20
|
+
export {
|
|
21
|
+
TreeView
|
|
22
|
+
};
|
|
@@ -150,6 +150,14 @@ var click = async (webElement, driver) => {
|
|
|
150
150
|
const actions = driver.actions({ async: true });
|
|
151
151
|
await actions.move({ origin: webElement }).click().perform();
|
|
152
152
|
};
|
|
153
|
+
var contextMenu = async (webElement, driver) => {
|
|
154
|
+
driver = driver ?? config().driver;
|
|
155
|
+
if (!await webElement.isDisplayed()) {
|
|
156
|
+
await driver.executeScript("arguments[0].scrollIntoView(true);", webElement);
|
|
157
|
+
}
|
|
158
|
+
const actions = driver.actions({ async: true });
|
|
159
|
+
await actions.move({ origin: webElement }).contextClick().perform();
|
|
160
|
+
};
|
|
153
161
|
|
|
154
162
|
// src/utils/locators.ts
|
|
155
163
|
import { By as By2 } from "selenium-webdriver";
|
|
@@ -161,6 +169,22 @@ var byTestId = (testId, element = "div") => {
|
|
|
161
169
|
};
|
|
162
170
|
var readonlyLocator = "readonly";
|
|
163
171
|
|
|
172
|
+
// src/utils/waitElementIsClickable.ts
|
|
173
|
+
async function waitElementIsClickable({
|
|
174
|
+
timeout,
|
|
175
|
+
errorMessage,
|
|
176
|
+
driver,
|
|
177
|
+
...rest
|
|
178
|
+
}) {
|
|
179
|
+
driver = driver ?? config().driver;
|
|
180
|
+
await wait(async () => {
|
|
181
|
+
const searchedElement = "by" in rest ? await fixElementStaleError(rest.by, driver) : rest.element;
|
|
182
|
+
const isDisabled = await searchedElement.getCssValue("pointer-events") === "none";
|
|
183
|
+
return await searchedElement.isDisplayed() && !isDisabled;
|
|
184
|
+
}, driver, errorMessage, timeout ?? config().timeout);
|
|
185
|
+
}
|
|
186
|
+
var waitElementIsClickable_default = waitElementIsClickable;
|
|
187
|
+
|
|
164
188
|
// src/pageObjects/elements/Editors/AbstractEditor.ts
|
|
165
189
|
import { By as By3, Key } from "selenium-webdriver";
|
|
166
190
|
|
|
@@ -226,8 +250,9 @@ var TextEditor = class extends AbstractDXEditorWithInput {
|
|
|
226
250
|
super(parentCssSelector, elementCssSelector, driver);
|
|
227
251
|
this.setClearStrategy(new InputClearStrategy());
|
|
228
252
|
}
|
|
229
|
-
getValue() {
|
|
230
|
-
|
|
253
|
+
async getValue() {
|
|
254
|
+
const value = await super.getInputValue();
|
|
255
|
+
return value == "" ? null : value;
|
|
231
256
|
}
|
|
232
257
|
setValue(value) {
|
|
233
258
|
return this.setInputValue(value);
|
|
@@ -262,6 +287,7 @@ var ControlClass = /* @__PURE__ */ ((ControlClass2) => {
|
|
|
262
287
|
ControlClass2["SingleDateRange"] = "single-date-range-control";
|
|
263
288
|
ControlClass2["BooleanSelector"] = "buttons-group";
|
|
264
289
|
ControlClass2["ButtonGroup"] = "button-group-field";
|
|
290
|
+
ControlClass2["HeaderFilterDictionary"] = "header-filter-dictionary";
|
|
265
291
|
return ControlClass2;
|
|
266
292
|
})(ControlClass || {});
|
|
267
293
|
|
|
@@ -420,7 +446,8 @@ var TagBox = class extends AbstractDXEditorWithInput {
|
|
|
420
446
|
await this.confirmSelection();
|
|
421
447
|
}
|
|
422
448
|
async waitOptionSelection() {
|
|
423
|
-
await fixElementStaleError(By6.css(TAG_BOX_LIST_ITEM_SELECTOR), this.driver);
|
|
449
|
+
const option = await fixElementStaleError(By6.css(TAG_BOX_LIST_ITEM_SELECTOR), this.driver);
|
|
450
|
+
await wait(() => option.isDisplayed(), this.driver);
|
|
424
451
|
}
|
|
425
452
|
async selectOption(inputEl, value, lastElement) {
|
|
426
453
|
try {
|
|
@@ -546,33 +573,44 @@ var BaseDateEditor = class extends AbstractDXEditorWithInput {
|
|
|
546
573
|
super(parentCssSelector, elementCssSelector, driver);
|
|
547
574
|
this.setClearStrategy(new InputClearStrategy());
|
|
548
575
|
}
|
|
549
|
-
async
|
|
576
|
+
async setArrayValue(value) {
|
|
550
577
|
const actions = this.driver.actions({ async: true });
|
|
551
578
|
const dateField = await this.driver.findElement(By8.css(`${this.getFullCssSelector()}`));
|
|
579
|
+
const dateInputEl = await this.getInputElement();
|
|
552
580
|
const dateFieldDataTestID = await this.getDataTestId();
|
|
553
|
-
const
|
|
581
|
+
const formattedDates = value.map(formatDMYDate);
|
|
582
|
+
const button = await dateField.findElement(By8.css(`.${BTN_CALENDAR_POPOVER_OPEN_SELECTOR}`));
|
|
583
|
+
await click(button, this.driver);
|
|
584
|
+
const calendarPopoverElement = await this.driver.findElement(By8.css(byTestIdCssSelector(`${dateFieldDataTestID}-calendar-popover`)));
|
|
585
|
+
const dateFromInput = await calendarPopoverElement.findElement(
|
|
586
|
+
By8.css(`.${BTN_CALENDAR_POPOVER_DATE_FROM_INPUT_SELECTOR} .dx-texteditor-input`)
|
|
587
|
+
);
|
|
588
|
+
const dateToInput = await calendarPopoverElement.findElement(
|
|
589
|
+
By8.css(`.${BTN_CALENDAR_POPOVER_DATE_TO_INPUT_SELECTOR} .dx-texteditor-input`)
|
|
590
|
+
);
|
|
591
|
+
await click(dateFromInput, this.driver);
|
|
592
|
+
await dateFromInput.sendKeys(formattedDates[0]);
|
|
593
|
+
await click(dateToInput, this.driver);
|
|
594
|
+
await actions.move({ origin: dateInputEl }).sendKeys(Key3.HOME).perform();
|
|
595
|
+
await dateToInput.sendKeys(formattedDates[1]);
|
|
596
|
+
await actions.move({ origin: dateInputEl }).sendKeys(Key3.ENTER).perform();
|
|
597
|
+
const btnOk = await this.driver.findElement(By8.css(`.${BTN_SAVE_SELECTOR}`));
|
|
598
|
+
await click(btnOk, this.driver);
|
|
599
|
+
}
|
|
600
|
+
async setSingleValue(value) {
|
|
601
|
+
const actions = this.driver.actions({ async: true });
|
|
602
|
+
const formattedDate = formatDMYDate(value);
|
|
554
603
|
const dateInputEl = await this.getInputElement();
|
|
555
|
-
await dateInputEl.
|
|
604
|
+
await click(dateInputEl, this.driver);
|
|
605
|
+
await actions.move({ origin: dateInputEl }).sendKeys(Key3.HOME).perform();
|
|
606
|
+
await actions.move({ origin: dateInputEl }).sendKeys(formattedDate, Key3.ENTER).perform();
|
|
607
|
+
}
|
|
608
|
+
async setDateValue(value) {
|
|
609
|
+
await this.clear();
|
|
556
610
|
if (Array.isArray(value)) {
|
|
557
|
-
|
|
558
|
-
const button = await dateField.findElement(By8.css(`.${BTN_CALENDAR_POPOVER_OPEN_SELECTOR}`));
|
|
559
|
-
await button.click();
|
|
560
|
-
const calendarPopoverElement = await this.driver.findElement(By8.css(calendarPopoverSelector));
|
|
561
|
-
const dateFromInput = await calendarPopoverElement.findElement(By8.css(`.${BTN_CALENDAR_POPOVER_DATE_FROM_INPUT_SELECTOR} .dx-texteditor-input`));
|
|
562
|
-
const dateToInput = await calendarPopoverElement.findElement(By8.css(`.${BTN_CALENDAR_POPOVER_DATE_TO_INPUT_SELECTOR} .dx-texteditor-input`));
|
|
563
|
-
await dateFromInput.click();
|
|
564
|
-
await dateFromInput.sendKeys(formattedDates[0]);
|
|
565
|
-
await dateToInput.click();
|
|
566
|
-
await actions.move({ origin: dateInputEl }).sendKeys(Key3.HOME).perform();
|
|
567
|
-
await dateToInput.sendKeys(formattedDates[1]);
|
|
568
|
-
await actions.move({ origin: dateInputEl }).sendKeys(Key3.ENTER).perform();
|
|
569
|
-
const btnOk = await this.driver.findElement(By8.css(`.${BTN_SAVE_SELECTOR}`));
|
|
570
|
-
await btnOk.click();
|
|
611
|
+
await this.setArrayValue(value);
|
|
571
612
|
} else {
|
|
572
|
-
|
|
573
|
-
await click(dateInputEl, this.driver);
|
|
574
|
-
await actions.move({ origin: dateInputEl }).sendKeys(Key3.HOME).perform();
|
|
575
|
-
await actions.move({ origin: dateInputEl }).sendKeys(formattedDate, Key3.ENTER).perform();
|
|
613
|
+
await this.setSingleValue(value);
|
|
576
614
|
}
|
|
577
615
|
}
|
|
578
616
|
};
|
|
@@ -635,15 +673,14 @@ var DateRangeEditor = class extends BaseDateEditor {
|
|
|
635
673
|
// src/pageObjects/elements/Editors/Date/DateEditor.ts
|
|
636
674
|
var DateEditor = class extends AbstractDXEditorWithInput {
|
|
637
675
|
editorInstance = null;
|
|
638
|
-
|
|
639
|
-
|
|
640
|
-
|
|
641
|
-
|
|
642
|
-
|
|
643
|
-
async init(parentCssSelector, elementCssSelector, driver) {
|
|
644
|
-
await this.updateEditorInstance(parentCssSelector, elementCssSelector, driver);
|
|
676
|
+
async init() {
|
|
677
|
+
if (this.editorInstance) {
|
|
678
|
+
return this.editorInstance;
|
|
679
|
+
}
|
|
680
|
+
await this.setEditorInstance();
|
|
645
681
|
}
|
|
646
|
-
async
|
|
682
|
+
async setEditorInstance() {
|
|
683
|
+
const { parentCssSelector, elementCssSelector, driver } = this;
|
|
647
684
|
const elementInstance = new AbstractFormElement(parentCssSelector, elementCssSelector, driver);
|
|
648
685
|
const classString = await elementInstance.getClasses();
|
|
649
686
|
switch (true) {
|
|
@@ -657,25 +694,105 @@ var DateEditor = class extends AbstractDXEditorWithInput {
|
|
|
657
694
|
this.editorInstance = new SingleDateEditor(parentCssSelector, elementCssSelector, driver);
|
|
658
695
|
}
|
|
659
696
|
}
|
|
660
|
-
async
|
|
661
|
-
|
|
662
|
-
|
|
697
|
+
async setValue(value) {
|
|
698
|
+
await this.init();
|
|
699
|
+
await this.editorInstance.setValue(value);
|
|
700
|
+
await this.setEditorInstance();
|
|
701
|
+
}
|
|
702
|
+
async getValue() {
|
|
703
|
+
await this.init();
|
|
704
|
+
return this.editorInstance.getValue();
|
|
705
|
+
}
|
|
706
|
+
};
|
|
707
|
+
|
|
708
|
+
// src/pageObjects/elements/Editors/HeaderFilterDictionary.ts
|
|
709
|
+
import { By as By11, Key as Key4 } from "selenium-webdriver";
|
|
710
|
+
var TAGS_SELECTOR2 = ".dx-tag .tag-text";
|
|
711
|
+
var DX_TAG_CONTAINER2 = "dx-tag-container";
|
|
712
|
+
var DX_TEXTEDITOR_EMPTY3 = "dx-texteditor-empty";
|
|
713
|
+
var CUSTOM_OPTION_LIST_SELECTOR = "custom-list";
|
|
714
|
+
var SELECT_BOX_OPTION_TEXT_CONTAINER_CLASS2 = "d5-multi-select-item";
|
|
715
|
+
var TAG_BOX_LIST_ITEM_SELECTOR2 = '.dx-overlay-wrapper .dx-list-item[aria-selected="true"]';
|
|
716
|
+
var combinedOptionHeaderFilterDictValueXpath = (value) => `//div[contains(@class, '${SELECT_BOX_OPTION_TEXT_CONTAINER_CLASS2}') and contains(text(), '${value}')]`;
|
|
717
|
+
var dropDownHeaderFilterDictionaryOptionClick = async (optionValue, driver, dataTEST = "", delay = true) => {
|
|
718
|
+
const { implicit } = await driver.manage().getTimeouts();
|
|
719
|
+
let optElement = null;
|
|
720
|
+
const timeout = delay ? implicit : 600;
|
|
721
|
+
let err = null;
|
|
722
|
+
try {
|
|
723
|
+
const calendarPopoverSelector = byTestIdCssSelector(`${dataTEST}`);
|
|
724
|
+
await driver.manage().setTimeouts({ implicit: timeout });
|
|
725
|
+
const calendarPopoverElement = await driver.findElement(By11.css(calendarPopoverSelector));
|
|
726
|
+
const customOptionList = calendarPopoverElement.findElement(By11.css(`.${CUSTOM_OPTION_LIST_SELECTOR}`));
|
|
727
|
+
optElement = await customOptionList.findElement(By11.xpath(combinedOptionHeaderFilterDictValueXpath(optionValue)));
|
|
728
|
+
await click(optElement, driver);
|
|
729
|
+
} catch (e) {
|
|
730
|
+
err = new Error(`Item not found: "${optionValue}"`);
|
|
731
|
+
} finally {
|
|
732
|
+
await driver.manage().setTimeouts({ implicit });
|
|
733
|
+
}
|
|
734
|
+
if (err)
|
|
735
|
+
throw err;
|
|
736
|
+
};
|
|
737
|
+
var HeaderFilterDictionary = class extends AbstractDXEditorWithInput {
|
|
738
|
+
constructor(parentCssSelector, elementCssSelector, driver) {
|
|
739
|
+
super(parentCssSelector, elementCssSelector, driver);
|
|
740
|
+
this.setClearStrategy(new ClearButtonStrategy(this.getFullCssSelector(), this.driver));
|
|
741
|
+
}
|
|
742
|
+
async setTagBoxInputValue(values) {
|
|
743
|
+
const lastElement = values[values.length - 1];
|
|
744
|
+
const inputEl = await this.getInputElement();
|
|
745
|
+
await inputEl.click();
|
|
746
|
+
for (const value of values) {
|
|
747
|
+
await this.selectOption(inputEl, value, lastElement);
|
|
663
748
|
}
|
|
664
749
|
}
|
|
665
|
-
async
|
|
666
|
-
await
|
|
667
|
-
|
|
668
|
-
|
|
669
|
-
|
|
750
|
+
async waitOptionSelection() {
|
|
751
|
+
await fixElementStaleError(By11.css(TAG_BOX_LIST_ITEM_SELECTOR2), this.driver);
|
|
752
|
+
}
|
|
753
|
+
async selectOption(inputEl, value, lastElement) {
|
|
754
|
+
try {
|
|
755
|
+
await inputEl.sendKeys(value);
|
|
756
|
+
const dataTEST = await this.getDataTestId();
|
|
757
|
+
await dropDownHeaderFilterDictionaryOptionClick(value, this.driver, dataTEST);
|
|
758
|
+
const textLength = await inputEl.getAttribute("value").then((value2) => value2.length);
|
|
759
|
+
for (let i = 0; i < textLength; i++) {
|
|
760
|
+
await inputEl.sendKeys(Key4.BACK_SPACE);
|
|
761
|
+
}
|
|
762
|
+
} catch (error) {
|
|
763
|
+
throw error;
|
|
764
|
+
}
|
|
765
|
+
await this.waitOptionSelection();
|
|
766
|
+
if (value !== lastElement) {
|
|
767
|
+
await inputEl.clear();
|
|
670
768
|
}
|
|
671
|
-
|
|
769
|
+
}
|
|
770
|
+
async getHeaderFilterDictionaryInputValue() {
|
|
771
|
+
if (await this.isHeaderFilterDictionaryEmpty()) {
|
|
772
|
+
return [];
|
|
773
|
+
}
|
|
774
|
+
const tags = await this.driver.findElements(
|
|
775
|
+
By11.css(`${this.getFullCssSelector()} .${DX_TAG_CONTAINER2} ${TAGS_SELECTOR2}`)
|
|
776
|
+
);
|
|
777
|
+
const values = [];
|
|
778
|
+
for (const tag of tags) {
|
|
779
|
+
values.push(await tag.getAttribute("textContent"));
|
|
780
|
+
}
|
|
781
|
+
return values;
|
|
782
|
+
}
|
|
783
|
+
async isHeaderFilterDictionaryEmpty() {
|
|
784
|
+
const classAttribute = await this.getClasses();
|
|
785
|
+
return classAttribute.includes(DX_TEXTEDITOR_EMPTY3);
|
|
672
786
|
}
|
|
673
787
|
async getValue() {
|
|
674
|
-
await this.
|
|
675
|
-
|
|
676
|
-
|
|
788
|
+
const value = await this.getHeaderFilterDictionaryInputValue();
|
|
789
|
+
return value.length ? value : null;
|
|
790
|
+
}
|
|
791
|
+
async setValue(values) {
|
|
792
|
+
if (!Array.isArray(values)) {
|
|
793
|
+
values = [values];
|
|
677
794
|
}
|
|
678
|
-
|
|
795
|
+
await this.setTagBoxInputValue(values);
|
|
679
796
|
}
|
|
680
797
|
};
|
|
681
798
|
|
|
@@ -702,6 +819,8 @@ var editorFactory = async (parentCssSelector, elementCssSelector, driver) => {
|
|
|
702
819
|
return new BooleanSelector(parentCssSelector, elementCssSelector, driver);
|
|
703
820
|
if (classSting.includes("button-group-field" /* ButtonGroup */))
|
|
704
821
|
return new ButtonGroup(parentCssSelector, elementCssSelector, driver);
|
|
822
|
+
if (classSting.includes("header-filter-dictionary" /* HeaderFilterDictionary */))
|
|
823
|
+
return new HeaderFilterDictionary(parentCssSelector, elementCssSelector, driver);
|
|
705
824
|
throw new Error("Unknown type of editor. Please write ticket to the support");
|
|
706
825
|
};
|
|
707
826
|
|
|
@@ -736,6 +855,38 @@ function createFormButtonTestId(formName, itemName) {
|
|
|
736
855
|
function createSubSystemTestId(itemName) {
|
|
737
856
|
return `${"subsystem-item" /* SUBSYSTEM_ITEM */}-${itemName}`;
|
|
738
857
|
}
|
|
858
|
+
function createEditorButtonTestId(itemName) {
|
|
859
|
+
return `${"editor-button" /* EDITOR_BUTTON */}-${itemName}`;
|
|
860
|
+
}
|
|
861
|
+
|
|
862
|
+
// src/pageObjects/elements/EditorButton.ts
|
|
863
|
+
var EditorButton = class extends AbstractElementWithParent {
|
|
864
|
+
name;
|
|
865
|
+
constructor(parentCssSelector, name, driver) {
|
|
866
|
+
super(parentCssSelector, byTestIdCssSelector(createEditorButtonTestId(name)), driver);
|
|
867
|
+
this.name = name;
|
|
868
|
+
}
|
|
869
|
+
buttonNotDisplayedError() {
|
|
870
|
+
return `Editor Button ${this.name} cannot be clicked. It is not displayed or it is disabled`;
|
|
871
|
+
}
|
|
872
|
+
async click() {
|
|
873
|
+
const button = await this.getElement();
|
|
874
|
+
await waitElementIsClickable_default({
|
|
875
|
+
element: button,
|
|
876
|
+
errorMessage: this.buttonNotDisplayedError(),
|
|
877
|
+
driver: this.driver
|
|
878
|
+
});
|
|
879
|
+
await click(button, this.driver);
|
|
880
|
+
}
|
|
881
|
+
async isDisplayed() {
|
|
882
|
+
try {
|
|
883
|
+
const button = await this.getElement();
|
|
884
|
+
return await button.isDisplayed();
|
|
885
|
+
} catch (error) {
|
|
886
|
+
return false;
|
|
887
|
+
}
|
|
888
|
+
}
|
|
889
|
+
};
|
|
739
890
|
|
|
740
891
|
// src/pageObjects/elements/AbstractEditor.ts
|
|
741
892
|
var AbstractEditor = class extends AbstractElementWithParent {
|
|
@@ -802,6 +953,31 @@ var AbstractEditor = class extends AbstractElementWithParent {
|
|
|
802
953
|
await this.initEditor();
|
|
803
954
|
return this.editor.isReadonly();
|
|
804
955
|
}
|
|
956
|
+
/**
|
|
957
|
+
* Возвращает значение true|false в зависимости isDisplayed поле или нет
|
|
958
|
+
* @example
|
|
959
|
+
* expect(await formEdit.field('NumberFld').isDisplayed()).toBe(true);
|
|
960
|
+
* expect(await formEdit.field('TextFld').isDisplayed()).toBe(false);
|
|
961
|
+
*/
|
|
962
|
+
async isDisplayed() {
|
|
963
|
+
try {
|
|
964
|
+
await this.initEditor();
|
|
965
|
+
const element = await this.getElement();
|
|
966
|
+
return await element.isDisplayed();
|
|
967
|
+
} catch {
|
|
968
|
+
return false;
|
|
969
|
+
}
|
|
970
|
+
}
|
|
971
|
+
/**
|
|
972
|
+
* Находит кнопку на поле по имени
|
|
973
|
+
* @example
|
|
974
|
+
* const form= new MyForm();
|
|
975
|
+
* //...
|
|
976
|
+
* await form.field('Name').button('editorButton).click()
|
|
977
|
+
*/
|
|
978
|
+
button(name) {
|
|
979
|
+
return new EditorButton(this.getFullCssSelector(), name, this.driver);
|
|
980
|
+
}
|
|
805
981
|
};
|
|
806
982
|
|
|
807
983
|
// src/pageObjects/elements/FormField.ts
|
|
@@ -812,30 +988,16 @@ var FormField = class extends AbstractEditor {
|
|
|
812
988
|
};
|
|
813
989
|
|
|
814
990
|
// src/pageObjects/elements/Forms/Form.ts
|
|
815
|
-
import { By as
|
|
991
|
+
import { By as By15 } from "selenium-webdriver";
|
|
816
992
|
|
|
817
|
-
// src/
|
|
818
|
-
async function waitElementIsClickable({
|
|
819
|
-
element,
|
|
820
|
-
timeout,
|
|
821
|
-
errorMessage,
|
|
822
|
-
driver
|
|
823
|
-
}) {
|
|
824
|
-
driver = driver ?? config().driver;
|
|
825
|
-
await wait(async () => {
|
|
826
|
-
const isDisabled = await element.getCssValue("pointer-events") === "none";
|
|
827
|
-
return await element.isDisplayed() && !isDisabled;
|
|
828
|
-
}, driver, errorMessage, timeout ?? config().timeout);
|
|
829
|
-
}
|
|
830
|
-
|
|
831
|
-
// src/pageObjects/elements/TableToolbar/AbstractButton.ts
|
|
993
|
+
// src/pageObjects/elements/AbstractButton.ts
|
|
832
994
|
var AbstractButton = class extends AbstractElementWithParent {
|
|
833
995
|
constructor(parentCssSelector, elementCssSelector, driver) {
|
|
834
996
|
super(parentCssSelector, elementCssSelector, driver);
|
|
835
997
|
}
|
|
836
998
|
async click() {
|
|
837
999
|
const button = await this.getElement();
|
|
838
|
-
await
|
|
1000
|
+
await waitElementIsClickable_default({
|
|
839
1001
|
element: button,
|
|
840
1002
|
errorMessage: this.buttonNotDisplayedError(),
|
|
841
1003
|
driver: this.driver
|
|
@@ -846,10 +1008,18 @@ var AbstractButton = class extends AbstractElementWithParent {
|
|
|
846
1008
|
const button = await this.getElement();
|
|
847
1009
|
return await button.getCssValue("pointer-events") === "none";
|
|
848
1010
|
}
|
|
1011
|
+
async isDisplayed() {
|
|
1012
|
+
try {
|
|
1013
|
+
const button = await this.getElement();
|
|
1014
|
+
return await button.isDisplayed();
|
|
1015
|
+
} catch {
|
|
1016
|
+
return false;
|
|
1017
|
+
}
|
|
1018
|
+
}
|
|
849
1019
|
};
|
|
850
1020
|
|
|
851
1021
|
// src/pageObjects/elements/DXComponents/DXButton.ts
|
|
852
|
-
import { By as
|
|
1022
|
+
import { By as By12 } from "selenium-webdriver";
|
|
853
1023
|
var DXButton = class extends AbstractButton {
|
|
854
1024
|
async getText() {
|
|
855
1025
|
const classes = await this.getClasses();
|
|
@@ -857,7 +1027,7 @@ var DXButton = class extends AbstractButton {
|
|
|
857
1027
|
return null;
|
|
858
1028
|
}
|
|
859
1029
|
const el = await this.getElement();
|
|
860
|
-
const textEl = el.findElement(
|
|
1030
|
+
const textEl = el.findElement(By12.className("dx-button-text"));
|
|
861
1031
|
return await textEl.getText();
|
|
862
1032
|
}
|
|
863
1033
|
};
|
|
@@ -887,7 +1057,7 @@ var Panel = class extends AbstractGroup {
|
|
|
887
1057
|
};
|
|
888
1058
|
|
|
889
1059
|
// src/pageObjects/elements/Groups/TabPanel.ts
|
|
890
|
-
import { By as
|
|
1060
|
+
import { By as By13 } from "selenium-webdriver";
|
|
891
1061
|
var TabPanelItem = class extends AbstractGroup {
|
|
892
1062
|
constructor(parentCssSelector, elementCssSelector, driver) {
|
|
893
1063
|
super(parentCssSelector, elementCssSelector, driver);
|
|
@@ -897,7 +1067,7 @@ var TabPanelItem = class extends AbstractGroup {
|
|
|
897
1067
|
}
|
|
898
1068
|
async isActive() {
|
|
899
1069
|
const tabPanelItemElement = await this.getElement();
|
|
900
|
-
const grandparentTab = await tabPanelItemElement.findElement(
|
|
1070
|
+
const grandparentTab = await tabPanelItemElement.findElement(By13.xpath('ancestor::div[@role="tab"][1]'));
|
|
901
1071
|
return await grandparentTab.getAttribute("aria-selected") === "true";
|
|
902
1072
|
}
|
|
903
1073
|
async getTitle() {
|
|
@@ -914,7 +1084,7 @@ var TabPanel = class extends AbstractGroup {
|
|
|
914
1084
|
};
|
|
915
1085
|
|
|
916
1086
|
// src/pageObjects/elements/Groups/Accordion/AccordionItem.ts
|
|
917
|
-
import { By as
|
|
1087
|
+
import { By as By14 } from "selenium-webdriver";
|
|
918
1088
|
var ACCORDION_TITLE_CONTAINER = "accordion-title-container";
|
|
919
1089
|
var AccordionItem = class extends AbstractGroup {
|
|
920
1090
|
constructor(parentCssSelector, elementCssSelector, driver) {
|
|
@@ -926,7 +1096,7 @@ var AccordionItem = class extends AbstractGroup {
|
|
|
926
1096
|
}
|
|
927
1097
|
async clickAccordionItemTitle() {
|
|
928
1098
|
const accordionElement = await this.getElement();
|
|
929
|
-
const accordTitleElement = await accordionElement.findElement(
|
|
1099
|
+
const accordTitleElement = await accordionElement.findElement(By14.className(ACCORDION_TITLE_CONTAINER));
|
|
930
1100
|
await accordTitleElement.click();
|
|
931
1101
|
}
|
|
932
1102
|
async click() {
|
|
@@ -1106,23 +1276,28 @@ var AbstractForm = class extends AbstractPage {
|
|
|
1106
1276
|
};
|
|
1107
1277
|
|
|
1108
1278
|
// src/pageObjects/elements/Forms/createSubFormInstance.ts
|
|
1279
|
+
var SECONDARY_DRAWER_LAYOUT_CONTENT = ".secondary-drawer-layout-content";
|
|
1109
1280
|
var subFormTestId = (name) => `subform-${name}`;
|
|
1110
|
-
function subformCssSelector(parentCssSelector, testId) {
|
|
1111
|
-
|
|
1281
|
+
function subformCssSelector(parentCssSelector, testId, isDockPanel = false) {
|
|
1282
|
+
if (isDockPanel) {
|
|
1283
|
+
return `${SECONDARY_DRAWER_LAYOUT_CONTENT} ${byTestIdCssSelector(testId)}`;
|
|
1284
|
+
} else {
|
|
1285
|
+
return `${parentCssSelector} ${byTestIdCssSelector(testId)}`;
|
|
1286
|
+
}
|
|
1112
1287
|
}
|
|
1113
1288
|
async function classDependencyInjector(formType) {
|
|
1114
1289
|
let SubFormFactoryClass;
|
|
1115
1290
|
switch (formType) {
|
|
1116
1291
|
case "1" /* LIST */:
|
|
1117
|
-
SubFormFactoryClass = (await import("./ListForm-
|
|
1292
|
+
SubFormFactoryClass = (await import("./ListForm-EM7E4ZMM.mjs")).default;
|
|
1118
1293
|
break;
|
|
1119
1294
|
case "3" /* TREE */:
|
|
1120
|
-
SubFormFactoryClass = (await import("./TreeView-
|
|
1295
|
+
SubFormFactoryClass = (await import("./TreeView-F2XF44N2.mjs")).default;
|
|
1121
1296
|
break;
|
|
1122
1297
|
case "2" /* EDIT */:
|
|
1123
1298
|
case "99" /* FREE_FORM */:
|
|
1124
1299
|
case "4" /* REPORT */:
|
|
1125
|
-
SubFormFactoryClass = (await import("./FormEdit-
|
|
1300
|
+
SubFormFactoryClass = (await import("./FormEdit-GTZISTTI.mjs")).default;
|
|
1126
1301
|
break;
|
|
1127
1302
|
default:
|
|
1128
1303
|
throw new Error(`Unsupported form type ${formType}`);
|
|
@@ -1152,10 +1327,15 @@ var Form = class extends AbstractForm {
|
|
|
1152
1327
|
*/
|
|
1153
1328
|
async getTitleText() {
|
|
1154
1329
|
if (await this.isModal()) {
|
|
1155
|
-
const titleEl2 = await this.driver.findElement(
|
|
1330
|
+
const titleEl2 = await this.driver.findElement(By15.css(`${this.popupContainerCssSelector} .popup-title`));
|
|
1331
|
+
await waitElementIsVisible({
|
|
1332
|
+
element: titleEl2,
|
|
1333
|
+
driver: this.driver,
|
|
1334
|
+
errorMessage: `Form title element is not visible`
|
|
1335
|
+
});
|
|
1156
1336
|
return titleEl2.getText();
|
|
1157
1337
|
}
|
|
1158
|
-
let titleEl = await this.driver.findElement(
|
|
1338
|
+
let titleEl = await this.driver.findElement(By15.className("main-toolbar-form-title"));
|
|
1159
1339
|
return titleEl.getText();
|
|
1160
1340
|
}
|
|
1161
1341
|
setSubFormMode() {
|
|
@@ -1171,9 +1351,10 @@ var Form = class extends AbstractForm {
|
|
|
1171
1351
|
* //...
|
|
1172
1352
|
* expect(await form.subForm(name));
|
|
1173
1353
|
*/
|
|
1174
|
-
async subForm(name) {
|
|
1175
|
-
const
|
|
1176
|
-
const
|
|
1354
|
+
async subForm(name, options = {}) {
|
|
1355
|
+
const { isDockPanel = false } = options;
|
|
1356
|
+
const cssSelector = subformCssSelector(this.containerCssSelector, subFormTestId(name), isDockPanel);
|
|
1357
|
+
const byCssSelector = By15.css(cssSelector);
|
|
1177
1358
|
const subFormEl = await this.driver.findElement(byCssSelector);
|
|
1178
1359
|
await waitElementIsVisible({
|
|
1179
1360
|
element: subFormEl,
|
|
@@ -1204,9 +1385,11 @@ export {
|
|
|
1204
1385
|
wait,
|
|
1205
1386
|
waitElementIsVisible,
|
|
1206
1387
|
click,
|
|
1388
|
+
contextMenu,
|
|
1207
1389
|
byTestIdCssSelector,
|
|
1208
1390
|
byTestId,
|
|
1209
1391
|
readonlyLocator,
|
|
1392
|
+
waitElementIsClickable_default,
|
|
1210
1393
|
AbstractElementWithParent,
|
|
1211
1394
|
TextEditor,
|
|
1212
1395
|
NumberEditor,
|
|
@@ -1218,7 +1401,6 @@ export {
|
|
|
1218
1401
|
createLayoutFilterTestId,
|
|
1219
1402
|
createTableId,
|
|
1220
1403
|
createSubSystemTestId,
|
|
1221
|
-
waitElementIsClickable,
|
|
1222
1404
|
AbstractButton,
|
|
1223
1405
|
AbstractEditor,
|
|
1224
1406
|
FormField,
|