@thinkwise/testwise 0.2.21 → 0.2.62

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.
Files changed (230) hide show
  1. package/Testwise.ts +2 -0
  2. package/artifact-builder/SelectorBuilder.ts +2 -2
  3. package/artifact-builder/SubjectComponentGenerator.ts +21 -12
  4. package/artifact-builder/SubjectGenerator.ts +20 -6
  5. package/components/action-bar/ActionBar.ts +7 -7
  6. package/components/action-bar/CustomActionBar.ts +0 -5
  7. package/components/cardlist/Cardlist.ts +3 -3
  8. package/components/chart/Chart.ts +3 -3
  9. package/components/combined-filter/CombinedFilter.ts +3 -3
  10. package/components/cube-view-bar/CubeViewBar.ts +3 -3
  11. package/components/filter/ExcelStyleFilterPopup.ts +29 -0
  12. package/components/filter/ExcelStyleFilterPopupObjects.ts +20 -0
  13. package/components/filter/FilterForm.ts +3 -3
  14. package/components/filter/FilterPopup.ts +187 -0
  15. package/components/filter/FilterPopupObjects.ts +63 -0
  16. package/components/filter/ManagePrefilterPopup.ts +44 -0
  17. package/components/filter/ManagePrefilterPopupObjects.ts +28 -0
  18. package/components/form/Form.ts +3 -3
  19. package/components/grid/Grid.ts +15 -119
  20. package/components/grid/GridObjects.ts +0 -4
  21. package/components/index.ts +4 -0
  22. package/components/maps/Maps.ts +3 -3
  23. package/components/menu/ListBarMenuComponent.ts +11 -0
  24. package/components/menu/ListBarMenuComponentObjects.ts +6 -0
  25. package/components/pivot-grid/PivotGrid.ts +3 -3
  26. package/components/pivot-grid/PivotGridFieldList.ts +3 -3
  27. package/components/pop-up/AllRowsPopUp.ts +29 -0
  28. package/components/pop-up/AllRowsPopUpObjects.ts +22 -0
  29. package/components/prefilter-list/PrefilterList.ts +3 -3
  30. package/components/preview/Preview.ts +3 -3
  31. package/components/report-bar/ReportBar.ts +3 -3
  32. package/components/report-tiles/ReportTiles.ts +3 -3
  33. package/components/scheduler/Scheduler.ts +3 -3
  34. package/components/splitter/Splitter.ts +3 -3
  35. package/components/tab/BaseTab.ts +3 -3
  36. package/components/tab/DetailTabPage.ts +4 -4
  37. package/components/tab/Tab.ts +4 -4
  38. package/components/task/TaskBar.ts +3 -3
  39. package/components/task/TaskTiles.ts +3 -3
  40. package/components/topbar/TopBar.ts +2 -0
  41. package/components/tree-view/TreeView.ts +3 -3
  42. package/controls/DateControl.ts +6 -6
  43. package/controls/DateControlObjects.ts +0 -0
  44. package/controls/FormComboBox.ts +7 -7
  45. package/controls/FormComboBoxObjects.ts +0 -0
  46. package/controls/GridColumnControl.ts +68 -0
  47. package/controls/GridColumnControlObjects.ts +20 -0
  48. package/controls/InputFieldControl.ts +6 -6
  49. package/controls/InputFieldControlObjects.ts +0 -0
  50. package/controls/LookupDropdown.ts +58 -16
  51. package/controls/index.ts +1 -0
  52. package/dist/Testwise.d.ts +1 -0
  53. package/dist/Testwise.js +1 -0
  54. package/dist/Testwise.js.map +1 -1
  55. package/dist/artifact-builder/SelectorBuilder.d.ts +1 -1
  56. package/dist/artifact-builder/SelectorBuilder.js +2 -2
  57. package/dist/artifact-builder/SelectorBuilder.js.map +1 -1
  58. package/dist/artifact-builder/SubjectComponentGenerator.js +18 -12
  59. package/dist/artifact-builder/SubjectComponentGenerator.js.map +1 -1
  60. package/dist/artifact-builder/SubjectGenerator.d.ts +1 -0
  61. package/dist/artifact-builder/SubjectGenerator.js +16 -6
  62. package/dist/artifact-builder/SubjectGenerator.js.map +1 -1
  63. package/dist/components/action-bar/ActionBar.d.ts +2 -2
  64. package/dist/components/action-bar/ActionBar.js +7 -7
  65. package/dist/components/action-bar/ActionBar.js.map +1 -1
  66. package/dist/components/action-bar/CustomActionBar.d.ts +0 -2
  67. package/dist/components/action-bar/CustomActionBar.js +0 -3
  68. package/dist/components/action-bar/CustomActionBar.js.map +1 -1
  69. package/dist/components/cardlist/Cardlist.d.ts +2 -2
  70. package/dist/components/cardlist/Cardlist.js +2 -2
  71. package/dist/components/cardlist/Cardlist.js.map +1 -1
  72. package/dist/components/chart/Chart.d.ts +2 -2
  73. package/dist/components/chart/Chart.js +2 -2
  74. package/dist/components/chart/Chart.js.map +1 -1
  75. package/dist/components/combined-filter/CombinedFilter.d.ts +2 -2
  76. package/dist/components/combined-filter/CombinedFilter.js +2 -2
  77. package/dist/components/combined-filter/CombinedFilter.js.map +1 -1
  78. package/dist/components/cube-view-bar/CubeViewBar.d.ts +2 -2
  79. package/dist/components/cube-view-bar/CubeViewBar.js +2 -2
  80. package/dist/components/cube-view-bar/CubeViewBar.js.map +1 -1
  81. package/dist/components/filter/ExcelStyleFilterPopup.d.ts +9 -0
  82. package/dist/components/filter/ExcelStyleFilterPopup.js +22 -0
  83. package/dist/components/filter/ExcelStyleFilterPopup.js.map +1 -0
  84. package/dist/components/filter/ExcelStyleFilterPopupObjects.d.ts +9 -0
  85. package/dist/components/filter/ExcelStyleFilterPopupObjects.js +13 -0
  86. package/dist/components/filter/ExcelStyleFilterPopupObjects.js.map +1 -0
  87. package/dist/components/filter/FilterForm.d.ts +2 -2
  88. package/dist/components/filter/FilterForm.js +2 -2
  89. package/dist/components/filter/FilterForm.js.map +1 -1
  90. package/dist/components/filter/FilterPopup.d.ts +41 -0
  91. package/dist/components/filter/FilterPopup.js +126 -0
  92. package/dist/components/filter/FilterPopup.js.map +1 -0
  93. package/dist/components/filter/FilterPopupObjects.d.ts +29 -0
  94. package/dist/components/filter/FilterPopupObjects.js +30 -0
  95. package/dist/components/filter/FilterPopupObjects.js.map +1 -0
  96. package/dist/components/filter/ManagePrefilterPopup.d.ts +14 -0
  97. package/dist/components/filter/ManagePrefilterPopup.js +33 -0
  98. package/dist/components/filter/ManagePrefilterPopup.js.map +1 -0
  99. package/dist/components/filter/ManagePrefilterPopupObjects.d.ts +11 -0
  100. package/dist/components/filter/ManagePrefilterPopupObjects.js +19 -0
  101. package/dist/components/filter/ManagePrefilterPopupObjects.js.map +1 -0
  102. package/dist/components/form/Form.d.ts +2 -2
  103. package/dist/components/form/Form.js +2 -2
  104. package/dist/components/form/Form.js.map +1 -1
  105. package/dist/components/grid/Grid.d.ts +4 -36
  106. package/dist/components/grid/Grid.js +14 -102
  107. package/dist/components/grid/Grid.js.map +1 -1
  108. package/dist/components/grid/GridObjects.d.ts +0 -2
  109. package/dist/components/grid/GridObjects.js +0 -2
  110. package/dist/components/grid/GridObjects.js.map +1 -1
  111. package/dist/components/index.d.ts +4 -0
  112. package/dist/components/index.js +4 -0
  113. package/dist/components/index.js.map +1 -1
  114. package/dist/components/maps/Maps.d.ts +2 -2
  115. package/dist/components/maps/Maps.js +2 -2
  116. package/dist/components/maps/Maps.js.map +1 -1
  117. package/dist/components/menu/ListBarMenuComponent.d.ts +6 -0
  118. package/dist/components/menu/ListBarMenuComponent.js +10 -0
  119. package/dist/components/menu/ListBarMenuComponent.js.map +1 -1
  120. package/dist/components/menu/ListBarMenuComponentObjects.d.ts +2 -0
  121. package/dist/components/menu/ListBarMenuComponentObjects.js +2 -0
  122. package/dist/components/menu/ListBarMenuComponentObjects.js.map +1 -1
  123. package/dist/components/pivot-grid/PivotGrid.d.ts +2 -2
  124. package/dist/components/pivot-grid/PivotGrid.js +2 -2
  125. package/dist/components/pivot-grid/PivotGrid.js.map +1 -1
  126. package/dist/components/pivot-grid/PivotGridFieldList.d.ts +2 -2
  127. package/dist/components/pivot-grid/PivotGridFieldList.js +2 -2
  128. package/dist/components/pivot-grid/PivotGridFieldList.js.map +1 -1
  129. package/dist/components/pop-up/AllRowsPopUp.d.ts +12 -0
  130. package/dist/components/pop-up/AllRowsPopUp.js +19 -0
  131. package/dist/components/pop-up/AllRowsPopUp.js.map +1 -0
  132. package/dist/components/pop-up/AllRowsPopUpObjects.d.ts +11 -0
  133. package/dist/components/pop-up/AllRowsPopUpObjects.js +13 -0
  134. package/dist/components/pop-up/AllRowsPopUpObjects.js.map +1 -0
  135. package/dist/components/prefilter-list/PrefilterList.d.ts +2 -2
  136. package/dist/components/prefilter-list/PrefilterList.js +2 -2
  137. package/dist/components/prefilter-list/PrefilterList.js.map +1 -1
  138. package/dist/components/preview/Preview.d.ts +2 -2
  139. package/dist/components/preview/Preview.js +2 -2
  140. package/dist/components/preview/Preview.js.map +1 -1
  141. package/dist/components/report-bar/ReportBar.d.ts +2 -2
  142. package/dist/components/report-bar/ReportBar.js +2 -2
  143. package/dist/components/report-bar/ReportBar.js.map +1 -1
  144. package/dist/components/report-tiles/ReportTiles.d.ts +2 -2
  145. package/dist/components/report-tiles/ReportTiles.js +2 -2
  146. package/dist/components/report-tiles/ReportTiles.js.map +1 -1
  147. package/dist/components/scheduler/Scheduler.d.ts +2 -2
  148. package/dist/components/scheduler/Scheduler.js +2 -2
  149. package/dist/components/scheduler/Scheduler.js.map +1 -1
  150. package/dist/components/splitter/Splitter.d.ts +2 -2
  151. package/dist/components/splitter/Splitter.js +2 -2
  152. package/dist/components/splitter/Splitter.js.map +1 -1
  153. package/dist/components/tab/BaseTab.d.ts +2 -2
  154. package/dist/components/tab/BaseTab.js +2 -2
  155. package/dist/components/tab/BaseTab.js.map +1 -1
  156. package/dist/components/tab/DetailTabPage.d.ts +2 -2
  157. package/dist/components/tab/DetailTabPage.js +3 -3
  158. package/dist/components/tab/DetailTabPage.js.map +1 -1
  159. package/dist/components/tab/Tab.d.ts +2 -2
  160. package/dist/components/tab/Tab.js +3 -3
  161. package/dist/components/tab/Tab.js.map +1 -1
  162. package/dist/components/task/TaskBar.d.ts +2 -2
  163. package/dist/components/task/TaskBar.js +2 -2
  164. package/dist/components/task/TaskBar.js.map +1 -1
  165. package/dist/components/task/TaskTiles.d.ts +2 -2
  166. package/dist/components/task/TaskTiles.js +2 -2
  167. package/dist/components/task/TaskTiles.js.map +1 -1
  168. package/dist/components/topbar/TopBar.d.ts +1 -0
  169. package/dist/components/topbar/TopBar.js +1 -0
  170. package/dist/components/topbar/TopBar.js.map +1 -1
  171. package/dist/components/tree-view/TreeView.d.ts +2 -2
  172. package/dist/components/tree-view/TreeView.js +2 -2
  173. package/dist/components/tree-view/TreeView.js.map +1 -1
  174. package/dist/controls/DateControl.d.ts +3 -3
  175. package/dist/controls/DateControl.js +5 -5
  176. package/dist/controls/DateControl.js.map +1 -1
  177. package/dist/controls/DateControlObjects.d.ts +1 -0
  178. package/dist/controls/DateControlObjects.js +2 -0
  179. package/dist/controls/DateControlObjects.js.map +1 -0
  180. package/dist/controls/FormComboBox.d.ts +2 -2
  181. package/dist/controls/FormComboBox.js +6 -6
  182. package/dist/controls/FormComboBox.js.map +1 -1
  183. package/dist/controls/FormComboBoxObjects.d.ts +1 -0
  184. package/dist/controls/FormComboBoxObjects.js +2 -0
  185. package/dist/controls/FormComboBoxObjects.js.map +1 -0
  186. package/dist/controls/GridColumnControl.d.ts +10 -0
  187. package/dist/controls/GridColumnControl.js +43 -0
  188. package/dist/controls/GridColumnControl.js.map +1 -0
  189. package/dist/controls/GridColumnControlObjects.d.ts +9 -0
  190. package/dist/controls/GridColumnControlObjects.js +13 -0
  191. package/dist/controls/GridColumnControlObjects.js.map +1 -0
  192. package/dist/controls/InputFieldControl.d.ts +3 -3
  193. package/dist/controls/InputFieldControl.js +5 -5
  194. package/dist/controls/InputFieldControl.js.map +1 -1
  195. package/dist/controls/InputFieldControlObjects.d.ts +1 -0
  196. package/dist/controls/InputFieldControlObjects.js +2 -0
  197. package/dist/controls/InputFieldControlObjects.js.map +1 -0
  198. package/dist/controls/LookupDropdown.d.ts +6 -1
  199. package/dist/controls/LookupDropdown.js +42 -13
  200. package/dist/controls/LookupDropdown.js.map +1 -1
  201. package/dist/controls/index.d.ts +1 -0
  202. package/dist/controls/index.js +1 -0
  203. package/dist/controls/index.js.map +1 -1
  204. package/dist/enums/ElementTypes.d.ts +1 -1
  205. package/dist/enums/ElementTypes.js +1 -1
  206. package/dist/enums/ElementTypes.js.map +1 -1
  207. package/dist/helpers/FlightTracker.d.ts +7 -0
  208. package/dist/helpers/FlightTracker.js +63 -11
  209. package/dist/helpers/FlightTracker.js.map +1 -1
  210. package/dist/helpers/LoginHelper.d.ts +11 -3
  211. package/dist/helpers/LoginHelper.js +59 -13
  212. package/dist/helpers/LoginHelper.js.map +1 -1
  213. package/dist/index.d.ts +1 -1
  214. package/dist/index.js +1 -1
  215. package/dist/index.js.map +1 -1
  216. package/dist/page-extensions/GlobalComponents.d.ts +2 -1
  217. package/dist/page-extensions/GlobalComponents.js +2 -1
  218. package/dist/page-extensions/GlobalComponents.js.map +1 -1
  219. package/dist/page-overrides/ClickOverride.d.ts +1 -0
  220. package/dist/page-overrides/ClickOverride.js +57 -46
  221. package/dist/page-overrides/ClickOverride.js.map +1 -1
  222. package/dist/types/Universal.d.ts +1 -0
  223. package/enums/ElementTypes.ts +1 -1
  224. package/helpers/FlightTracker.ts +71 -11
  225. package/helpers/LoginHelper.ts +79 -21
  226. package/index.ts +1 -1
  227. package/package.json +6 -5
  228. package/page-extensions/GlobalComponents.ts +3 -0
  229. package/page-overrides/ClickOverride.ts +69 -64
  230. package/types/Universal.ts +1 -0
@@ -4,18 +4,29 @@ const waitForRequestsToComplete = testwiseConfig().get('featureSettings.Inflight
4
4
  const continueOnError = testwiseConfig().get('featureSettings.InflightRequests.continueOnError') ?? true;
5
5
  export class ClickOverride {
6
6
  constructor(test) {
7
+ this._page = null;
7
8
  this.flightTracker = new FlightTracker();
8
9
  this._test = test.extend({
9
10
  page: async ({ page }, use) => {
11
+ this._page = page;
12
+ const isTrackable = (url, resourceType) => {
13
+ const lowerUrl = url.toLowerCase();
14
+ return (resourceType === 'xhr' &&
15
+ !lowerUrl.includes('/detect_change(') &&
16
+ !lowerUrl.includes('/set_gui_start_use_log_session') &&
17
+ !lowerUrl.includes('download_icon') &&
18
+ !lowerUrl.includes('download_list_bar_grp_icon') &&
19
+ !lowerUrl.includes('/badge()'));
20
+ };
10
21
  const overrideClickMethod = (locator) => {
11
22
  const originalClickMethod = locator.click.bind(locator);
12
23
  page.on('request', (request) => {
13
- if (request.resourceType() === 'xhr') {
24
+ if (isTrackable(request.url(), request.resourceType())) {
14
25
  this.flightTracker.requestsInFlight++;
15
26
  }
16
27
  });
17
28
  page.on('response', (response) => {
18
- if (response.request().resourceType() === 'xhr') {
29
+ if (isTrackable(response.request().url(), response.request().resourceType())) {
19
30
  if (this.flightTracker.requestsInFlight > 0) {
20
31
  this.flightTracker.requestsInFlight--;
21
32
  }
@@ -32,57 +43,57 @@ export class ClickOverride {
32
43
  }
33
44
  catch (error) {
34
45
  console.warn('Exception while waiting for inflight requests to finish:', error);
46
+ if (this._page) {
47
+ const inflightRequests = await this._page.evaluate(() => {
48
+ return performance
49
+ .getEntriesByType('resource')
50
+ .filter((entry) => {
51
+ const res = entry;
52
+ return (res.initiatorType === 'xmlhttprequest' &&
53
+ !res.name.includes('/detect_change(') &&
54
+ !res.name.includes('/set_gui_start_use_log_session'));
55
+ })
56
+ .map((entry) => entry.name);
57
+ });
58
+ console.debug('Current inflight XHR requests:', inflightRequests);
59
+ }
35
60
  if (!continueOnError)
36
61
  throw error;
37
62
  }
38
63
  }
64
+ return;
39
65
  };
40
- // Ensure chaining works by overriding methods that return new Locators
41
- const originalLocatorMethod = locator.locator.bind(locator);
42
- locator.locator = (...args) => overrideClickMethod(originalLocatorMethod(...args));
43
- // Override the filter method so returned locators also have custom click logic
44
- const originalFilterMethod = locator.filter?.bind(locator);
45
- locator.filter = (...args) => overrideClickMethod(originalFilterMethod(...args));
46
- const originalGetByTextMethod = locator.getByText.bind(locator);
47
- locator.getByText = (...args) => overrideClickMethod(originalGetByTextMethod(...args));
48
- const originalGetByTestIdMethod = locator.getByTestId.bind(locator);
49
- locator.getByTestId = (...args) => overrideClickMethod(originalGetByTestIdMethod(...args));
50
- const originalGetByAltTextMethod = locator.getByAltText.bind(locator);
51
- locator.getByAltText = (...args) => overrideClickMethod(originalGetByAltTextMethod(...args));
52
- const originalGetByLabelMethod = locator.getByLabel.bind(locator);
53
- locator.getByLabel = (...args) => overrideClickMethod(originalGetByLabelMethod(...args));
54
- const originalGetByRoleMethod = locator.getByRole.bind(locator);
55
- locator.getByRole = (...args) => overrideClickMethod(originalGetByRoleMethod(...args));
56
- const originalGetByPlaceholderMethod = locator.getByPlaceholder.bind(locator);
57
- locator.getByPlaceholder = (...args) => overrideClickMethod(originalGetByPlaceholderMethod(...args));
58
- const originalGetByTitleMethod = locator.getByTitle.bind(locator);
59
- locator.getByTitle = (...args) => overrideClickMethod(originalGetByTitleMethod(...args));
66
+ const locatorMethods = [
67
+ 'locator',
68
+ 'filter',
69
+ 'getByText',
70
+ 'getByTestId',
71
+ 'getByAltText',
72
+ 'getByLabel',
73
+ 'getByRole',
74
+ 'getByPlaceholder',
75
+ 'getByTitle'
76
+ ];
77
+ for (const method of locatorMethods) {
78
+ const original = locator[method].bind(locator);
79
+ locator[method] = (...args) => overrideClickMethod(original(...args));
80
+ }
60
81
  return locator;
61
82
  };
62
- // Override the getByTestId.click method
63
- const originalGetByTestId = page.getByTestId.bind(page);
64
- page.getByTestId = (...args) => overrideClickMethod(originalGetByTestId(...args));
65
- // Override the locator.click method
66
- const originalLocator = page.locator.bind(page);
67
- page.locator = (...args) => overrideClickMethod(originalLocator(...args));
68
- // Override the getByAltText.click method
69
- const originalGetByAltText = page.getByAltText.bind(page);
70
- page.getByAltText = (...args) => overrideClickMethod(originalGetByAltText(...args));
71
- // Override the getByLabel.click method
72
- const originalGetByLabel = page.getByLabel.bind(page);
73
- page.getByLabel = (...args) => overrideClickMethod(originalGetByLabel(...args));
74
- // Override the getByRole.click method
75
- const originalGetByRole = page.getByRole.bind(page);
76
- page.getByRole = (...args) => overrideClickMethod(originalGetByRole(...args));
77
- // Override the getByPlaceholder.click method
78
- const originalGetByPlaceholder = page.getByPlaceholder.bind(page);
79
- page.getByPlaceholder = (...args) => overrideClickMethod(originalGetByPlaceholder(...args));
80
- // Override the getByText.click method
81
- const originalGetByText = page.getByText.bind(page);
82
- page.getByText = (...args) => overrideClickMethod(originalGetByText(...args));
83
- // Override the getByTitle.click method
84
- const originalGetByTitle = page.getByTitle.bind(page);
85
- page.getByTitle = (...args) => overrideClickMethod(originalGetByTitle(...args));
83
+ const rootMethods = [
84
+ 'locator',
85
+ 'getByTestId',
86
+ 'getByAltText',
87
+ 'getByLabel',
88
+ 'getByRole',
89
+ 'getByPlaceholder',
90
+ 'getByText',
91
+ 'getByTitle'
92
+ ];
93
+ for (const method of rootMethods) {
94
+ const original = page[method].bind(page);
95
+ page[method] = (...args) => overrideClickMethod(original(...args));
96
+ }
86
97
  await use(page);
87
98
  }
88
99
  });
@@ -1 +1 @@
1
- {"version":3,"file":"ClickOverride.js","sourceRoot":"","sources":["../../page-overrides/ClickOverride.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"ClickOverride.js","sourceRoot":"","sources":["../../page-overrides/ClickOverride.ts"],"names":[],"mappings":"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"}
@@ -22,4 +22,5 @@ export type UniversalLoginOptions = {
22
22
  serviceUrl?: string;
23
23
  metaEndpoint?: string;
24
24
  config?: UniversalConfigOptions;
25
+ userPreference?: number;
25
26
  };
@@ -4,7 +4,7 @@ export enum KnownElementTypes {
4
4
  Textarea = 'textarea',
5
5
  Checkbox = 'checkbox',
6
6
  Lookup = 'lookup',
7
- Column = 'column_cells',
7
+ Column = 'column',
8
8
  ComboBox = 'combo_box',
9
9
  DatePicker = 'date_picker'
10
10
  }
@@ -2,25 +2,85 @@ import { EventEmitter } from 'node:events';
2
2
  import { testwiseConfig } from '../services/ConfigBuilder.js';
3
3
 
4
4
  const timeout = testwiseConfig().get<number>('featureSettings.InflightRequests.waitTimeout') ?? 5000;
5
+ const stabilityTime = 150;
5
6
 
6
7
  export class FlightTracker {
7
8
  public requestsInFlight: number = 0;
9
+ private activeRequests = new Set<string>();
8
10
  public eventEmitter: EventEmitter = new EventEmitter();
9
11
 
12
+ /**
13
+ * Filters out non-functional "noise" requests that shouldn't block test execution.
14
+ */
15
+ public isEssentialRequest(url: string): boolean {
16
+ const noisePatterns = [
17
+ '.download_icon',
18
+ '.download_list_bar_grp_icon',
19
+ '.download_form_next_grp_icon',
20
+ '/badge()',
21
+ 'universal_background_picture',
22
+ 'i_ui_theme'
23
+ ];
24
+
25
+ return !noisePatterns.some((pattern) => url.includes(pattern));
26
+ }
27
+
28
+ public handleRequestStarted = (url: string) => {
29
+ if (this.isEssentialRequest(url)) {
30
+ this.activeRequests.add(url);
31
+ this.requestsInFlight = this.activeRequests.size;
32
+ }
33
+ };
34
+
35
+ public handleRequestFinished = (url: string) => {
36
+ if (this.isEssentialRequest(url)) {
37
+ this.activeRequests.delete(url);
38
+ this.requestsInFlight = this.activeRequests.size;
39
+ if (this.requestsInFlight === 0) {
40
+ this.eventEmitter.emit('idle');
41
+ }
42
+ }
43
+ };
44
+
10
45
  public waitToContinue = async (): Promise<void> => {
11
46
  if (this.requestsInFlight === 0) {
12
- return;
47
+ await new Promise((res) => setTimeout(res, stabilityTime));
48
+ if (this.requestsInFlight === 0) return;
13
49
  }
14
50
 
15
- await Promise.race([
16
- new Promise<void>((resolve) => {
17
- this.eventEmitter.once('idle', resolve);
18
- }),
19
- new Promise<void>((_, reject) => {
20
- setTimeout(() => {
21
- reject(new Error('Timeout waiting for requests to complete'));
22
- }, timeout);
23
- })
24
- ]);
51
+ let timeoutId: NodeJS.Timeout;
52
+
53
+ const idlePromise = new Promise<void>((resolve) => {
54
+ const checkIdle = () => {
55
+ if (this.requestsInFlight === 0) {
56
+ setTimeout(() => {
57
+ if (this.requestsInFlight === 0) {
58
+ this.eventEmitter.off('idle', checkIdle);
59
+ resolve();
60
+ }
61
+ }, stabilityTime);
62
+ }
63
+ };
64
+ this.eventEmitter.on('idle', checkIdle);
65
+ });
66
+
67
+ const timeoutPromise = new Promise<void>((_, reject) => {
68
+ timeoutId = setTimeout(() => {
69
+ const pending = Array.from(this.activeRequests).join('\n -> ');
70
+ reject(
71
+ new Error(
72
+ `Timeout waiting for ${this.requestsInFlight} requests to complete (${timeout}ms).\nPending Essential Requests:\n -> ${pending}`
73
+ )
74
+ );
75
+ }, timeout);
76
+ });
77
+
78
+ try {
79
+ await Promise.race([idlePromise, timeoutPromise]);
80
+ } finally {
81
+ // biome-ignore lint/style/noNonNullAssertion: should be defined if we reach here
82
+ if (timeoutId!) clearTimeout(timeoutId);
83
+ this.eventEmitter.removeAllListeners('idle');
84
+ }
25
85
  };
26
86
  }
@@ -1,32 +1,24 @@
1
1
  import fs from 'node:fs';
2
2
  import path from 'node:path';
3
3
  import { fileURLToPath } from 'node:url';
4
- import type { Page } from '@playwright/test';
4
+ import type { APIResponse, Page } from '@playwright/test';
5
5
  import { testwiseConfig } from '../services/ConfigBuilder.js';
6
6
  import type { UniversalConfigOptions, UniversalLoginOptions } from '../types/index.js';
7
7
  import { pollUntil } from './Poll.js';
8
8
 
9
- const _dirname = path.dirname(fileURLToPath(import.meta.url));
10
- const configFixture = JSON.parse(fs.readFileSync(path.resolve(_dirname, '../../config.json'), 'utf-8'));
9
+ const dirname = path.dirname(fileURLToPath(import.meta.url));
10
+ const configFixture = JSON.parse(fs.readFileSync(path.resolve(dirname, '../../config.json'), 'utf-8'));
11
11
 
12
12
  export class LoginHelper {
13
13
  private _page: Page;
14
- private _serviceUrl: string;
15
- private _metaEndpoint: string;
14
+ protected serviceUrl = String(testwiseConfig().get('environmentSettings.serviceUrl'));
15
+ protected metaEndpoint = String(testwiseConfig().get('environmentSettings.metaEndpoint'));
16
16
 
17
17
  constructor(page: Page) {
18
- this._page = page;
19
-
20
- const serviceUrl = testwiseConfig().get<string>('environmentSettings.serviceUrl');
21
- const metaEndpoint = testwiseConfig().get<string>('environmentSettings.metaEndpoint');
18
+ if (!this.serviceUrl || this.serviceUrl === 'undefined') throw new Error('Service URL not found');
19
+ if (!this.metaEndpoint || this.metaEndpoint === 'undefined') throw new Error('Meta endpoint not found');
22
20
 
23
- if (!serviceUrl || !metaEndpoint)
24
- throw new Error(
25
- 'Either environmentSettings.serviceUrl or environmentSettings.metaEndpoint is not defined in the configuration.'
26
- );
27
-
28
- this._serviceUrl = serviceUrl;
29
- this._metaEndpoint = metaEndpoint;
21
+ this._page = page;
30
22
  }
31
23
 
32
24
  /**
@@ -101,11 +93,11 @@ export class LoginHelper {
101
93
  }
102
94
 
103
95
  if (serviceUrl && metaEndpoint) {
104
- this._serviceUrl = serviceUrl;
105
- this._metaEndpoint = metaEndpoint;
96
+ this.serviceUrl = serviceUrl;
97
+ this.metaEndpoint = metaEndpoint;
106
98
  }
107
99
 
108
- const response = await this._page.request.post(`${this._serviceUrl}/account/api/login`, {
100
+ const response = await this._page.request.post(`${this.serviceUrl}/account/api/login`, {
109
101
  form: {
110
102
  UserName: username,
111
103
  Password: password
@@ -116,6 +108,36 @@ export class LoginHelper {
116
108
  throw new Error(`Login failed with status code: ${response.status()}`);
117
109
  }
118
110
 
111
+ if (password === username && /^Worker_\d+$/.test(username)) {
112
+ const userPreferences = new UserPreferences(this._page, this.serviceUrl, this.metaEndpoint);
113
+
114
+ if (!options.userPreference) {
115
+ console.info(
116
+ `No user preference configuration ID provided for worker account ${username}. User preferences will be disabled to prevent unexpected test behavior.`
117
+ );
118
+ } else {
119
+ console.info(
120
+ `User preference configuration ID ${options.userPreference} provided for worker account ${username}. Attempting to disable user preferences before re-enabling with provided configuration.`
121
+ );
122
+ }
123
+
124
+ try {
125
+ await userPreferences.disable();
126
+ console.info(`Successfully disabled user preferences for worker account ${username}.`);
127
+
128
+ if (options.userPreference) {
129
+ await userPreferences.run(options.userPreference);
130
+ console.info(
131
+ `Successfully re-enabled user preferences for worker account ${username} with configuration ID ${options.userPreference}.`
132
+ );
133
+ }
134
+ } catch (error) {
135
+ console.warn(
136
+ `User preferences may not be properly configured for worker account ${username}. Tests may be unstable. Error details: ${error}`
137
+ );
138
+ }
139
+ }
140
+
119
141
  // Set the navigator.language property
120
142
  await this._page.route('**/*', (route, request) => {
121
143
  route.continue({
@@ -142,7 +164,7 @@ export class LoginHelper {
142
164
  contentType: 'application/json',
143
165
  body: JSON.stringify({
144
166
  ...configFixture,
145
- serviceUrl: `${this._serviceUrl}/iam/${this._metaEndpoint}`,
167
+ serviceUrl: `${this.serviceUrl}/iam/${this.metaEndpoint}`,
146
168
  ...options
147
169
  })
148
170
  });
@@ -150,7 +172,7 @@ export class LoginHelper {
150
172
  }
151
173
 
152
174
  public async logOut() {
153
- const response = await this._page.request.post(`${this._serviceUrl}/account/api/logout`);
175
+ const response = await this._page.request.post(`${this.serviceUrl}/account/api/logout`);
154
176
 
155
177
  if (![204, 401].includes(response.status())) {
156
178
  throw new Error(`Logout failed with status code: ${response.status()}`);
@@ -159,3 +181,39 @@ export class LoginHelper {
159
181
  await this._page.context().clearCookies();
160
182
  }
161
183
  }
184
+
185
+ export class UserPreferences {
186
+ private _page: Page;
187
+
188
+ public readonly guiApplAlias = String(testwiseConfig().get<string>('environmentSettings.guiApplAlias'));
189
+ public readonly url: string;
190
+
191
+ constructor(requestContext: Page, serviceUrl?: string, metaEndpoint?: string) {
192
+ this._page = requestContext;
193
+
194
+ serviceUrl = serviceUrl ?? testwiseConfig().get<string>('environmentSettings.serviceUrl');
195
+ metaEndpoint = metaEndpoint ?? testwiseConfig().get<string>('environmentSettings.metaEndpoint');
196
+
197
+ if (!serviceUrl) throw new Error('Service URL not found or is empty');
198
+ if (!metaEndpoint) throw new Error('Meta endpoint not found or is empty');
199
+ if (!this.guiApplAlias) throw new Error('GUI application alias not found or is empty');
200
+
201
+ this.url = `${serviceUrl}/${metaEndpoint}/${this.guiApplAlias}`;
202
+ }
203
+
204
+ public async run(upConfigurationId: number) {
205
+ const fullUrl = `${this.url}/set_up_configuration`;
206
+
207
+ const data = {
208
+ up_configuration_id: upConfigurationId
209
+ };
210
+
211
+ await this._page.request.post(fullUrl, { headers: { 'Content-Type': 'application/json; charset=utf-8' }, data });
212
+ }
213
+
214
+ public async disable(): Promise<APIResponse> {
215
+ const fullUrl = `${this.url}/disable_up`;
216
+
217
+ return await this._page.request.post(fullUrl, { headers: { 'Content-Type': 'application/json; charset=utf-8' } });
218
+ }
219
+ }
package/index.ts CHANGED
@@ -12,7 +12,6 @@ console.warn = (...args: unknown[]) => logger.warn(args.join(' '));
12
12
  console.error = (...args: unknown[]) => logger.error(args.join(' '));
13
13
  console.debug = (...args: unknown[]) => logger.debug(args.join(' '));
14
14
 
15
- export { originalLog, originalInfo, originalWarn, originalError, originalDebug };
16
15
  export * from './artifact-builder/index.js';
17
16
  export * from './components/index.js';
18
17
  export * from './controls/index.js';
@@ -23,3 +22,4 @@ export * from './page-overrides/index.js';
23
22
  export * from './services/index.js';
24
23
  export * from './Testwise.js';
25
24
  export * from './types/index.js';
25
+ export { originalDebug, originalError, originalInfo, originalLog, originalWarn };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@thinkwise/testwise",
3
- "version": "0.2.21",
3
+ "version": "0.2.62",
4
4
  "main": "dist/index.js",
5
5
  "type": "module",
6
6
  "bin": {
@@ -9,8 +9,8 @@
9
9
  },
10
10
  "scripts": {
11
11
  "lint": "eslint ./ --cache --ignore-pattern .gitignore",
12
- "format:fix": "npm run lint --fix && biome check --fix --unsafe",
13
- "format:check": "npm run lint && biome check",
12
+ "format:fix": "run-s \"lint --fix\" && biome check --fix --unsafe",
13
+ "format:check": "run-s \"lint \" && biome check",
14
14
  "postinstall": "node scripts/main.js postinstall"
15
15
  },
16
16
  "keywords": [],
@@ -18,7 +18,7 @@
18
18
  "license": "ISC",
19
19
  "description": "",
20
20
  "dependencies": {
21
- "@thinkwise/backups": "^1.0.13",
21
+ "@thinkwise/backups": "^1.0.16",
22
22
  "@types/node": "^22.15.29",
23
23
  "axios": "^1.9.0",
24
24
  "chalk": "^5.4.1",
@@ -37,10 +37,11 @@
37
37
  "@playwright/test": "^1.56.1"
38
38
  },
39
39
  "devDependencies": {
40
- "@biomejs/biome": "^2.3.8",
40
+ "@biomejs/biome": "^2.4.8",
41
41
  "@eslint/js": "^9.28.0",
42
42
  "eslint": "^9.39.2",
43
43
  "eslint-plugin-playwright": "^2.2.0",
44
+ "npm-run-all": "^4.1.5",
44
45
  "typescript-eslint": "^8.34.0"
45
46
  },
46
47
  "exports": {
@@ -2,6 +2,7 @@ import type { Page } from '@playwright/test';
2
2
  import {
3
3
  ExportComponent,
4
4
  ListBarMenuComponent,
5
+ ManagePrefilterPopup,
5
6
  PopUpComponent,
6
7
  SnackBarComponent,
7
8
  TopBarComponent
@@ -14,6 +15,7 @@ class GlobalComponents {
14
15
  public snackBar: SnackBarComponent;
15
16
  public topBar: TopBarComponent;
16
17
  public listBarMenu: ListBarMenuComponent;
18
+ public managePrefilterPopup: ManagePrefilterPopup;
17
19
 
18
20
  constructor(page: Page) {
19
21
  this.popUp = new PopUpComponent(page);
@@ -21,6 +23,7 @@ class GlobalComponents {
21
23
  this.snackBar = new SnackBarComponent(page);
22
24
  this.topBar = new TopBarComponent(page);
23
25
  this.listBarMenu = new ListBarMenuComponent(page);
26
+ this.managePrefilterPopup = new ManagePrefilterPopup(page);
24
27
  }
25
28
  }
26
29