@thinkwise/testwise 0.2.62 → 0.2.99

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 (458) hide show
  1. package/Testwise.ts +35 -0
  2. package/artifact-builder/ArtifactManager.ts +25 -2
  3. package/artifact-builder/ComponentClassModelBuilder.ts +148 -0
  4. package/artifact-builder/InterfaceGenerator.ts +31 -33
  5. package/artifact-builder/ModelDataBuilder.ts +18 -20
  6. package/artifact-builder/ModelDataRefiner.ts +23 -3
  7. package/artifact-builder/SchemaGenerator.ts +45 -35
  8. package/artifact-builder/ScreenInterfaceRefiner.ts +25 -10
  9. package/artifact-builder/SelectorBuilder.ts +30 -24
  10. package/artifact-builder/SubjectClassModelBuilder.ts +209 -0
  11. package/artifact-builder/SubjectComponentGenerator.ts +67 -246
  12. package/artifact-builder/SubjectGenerator.ts +117 -230
  13. package/artifact-builder/SubjectRegistration.ts +41 -32
  14. package/artifact-builder/TsFileModel.ts +94 -0
  15. package/artifact-builder/TsFileSerializer.ts +247 -0
  16. package/artifact-builder/helpers/DataRetriever.ts +64 -27
  17. package/artifact-builder/helpers/NamingHandler.ts +23 -78
  18. package/artifact-builder/helpers/PipelinePaths.ts +123 -0
  19. package/artifact-builder/helpers/Stopwatch.ts +10 -0
  20. package/artifact-builder/helpers/index.ts +1 -0
  21. package/artifact-builder/index.ts +4 -0
  22. package/components/BaseComponentObjects.ts +17 -0
  23. package/components/action-bar/ActionBar.ts +35 -47
  24. package/components/action-bar/ActionBarObjects.ts +2 -0
  25. package/components/action-bar/CustomActionBar.ts +6 -0
  26. package/components/cardlist/Cardlist.ts +6 -0
  27. package/components/chart/Chart.ts +6 -0
  28. package/components/combined-filter/CombinedFilter.ts +9 -0
  29. package/components/cube-view-bar/CubeViewBar.ts +6 -0
  30. package/components/export/ExportComponent.ts +12 -0
  31. package/components/filter/ExcelStyleFilterPopup.ts +83 -10
  32. package/components/filter/ExcelStyleFilterPopupObjects.ts +29 -3
  33. package/components/filter/FilterForm.ts +10 -0
  34. package/components/filter/FilterPopup.ts +30 -9
  35. package/components/filter/FilterPopupObjects.ts +10 -3
  36. package/components/filter/FindForm.ts +7 -0
  37. package/components/filter/ManagePrefilterPopup.ts +11 -0
  38. package/components/form/Form.ts +16 -0
  39. package/components/grid/Grid.ts +50 -14
  40. package/components/grid/GridObjects.ts +0 -15
  41. package/components/maps/Maps.ts +6 -0
  42. package/components/menu/ListBarMenuComponent.ts +10 -0
  43. package/components/pivot-grid/PivotGrid.ts +6 -0
  44. package/components/pivot-grid/PivotGridFieldList.ts +7 -0
  45. package/components/pop-up/AllRowsPopUp.ts +12 -0
  46. package/components/pop-up/PopUpComponent.ts +11 -0
  47. package/components/prefilter-list/PrefilterList.ts +9 -0
  48. package/components/preview/Preview.ts +6 -0
  49. package/components/report-bar/ReportBar.ts +6 -0
  50. package/components/report-tiles/ReportTiles.ts +6 -0
  51. package/components/scheduler/Scheduler.ts +6 -0
  52. package/components/snackbar/SnackBar.ts +12 -0
  53. package/components/splitter/Splitter.ts +6 -0
  54. package/components/tab/BaseTab.ts +5 -0
  55. package/components/tab/DetailTabPage.ts +11 -0
  56. package/components/tab/Tab.ts +10 -0
  57. package/components/task/TaskBar.ts +13 -3
  58. package/components/task/TaskTiles.ts +12 -3
  59. package/components/topbar/TopBar.ts +10 -0
  60. package/components/tree-view/TreeView.ts +9 -0
  61. package/controls/DateControl.ts +47 -9
  62. package/controls/DateControlObjects.ts +15 -0
  63. package/controls/FormComboBox.ts +43 -26
  64. package/controls/FormComboBoxObjects.ts +27 -0
  65. package/controls/GridColumnControl.ts +35 -4
  66. package/controls/GridColumnControlObjects.ts +1 -1
  67. package/controls/InputFieldControl.ts +61 -15
  68. package/controls/InputFieldControlObjects.ts +19 -0
  69. package/controls/LookupDropdown.ts +59 -31
  70. package/controls/LookupDropdownObjects.ts +19 -0
  71. package/dist/Testwise.js +35 -0
  72. package/dist/Testwise.js.map +1 -1
  73. package/dist/artifact-builder/ArtifactManager.d.ts +18 -1
  74. package/dist/artifact-builder/ArtifactManager.js +24 -2
  75. package/dist/artifact-builder/ArtifactManager.js.map +1 -1
  76. package/dist/artifact-builder/ComponentClassModelBuilder.d.ts +22 -0
  77. package/dist/artifact-builder/ComponentClassModelBuilder.js +115 -0
  78. package/dist/artifact-builder/ComponentClassModelBuilder.js.map +1 -0
  79. package/dist/artifact-builder/InterfaceGenerator.d.ts +15 -6
  80. package/dist/artifact-builder/InterfaceGenerator.js +27 -26
  81. package/dist/artifact-builder/InterfaceGenerator.js.map +1 -1
  82. package/dist/artifact-builder/ModelDataBuilder.d.ts +7 -0
  83. package/dist/artifact-builder/ModelDataBuilder.js +13 -5
  84. package/dist/artifact-builder/ModelDataBuilder.js.map +1 -1
  85. package/dist/artifact-builder/ModelDataRefiner.d.ts +18 -1
  86. package/dist/artifact-builder/ModelDataRefiner.js +18 -3
  87. package/dist/artifact-builder/ModelDataRefiner.js.map +1 -1
  88. package/dist/artifact-builder/SchemaGenerator.d.ts +21 -5
  89. package/dist/artifact-builder/SchemaGenerator.js +38 -26
  90. package/dist/artifact-builder/SchemaGenerator.js.map +1 -1
  91. package/dist/artifact-builder/ScreenInterfaceRefiner.d.ts +18 -1
  92. package/dist/artifact-builder/ScreenInterfaceRefiner.js +23 -9
  93. package/dist/artifact-builder/ScreenInterfaceRefiner.js.map +1 -1
  94. package/dist/artifact-builder/SelectorBuilder.d.ts +18 -5
  95. package/dist/artifact-builder/SelectorBuilder.js +29 -14
  96. package/dist/artifact-builder/SelectorBuilder.js.map +1 -1
  97. package/dist/artifact-builder/SubjectClassModelBuilder.d.ts +38 -0
  98. package/dist/artifact-builder/SubjectClassModelBuilder.js +158 -0
  99. package/dist/artifact-builder/SubjectClassModelBuilder.js.map +1 -0
  100. package/dist/artifact-builder/SubjectComponentGenerator.d.ts +25 -14
  101. package/dist/artifact-builder/SubjectComponentGenerator.js +65 -189
  102. package/dist/artifact-builder/SubjectComponentGenerator.js.map +1 -1
  103. package/dist/artifact-builder/SubjectGenerator.d.ts +32 -13
  104. package/dist/artifact-builder/SubjectGenerator.js +81 -165
  105. package/dist/artifact-builder/SubjectGenerator.js.map +1 -1
  106. package/dist/artifact-builder/SubjectRegistration.d.ts +22 -8
  107. package/dist/artifact-builder/SubjectRegistration.js +29 -14
  108. package/dist/artifact-builder/SubjectRegistration.js.map +1 -1
  109. package/dist/artifact-builder/TsFileModel.d.ts +86 -0
  110. package/dist/artifact-builder/TsFileModel.js +2 -0
  111. package/dist/artifact-builder/TsFileModel.js.map +1 -0
  112. package/dist/artifact-builder/TsFileSerializer.d.ts +19 -0
  113. package/dist/artifact-builder/TsFileSerializer.js +225 -0
  114. package/dist/artifact-builder/TsFileSerializer.js.map +1 -0
  115. package/dist/artifact-builder/helpers/DataRetriever.d.ts +22 -3
  116. package/dist/artifact-builder/helpers/DataRetriever.js +56 -26
  117. package/dist/artifact-builder/helpers/DataRetriever.js.map +1 -1
  118. package/dist/artifact-builder/helpers/NamingHandler.d.ts +18 -6
  119. package/dist/artifact-builder/helpers/NamingHandler.js +20 -61
  120. package/dist/artifact-builder/helpers/NamingHandler.js.map +1 -1
  121. package/dist/artifact-builder/helpers/PipelinePaths.d.ts +52 -0
  122. package/dist/artifact-builder/helpers/PipelinePaths.js +99 -0
  123. package/dist/artifact-builder/helpers/PipelinePaths.js.map +1 -0
  124. package/dist/artifact-builder/helpers/Stopwatch.d.ts +10 -0
  125. package/dist/artifact-builder/helpers/Stopwatch.js +10 -0
  126. package/dist/artifact-builder/helpers/Stopwatch.js.map +1 -1
  127. package/dist/artifact-builder/helpers/index.d.ts +1 -0
  128. package/dist/artifact-builder/helpers/index.js +1 -0
  129. package/dist/artifact-builder/helpers/index.js.map +1 -1
  130. package/dist/artifact-builder/index.d.ts +4 -0
  131. package/dist/artifact-builder/index.js +4 -0
  132. package/dist/artifact-builder/index.js.map +1 -1
  133. package/dist/components/BaseComponentObjects.d.ts +17 -0
  134. package/dist/components/BaseComponentObjects.js +17 -0
  135. package/dist/components/BaseComponentObjects.js.map +1 -1
  136. package/dist/components/action-bar/ActionBar.d.ts +21 -24
  137. package/dist/components/action-bar/ActionBar.js +31 -24
  138. package/dist/components/action-bar/ActionBar.js.map +1 -1
  139. package/dist/components/action-bar/ActionBarObjects.d.ts +1 -0
  140. package/dist/components/action-bar/ActionBarObjects.js +1 -0
  141. package/dist/components/action-bar/ActionBarObjects.js.map +1 -1
  142. package/dist/components/action-bar/CustomActionBar.d.ts +6 -0
  143. package/dist/components/action-bar/CustomActionBar.js +6 -0
  144. package/dist/components/action-bar/CustomActionBar.js.map +1 -1
  145. package/dist/components/cardlist/Cardlist.d.ts +6 -0
  146. package/dist/components/cardlist/Cardlist.js +6 -0
  147. package/dist/components/cardlist/Cardlist.js.map +1 -1
  148. package/dist/components/chart/Chart.d.ts +6 -0
  149. package/dist/components/chart/Chart.js +6 -0
  150. package/dist/components/chart/Chart.js.map +1 -1
  151. package/dist/components/combined-filter/CombinedFilter.d.ts +9 -0
  152. package/dist/components/combined-filter/CombinedFilter.js +9 -0
  153. package/dist/components/combined-filter/CombinedFilter.js.map +1 -1
  154. package/dist/components/cube-view-bar/CubeViewBar.d.ts +6 -0
  155. package/dist/components/cube-view-bar/CubeViewBar.js +6 -0
  156. package/dist/components/cube-view-bar/CubeViewBar.js.map +1 -1
  157. package/dist/components/export/ExportComponent.d.ts +12 -0
  158. package/dist/components/export/ExportComponent.js +12 -0
  159. package/dist/components/export/ExportComponent.js.map +1 -1
  160. package/dist/components/filter/ExcelStyleFilterPopup.d.ts +25 -2
  161. package/dist/components/filter/ExcelStyleFilterPopup.js +60 -6
  162. package/dist/components/filter/ExcelStyleFilterPopup.js.map +1 -1
  163. package/dist/components/filter/ExcelStyleFilterPopupObjects.d.ts +8 -1
  164. package/dist/components/filter/ExcelStyleFilterPopupObjects.js +15 -2
  165. package/dist/components/filter/ExcelStyleFilterPopupObjects.js.map +1 -1
  166. package/dist/components/filter/FilterForm.d.ts +10 -0
  167. package/dist/components/filter/FilterForm.js +10 -0
  168. package/dist/components/filter/FilterForm.js.map +1 -1
  169. package/dist/components/filter/FilterPopup.d.ts +22 -4
  170. package/dist/components/filter/FilterPopup.js +17 -9
  171. package/dist/components/filter/FilterPopup.js.map +1 -1
  172. package/dist/components/filter/FilterPopupObjects.d.ts +5 -2
  173. package/dist/components/filter/FilterPopupObjects.js +5 -2
  174. package/dist/components/filter/FilterPopupObjects.js.map +1 -1
  175. package/dist/components/filter/FindForm.d.ts +7 -0
  176. package/dist/components/filter/FindForm.js +7 -0
  177. package/dist/components/filter/FindForm.js.map +1 -1
  178. package/dist/components/filter/ManagePrefilterPopup.d.ts +11 -0
  179. package/dist/components/filter/ManagePrefilterPopup.js +11 -0
  180. package/dist/components/filter/ManagePrefilterPopup.js.map +1 -1
  181. package/dist/components/form/Form.d.ts +16 -0
  182. package/dist/components/form/Form.js +16 -0
  183. package/dist/components/form/Form.js.map +1 -1
  184. package/dist/components/grid/Grid.d.ts +20 -1
  185. package/dist/components/grid/Grid.js +35 -25
  186. package/dist/components/grid/Grid.js.map +1 -1
  187. package/dist/components/grid/GridObjects.d.ts +0 -4
  188. package/dist/components/grid/GridObjects.js +0 -6
  189. package/dist/components/grid/GridObjects.js.map +1 -1
  190. package/dist/components/maps/Maps.d.ts +6 -0
  191. package/dist/components/maps/Maps.js +6 -0
  192. package/dist/components/maps/Maps.js.map +1 -1
  193. package/dist/components/menu/ListBarMenuComponent.d.ts +10 -0
  194. package/dist/components/menu/ListBarMenuComponent.js +10 -0
  195. package/dist/components/menu/ListBarMenuComponent.js.map +1 -1
  196. package/dist/components/pivot-grid/PivotGrid.d.ts +6 -0
  197. package/dist/components/pivot-grid/PivotGrid.js +6 -0
  198. package/dist/components/pivot-grid/PivotGrid.js.map +1 -1
  199. package/dist/components/pivot-grid/PivotGridFieldList.d.ts +7 -0
  200. package/dist/components/pivot-grid/PivotGridFieldList.js +7 -0
  201. package/dist/components/pivot-grid/PivotGridFieldList.js.map +1 -1
  202. package/dist/components/pop-up/AllRowsPopUp.d.ts +12 -0
  203. package/dist/components/pop-up/AllRowsPopUp.js +12 -0
  204. package/dist/components/pop-up/AllRowsPopUp.js.map +1 -1
  205. package/dist/components/pop-up/PopUpComponent.d.ts +11 -0
  206. package/dist/components/pop-up/PopUpComponent.js +11 -0
  207. package/dist/components/pop-up/PopUpComponent.js.map +1 -1
  208. package/dist/components/prefilter-list/PrefilterList.d.ts +9 -0
  209. package/dist/components/prefilter-list/PrefilterList.js +9 -0
  210. package/dist/components/prefilter-list/PrefilterList.js.map +1 -1
  211. package/dist/components/preview/Preview.d.ts +6 -0
  212. package/dist/components/preview/Preview.js +6 -0
  213. package/dist/components/preview/Preview.js.map +1 -1
  214. package/dist/components/report-bar/ReportBar.d.ts +6 -0
  215. package/dist/components/report-bar/ReportBar.js +6 -0
  216. package/dist/components/report-bar/ReportBar.js.map +1 -1
  217. package/dist/components/report-tiles/ReportTiles.d.ts +6 -0
  218. package/dist/components/report-tiles/ReportTiles.js +6 -0
  219. package/dist/components/report-tiles/ReportTiles.js.map +1 -1
  220. package/dist/components/scheduler/Scheduler.d.ts +6 -0
  221. package/dist/components/scheduler/Scheduler.js +6 -0
  222. package/dist/components/scheduler/Scheduler.js.map +1 -1
  223. package/dist/components/snackbar/SnackBar.d.ts +12 -0
  224. package/dist/components/snackbar/SnackBar.js +12 -0
  225. package/dist/components/snackbar/SnackBar.js.map +1 -1
  226. package/dist/components/splitter/Splitter.d.ts +6 -0
  227. package/dist/components/splitter/Splitter.js +6 -0
  228. package/dist/components/splitter/Splitter.js.map +1 -1
  229. package/dist/components/tab/BaseTab.d.ts +5 -0
  230. package/dist/components/tab/BaseTab.js +5 -0
  231. package/dist/components/tab/BaseTab.js.map +1 -1
  232. package/dist/components/tab/DetailTabPage.d.ts +11 -0
  233. package/dist/components/tab/DetailTabPage.js +11 -0
  234. package/dist/components/tab/DetailTabPage.js.map +1 -1
  235. package/dist/components/tab/Tab.d.ts +10 -0
  236. package/dist/components/tab/Tab.js +10 -0
  237. package/dist/components/tab/Tab.js.map +1 -1
  238. package/dist/components/task/TaskBar.d.ts +12 -2
  239. package/dist/components/task/TaskBar.js +13 -3
  240. package/dist/components/task/TaskBar.js.map +1 -1
  241. package/dist/components/task/TaskTiles.d.ts +11 -2
  242. package/dist/components/task/TaskTiles.js +12 -3
  243. package/dist/components/task/TaskTiles.js.map +1 -1
  244. package/dist/components/topbar/TopBar.d.ts +10 -0
  245. package/dist/components/topbar/TopBar.js +10 -0
  246. package/dist/components/topbar/TopBar.js.map +1 -1
  247. package/dist/components/tree-view/TreeView.d.ts +9 -0
  248. package/dist/components/tree-view/TreeView.js +9 -0
  249. package/dist/components/tree-view/TreeView.js.map +1 -1
  250. package/dist/controls/DateControl.d.ts +40 -2
  251. package/dist/controls/DateControl.js +24 -7
  252. package/dist/controls/DateControl.js.map +1 -1
  253. package/dist/controls/DateControlObjects.d.ts +8 -1
  254. package/dist/controls/DateControlObjects.js +8 -1
  255. package/dist/controls/DateControlObjects.js.map +1 -1
  256. package/dist/controls/FormComboBox.d.ts +30 -0
  257. package/dist/controls/FormComboBox.js +19 -16
  258. package/dist/controls/FormComboBox.js.map +1 -1
  259. package/dist/controls/FormComboBoxObjects.d.ts +12 -1
  260. package/dist/controls/FormComboBoxObjects.js +15 -1
  261. package/dist/controls/FormComboBoxObjects.js.map +1 -1
  262. package/dist/controls/GridColumnControl.d.ts +30 -0
  263. package/dist/controls/GridColumnControl.js +13 -4
  264. package/dist/controls/GridColumnControl.js.map +1 -1
  265. package/dist/controls/GridColumnControlObjects.js +1 -1
  266. package/dist/controls/GridColumnControlObjects.js.map +1 -1
  267. package/dist/controls/InputFieldControl.d.ts +50 -3
  268. package/dist/controls/InputFieldControl.js +40 -11
  269. package/dist/controls/InputFieldControl.js.map +1 -1
  270. package/dist/controls/InputFieldControlObjects.d.ts +10 -1
  271. package/dist/controls/InputFieldControlObjects.js +10 -1
  272. package/dist/controls/InputFieldControlObjects.js.map +1 -1
  273. package/dist/controls/LookupDropdown.d.ts +29 -0
  274. package/dist/controls/LookupDropdown.js +36 -25
  275. package/dist/controls/LookupDropdown.js.map +1 -1
  276. package/dist/controls/LookupDropdownObjects.d.ts +10 -0
  277. package/dist/controls/LookupDropdownObjects.js +11 -0
  278. package/dist/controls/LookupDropdownObjects.js.map +1 -0
  279. package/dist/enums/ElementTypes.d.ts +18 -0
  280. package/dist/enums/ElementTypes.js +18 -0
  281. package/dist/enums/ElementTypes.js.map +1 -1
  282. package/dist/enums/ExportFormat.d.ts +8 -0
  283. package/dist/enums/ExportFormat.js +8 -0
  284. package/dist/enums/ExportFormat.js.map +1 -1
  285. package/dist/enums/LogLevel.d.ts +17 -0
  286. package/dist/enums/LogLevel.js +17 -1
  287. package/dist/enums/LogLevel.js.map +1 -1
  288. package/dist/enums/index.d.ts +1 -0
  289. package/dist/enums/index.js +1 -0
  290. package/dist/enums/index.js.map +1 -1
  291. package/dist/helpers/ConfigChecker.d.ts +13 -0
  292. package/dist/helpers/ConfigChecker.js +13 -0
  293. package/dist/helpers/ConfigChecker.js.map +1 -1
  294. package/dist/helpers/Ensure.d.ts +13 -0
  295. package/dist/helpers/Ensure.js +13 -0
  296. package/dist/helpers/Ensure.js.map +1 -1
  297. package/dist/helpers/FlightTracker.d.ts +13 -3
  298. package/dist/helpers/FlightTracker.js +103 -17
  299. package/dist/helpers/FlightTracker.js.map +1 -1
  300. package/dist/helpers/GlobalWaitEventHandler.d.ts +13 -0
  301. package/dist/helpers/GlobalWaitEventHandler.js +13 -0
  302. package/dist/helpers/GlobalWaitEventHandler.js.map +1 -1
  303. package/dist/helpers/LoginHelper.d.ts +35 -1
  304. package/dist/helpers/LoginHelper.js +46 -11
  305. package/dist/helpers/LoginHelper.js.map +1 -1
  306. package/dist/helpers/PathResolver.d.ts +22 -0
  307. package/dist/helpers/PathResolver.js +22 -0
  308. package/dist/helpers/PathResolver.js.map +1 -1
  309. package/dist/helpers/Poll.d.ts +13 -1
  310. package/dist/helpers/Poll.js +12 -0
  311. package/dist/helpers/Poll.js.map +1 -1
  312. package/dist/helpers/RegexHelper.d.ts +15 -0
  313. package/dist/helpers/RegexHelper.js +15 -3
  314. package/dist/helpers/RegexHelper.js.map +1 -1
  315. package/dist/helpers/SubjectNavigator.d.ts +26 -0
  316. package/dist/helpers/SubjectNavigator.js +51 -0
  317. package/dist/helpers/SubjectNavigator.js.map +1 -0
  318. package/dist/helpers/UserSimulationHelper.d.ts +14 -0
  319. package/dist/helpers/UserSimulationHelper.js +14 -0
  320. package/dist/helpers/UserSimulationHelper.js.map +1 -1
  321. package/dist/helpers/index.d.ts +1 -0
  322. package/dist/helpers/index.js +1 -0
  323. package/dist/helpers/index.js.map +1 -1
  324. package/dist/index.d.ts +6 -20
  325. package/dist/index.js +1 -0
  326. package/dist/index.js.map +1 -1
  327. package/dist/interfaces/IComponentObjects.d.ts +12 -0
  328. package/dist/interfaces/IComponentSchemaMeta.d.ts +15 -0
  329. package/dist/interfaces/IComponentSchemaMeta.js +2 -0
  330. package/dist/interfaces/IComponentSchemaMeta.js.map +1 -0
  331. package/dist/interfaces/IProperty.d.ts +13 -0
  332. package/dist/interfaces/IRegisteredSubjects.d.ts +12 -0
  333. package/dist/interfaces/ISeedSubjectDraft.d.ts +16 -0
  334. package/dist/interfaces/ISeedSubjectDraft.js +2 -0
  335. package/dist/interfaces/ISeedSubjectDraft.js.map +1 -0
  336. package/dist/interfaces/ISubject.d.ts +13 -0
  337. package/dist/interfaces/ISubjectDetail.d.ts +11 -0
  338. package/dist/interfaces/ISubjectDetail.js +2 -0
  339. package/dist/interfaces/ISubjectDetail.js.map +1 -0
  340. package/dist/mcp/ArtifactResolver.d.ts +152 -0
  341. package/dist/mcp/ArtifactResolver.js +232 -0
  342. package/dist/mcp/ArtifactResolver.js.map +1 -0
  343. package/dist/mcp/index.d.ts +2 -0
  344. package/dist/mcp/index.js +2 -0
  345. package/dist/mcp/index.js.map +1 -0
  346. package/dist/page-extensions/GlobalComponents.d.ts +30 -0
  347. package/dist/page-extensions/GlobalComponents.js +30 -0
  348. package/dist/page-extensions/GlobalComponents.js.map +1 -1
  349. package/dist/page-extensions/GoToDeepLink.d.ts +9 -0
  350. package/dist/page-extensions/GoToDeepLink.js +9 -0
  351. package/dist/page-extensions/GoToDeepLink.js.map +1 -1
  352. package/dist/page-extensions/LoginFeatures.d.ts +8 -0
  353. package/dist/page-extensions/LoginFeatures.js +8 -0
  354. package/dist/page-extensions/LoginFeatures.js.map +1 -1
  355. package/dist/page-extensions/SubjectRegistry.d.ts +31 -0
  356. package/dist/page-extensions/SubjectRegistry.js +31 -0
  357. package/dist/page-extensions/SubjectRegistry.js.map +1 -1
  358. package/dist/page-extensions/UserSimulation.d.ts +21 -0
  359. package/dist/page-extensions/UserSimulation.js +21 -0
  360. package/dist/page-extensions/UserSimulation.js.map +1 -1
  361. package/dist/page-extensions/WaitEventHandler.d.ts +20 -0
  362. package/dist/page-extensions/WaitEventHandler.js +20 -0
  363. package/dist/page-extensions/WaitEventHandler.js.map +1 -1
  364. package/dist/page-overrides/ClickOverride.d.ts +23 -2
  365. package/dist/page-overrides/ClickOverride.js +34 -50
  366. package/dist/page-overrides/ClickOverride.js.map +1 -1
  367. package/dist/page-overrides/FillOverride.d.ts +23 -0
  368. package/dist/page-overrides/FillOverride.js +46 -66
  369. package/dist/page-overrides/FillOverride.js.map +1 -1
  370. package/dist/services/ConfigBuilder.d.ts +24 -0
  371. package/dist/services/ConfigBuilder.js +24 -0
  372. package/dist/services/ConfigBuilder.js.map +1 -1
  373. package/dist/services/IndiciumApi.service.d.ts +26 -0
  374. package/dist/services/IndiciumApi.service.js +40 -5
  375. package/dist/services/IndiciumApi.service.js.map +1 -1
  376. package/dist/services/Logger.d.ts +13 -0
  377. package/dist/services/Logger.js +39 -0
  378. package/dist/services/Logger.js.map +1 -1
  379. package/dist/types/Components.d.ts +18 -1
  380. package/dist/types/Components.js +0 -1
  381. package/dist/types/Components.js.map +1 -1
  382. package/dist/types/LocatorType.d.ts +5 -0
  383. package/dist/types/LocatorType.js +2 -0
  384. package/dist/types/LocatorType.js.map +1 -0
  385. package/dist/types/PollTypes.d.ts +8 -0
  386. package/dist/types/Test.d.ts +18 -0
  387. package/dist/types/Universal.d.ts +12 -0
  388. package/dist/types/index.d.ts +2 -0
  389. package/dist/types/index.js +2 -0
  390. package/dist/types/index.js.map +1 -1
  391. package/enums/ElementTypes.ts +18 -0
  392. package/enums/ExportFormat.ts +8 -0
  393. package/enums/LogLevel.ts +17 -1
  394. package/enums/index.ts +1 -0
  395. package/helpers/ConfigChecker.ts +13 -0
  396. package/helpers/Ensure.ts +13 -0
  397. package/helpers/FlightTracker.ts +109 -20
  398. package/helpers/GlobalWaitEventHandler.ts +13 -0
  399. package/helpers/LoginHelper.ts +49 -12
  400. package/helpers/PathResolver.ts +22 -0
  401. package/helpers/Poll.ts +13 -1
  402. package/helpers/RegexHelper.ts +15 -3
  403. package/helpers/SubjectNavigator.ts +57 -0
  404. package/helpers/UserSimulationHelper.ts +14 -0
  405. package/helpers/index.ts +1 -0
  406. package/index.ts +1 -0
  407. package/interfaces/IComponentObjects.ts +12 -0
  408. package/interfaces/IComponentSchemaMeta.ts +17 -0
  409. package/interfaces/IProperty.ts +13 -0
  410. package/interfaces/IRegisteredSubjects.ts +12 -0
  411. package/interfaces/ISeedSubjectDraft.ts +17 -0
  412. package/interfaces/ISubject.ts +13 -0
  413. package/interfaces/ISubjectDetail.ts +12 -0
  414. package/mcp/ArtifactResolver.ts +296 -0
  415. package/mcp/index.ts +2 -0
  416. package/package.json +20 -8
  417. package/page-extensions/GlobalComponents.ts +30 -0
  418. package/page-extensions/GoToDeepLink.ts +9 -0
  419. package/page-extensions/LoginFeatures.ts +8 -0
  420. package/page-extensions/SubjectRegistry.ts +32 -0
  421. package/page-extensions/UserSimulation.ts +21 -0
  422. package/page-extensions/WaitEventHandler.ts +20 -0
  423. package/page-overrides/ClickOverride.ts +36 -55
  424. package/page-overrides/FillOverride.ts +59 -73
  425. package/promptCredentials.js +1 -1
  426. package/scripts/Testwise.template.json +1 -1
  427. package/scripts/diagram.js +2267 -0
  428. package/scripts/main.js +84 -63
  429. package/scripts/postinstall.js +55 -42
  430. package/scripts/setup.js +91 -37
  431. package/scripts/sync.js +767 -748
  432. package/services/ConfigBuilder.ts +24 -0
  433. package/services/IndiciumApi.service.ts +44 -6
  434. package/services/Logger.ts +40 -0
  435. package/templates/copilot-instructions.md +130 -0
  436. package/templates/mcp.json +9 -0
  437. package/templates/testwise-test-expert.agent.md +453 -0
  438. package/tests/tsconfig.json +12 -0
  439. package/tsconfig.json +6 -2
  440. package/types/Components.ts +17 -2
  441. package/types/LocatorType.ts +5 -0
  442. package/types/PollTypes.ts +8 -0
  443. package/types/Test.ts +18 -0
  444. package/types/Universal.ts +12 -0
  445. package/types/index.ts +2 -0
  446. package/dist/interfaces/IStoredTestResults.d.ts +0 -5
  447. package/dist/interfaces/IStoredTestResults.js +0 -2
  448. package/dist/interfaces/IStoredTestResults.js.map +0 -1
  449. package/dist/templates/test-artifacts/SubjectPageBase.d.ts +0 -5
  450. package/dist/templates/test-artifacts/SubjectPageBase.js +0 -6
  451. package/dist/templates/test-artifacts/SubjectPageBase.js.map +0 -1
  452. package/dist/templates/test-artifacts/screens/index.d.ts +0 -1
  453. package/dist/templates/test-artifacts/screens/index.js +0 -2
  454. package/dist/templates/test-artifacts/screens/index.js.map +0 -1
  455. package/dist/templates/test-artifacts/subjects/index.d.ts +0 -1
  456. package/dist/templates/test-artifacts/subjects/index.js +0 -2
  457. package/dist/templates/test-artifacts/subjects/index.js.map +0 -1
  458. package/interfaces/IStoredTestResults.ts +0 -6
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@thinkwise/testwise",
3
- "version": "0.2.62",
3
+ "version": "0.2.99",
4
4
  "main": "dist/index.js",
5
5
  "type": "module",
6
6
  "bin": {
@@ -11,25 +11,29 @@
11
11
  "lint": "eslint ./ --cache --ignore-pattern .gitignore",
12
12
  "format:fix": "run-s \"lint --fix\" && biome check --fix --unsafe",
13
13
  "format:check": "run-s \"lint \" && biome check",
14
- "postinstall": "node scripts/main.js postinstall"
14
+ "postinstall": "node scripts/main.js postinstall",
15
+ "test": "vitest run",
16
+ "test:watch": "vitest",
17
+ "test:coverage": "vitest run --coverage",
18
+ "diagram": "node scripts/main.js diagram"
15
19
  },
16
20
  "keywords": [],
17
21
  "author": "",
18
22
  "license": "ISC",
19
23
  "description": "",
20
24
  "dependencies": {
21
- "@thinkwise/backups": "^1.0.16",
22
- "@types/node": "^22.15.29",
25
+ "@thinkwise/backups": "^1.0.20",
23
26
  "axios": "^1.9.0",
24
27
  "chalk": "^5.4.1",
25
28
  "change-case": "^5.4.4",
26
29
  "csv-parse": "^5.6.0",
27
30
  "dotenv": "^17.2.2",
28
- "playwright-bdd": "^8.4.2",
31
+ "playwright-bdd": "^6.6.0",
29
32
  "prettier": "^3.8.1",
30
33
  "prompts": "^2.4.2",
31
34
  "quicktype-core": "^23.2.6",
32
35
  "rimraf": "^6.0.1",
36
+ "ts-morph": "^28.0.0",
33
37
  "ts-node": "^10.9.2",
34
38
  "typescript": "^5.8.3"
35
39
  },
@@ -37,12 +41,15 @@
37
41
  "@playwright/test": "^1.56.1"
38
42
  },
39
43
  "devDependencies": {
40
- "@biomejs/biome": "^2.4.8",
44
+ "@biomejs/biome": "^2.4.12",
41
45
  "@eslint/js": "^9.28.0",
46
+ "@types/node": "^25.6.0",
47
+ "@vitest/coverage-v8": "^4.1.5",
42
48
  "eslint": "^9.39.2",
43
49
  "eslint-plugin-playwright": "^2.2.0",
44
50
  "npm-run-all": "^4.1.5",
45
- "typescript-eslint": "^8.34.0"
51
+ "typescript-eslint": "^8.34.0",
52
+ "vitest": "^4.1.5"
46
53
  },
47
54
  "exports": {
48
55
  ".": {
@@ -52,6 +59,10 @@
52
59
  "./subjects/*": {
53
60
  "types": "./dist/test-artifacts/subjects/*/index.d.ts",
54
61
  "import": "./dist/test-artifacts/subjects/*/index.js"
62
+ },
63
+ "./helpers/SubjectNavigator": {
64
+ "types": "./dist/helpers/SubjectNavigator.d.ts",
65
+ "import": "./dist/helpers/SubjectNavigator.js"
55
66
  }
56
67
  },
57
68
  "files": [
@@ -74,6 +85,7 @@
74
85
  "test-artifacts/",
75
86
  "artifact-builder/",
76
87
  "**/config.json",
77
- "templates/"
88
+ "templates/",
89
+ "mcp/"
78
90
  ]
79
91
  }
@@ -9,6 +9,27 @@ import {
9
9
  } from '../components/index.js';
10
10
  import type { Test } from '../types/Test.js';
11
11
 
12
+ /**
13
+ * Holds pre-constructed instances of the Thinkwise UI components that are
14
+ * present globally across all screens (not tied to any specific subject).
15
+ *
16
+ * Accessed via `page.components` in tests. Available properties:
17
+ * - `popUp` — the main overlay/modal dialog
18
+ * - `export` — the export panel triggered from a grid or list
19
+ * - `snackBar` — the toast notification bar
20
+ * - `topBar` — the application top bar (breadcrumbs, user menu)
21
+ * - `listBarMenu` — the hamburger / list-bar dropdown menu
22
+ * - `managePrefilterPopup` — the "Manage prefilter" popup dialog
23
+ *
24
+ * @example
25
+ * ```ts
26
+ * // Confirm a save popup:
27
+ * await page.components.popUp.confirm();
28
+ *
29
+ * // Check a snackbar message:
30
+ * await expect(page.components.snackBar.message).toHaveText('Saved successfully');
31
+ * ```
32
+ */
12
33
  class GlobalComponents {
13
34
  public popUp: PopUpComponent;
14
35
  public export: ExportComponent;
@@ -36,6 +57,12 @@ declare module '@playwright/test' {
36
57
  export class Components {
37
58
  private _test: Test;
38
59
 
60
+ /**
61
+ * Extends the Playwright `Test` fixture to attach a `GlobalComponents` instance to
62
+ * `page.components` before each test, providing access to shared UI components
63
+ * such as `popUp`, `export`, `snackBar`, `topBar`, `listBarMenu`, and `managePrefilterPopup`.
64
+ * @param test - The Playwright `Test` fixture to extend.
65
+ */
39
66
  constructor(test: Test) {
40
67
  this._test = test.extend({
41
68
  page: async ({ page }, use) => {
@@ -46,6 +73,9 @@ export class Components {
46
73
  });
47
74
  }
48
75
 
76
+ /**
77
+ * Returns the extended `Test` fixture with `page.components` wired up.
78
+ */
49
79
  get test() {
50
80
  return this._test;
51
81
  }
@@ -9,6 +9,12 @@ declare module '@playwright/test' {
9
9
  export class GoToDeepLink {
10
10
  private _test: Test;
11
11
 
12
+ /**
13
+ * Extends the Playwright `Test` fixture to add a `page.goToDeepLink(deepLink)` method.
14
+ * The method preserves the current `#application=` hash segment and appends the given
15
+ * deep link path before navigating to the resulting URL.
16
+ * @param test - The Playwright `Test` fixture to extend.
17
+ */
12
18
  constructor(test: Test) {
13
19
  this._test = test.extend({
14
20
  page: async ({ page }, use) => {
@@ -39,6 +45,9 @@ export class GoToDeepLink {
39
45
  });
40
46
  }
41
47
 
48
+ /**
49
+ * Returns the extended `Test` fixture with `page.goToDeepLink` wired up.
50
+ */
42
51
  get test() {
43
52
  return this._test;
44
53
  }
@@ -15,6 +15,11 @@ export class LoginFeatures {
15
15
  private _loginHelper: LoginHelper | undefined;
16
16
  private _test: Test;
17
17
 
18
+ /**
19
+ * Extends the Playwright `Test` fixture to attach `logIn`, `logInWithCredentials`,
20
+ * `logInWithOptions`, and `logOut` methods to the page, backed by `LoginHelper`.
21
+ * @param test - The Playwright `Test` fixture to extend.
22
+ */
18
23
  constructor(test: Test) {
19
24
  this._test = test.extend({
20
25
  page: async ({ page }, use) => {
@@ -49,6 +54,9 @@ export class LoginFeatures {
49
54
  return this._loginHelper;
50
55
  }
51
56
 
57
+ /**
58
+ * Returns the extended `Test` fixture with login methods wired up on `page`.
59
+ */
52
60
  get test() {
53
61
  return this._test;
54
62
  }
@@ -1,12 +1,44 @@
1
1
  import type { Test } from '../types/Test.js';
2
+
3
+ /**
4
+ * Playwright page-extension that makes every generated subject class available
5
+ * on the `page.subject` proxy during tests.
6
+ *
7
+ * **What it does:** At test startup it reads the registered subject list and
8
+ * wires up a `page.subject` property. Accessing `page.subject.EmployeeMain`
9
+ * returns an instance of the generated `EmployeeMain` class, which exposes
10
+ * typed component properties (`form`, `grid`, `actionBar`, etc.) and a
11
+ * `goTo()` method that navigates to that screen.
12
+ *
13
+ * **Important — do not edit this file directly.** The real implementation is
14
+ * generated from `templates/SubjectRegistry.template.ts` by the
15
+ * `SubjectRegistration` pipeline step. Any changes made here will be
16
+ * overwritten on the next `testwise sync`. Edit the template instead.
17
+ *
18
+ * @example
19
+ * ```ts
20
+ * // In a test:
21
+ * const employee = await page.subject.EmployeeEditable1Main.goTo();
22
+ * await employee.form.firstNameField.fill('Jane');
23
+ * await employee.actionBar.save();
24
+ * ```
25
+ */
2
26
  export class SubjectRegistry {
3
27
  private _test: Test;
4
28
 
29
+ /**
30
+ * Stores the provided `Test` instance. The full implementation of this class is
31
+ * generated from the template in the templates folder — do not edit here directly.
32
+ * @param test - The Playwright `Test` fixture.
33
+ */
5
34
  constructor(test: Test) {
6
35
  // Implementation of this class is in the templates folder, don't edit here
7
36
  this._test = test;
8
37
  }
9
38
 
39
+ /**
40
+ * Returns the stored `Test` fixture.
41
+ */
10
42
  get test() {
11
43
  return this._test;
12
44
  }
@@ -9,10 +9,28 @@ declare module '@playwright/test' {
9
9
  }
10
10
  }
11
11
 
12
+ /**
13
+ * Playwright fixture layer that adds user-simulation methods to the page:
14
+ * `page.simulateUser(username)`, `page.getSimulatedUser()`, and
15
+ * `page.stopSimulation()`.
16
+ *
17
+ * These methods switch the active identity inside the running Thinkwise
18
+ * application without a full logout/login cycle, enabling RBAC tests.
19
+ *
20
+ * @example
21
+ * await page.simulateUser('manager@example.com');
22
+ * // assert manager-only visibility ...
23
+ * await page.stopSimulation();
24
+ */
12
25
  export class UserSimulation {
13
26
  private _userSimulationHelper: UserSimulationHelper | undefined;
14
27
  private _test: Test;
15
28
 
29
+ /**
30
+ * Extends the Playwright `Test` fixture to attach `simulateUser`, `getSimulatedUser`,
31
+ * and `stopSimulation` methods to the page, backed by `UserSimulationHelper`.
32
+ * @param test - The Playwright `Test` fixture to extend.
33
+ */
16
34
  constructor(test: Test) {
17
35
  this._test = test.extend({
18
36
  page: async ({ page }, use) => {
@@ -43,6 +61,9 @@ export class UserSimulation {
43
61
  return this._userSimulationHelper;
44
62
  }
45
63
 
64
+ /**
65
+ * Returns the extended `Test` fixture with user simulation methods wired up on `page`.
66
+ */
46
67
  get test() {
47
68
  return this._test;
48
69
  }
@@ -7,9 +7,26 @@ declare module '@playwright/test' {
7
7
  }
8
8
  }
9
9
 
10
+ /**
11
+ * Playwright fixture layer that attaches a `GlobalWaitEventHandler` instance
12
+ * to `page.waitEventHandler` before each test.
13
+ *
14
+ * Use `page.waitEventHandler` when you need to block test execution until a
15
+ * specific URL pattern has been responded to — for example, waiting for a
16
+ * background data-load endpoint before asserting on results.
17
+ *
18
+ * @example
19
+ * await page.waitEventHandler.waitForUrl('/api/employees/load');
20
+ * await expect(subject.grid.rows()).toHaveCount(10);
21
+ */
10
22
  export class WaitEventHandler {
11
23
  private _test: Test;
12
24
 
25
+ /**
26
+ * Extends the Playwright `Test` fixture to attach a `GlobalWaitEventHandler` instance
27
+ * to `page.waitEventHandler` before each test.
28
+ * @param test - The Playwright `Test` fixture to extend.
29
+ */
13
30
  constructor(test: Test) {
14
31
  this._test = test.extend({
15
32
  page: async ({ page }, use) => {
@@ -20,6 +37,9 @@ export class WaitEventHandler {
20
37
  });
21
38
  }
22
39
 
40
+ /**
41
+ * Returns the extended `Test` fixture with `page.waitEventHandler` wired up.
42
+ */
23
43
  get test() {
24
44
  return this._test;
25
45
  }
@@ -1,80 +1,58 @@
1
- import type { Locator, Page } from '@playwright/test';
1
+ import type { Locator } from '@playwright/test';
2
2
  import { FlightTracker } from '../helpers/FlightTracker.js';
3
3
  import { testwiseConfig } from '../services/ConfigBuilder.js';
4
4
  import type { Test } from '../types/Test.js';
5
5
 
6
6
  const waitForRequestsToComplete =
7
7
  testwiseConfig().get<boolean>('featureSettings.InflightRequests.waitForRequestsToComplete') ?? true;
8
- const continueOnError = testwiseConfig().get<boolean>('featureSettings.InflightRequests.continueOnError') ?? true;
9
8
 
9
+ /**
10
+ * Playwright fixture layer that wraps every Locator `click()` call to wait
11
+ * for in-flight XHR requests to settle before returning control to the test.
12
+ *
13
+ * **Why this exists:** The Thinkwise application fires XHR calls immediately
14
+ * after a click (save, navigation, data load). Without this override a test
15
+ * that clicks a button and then immediately reads a value races against the
16
+ * server response. `ClickOverride` uses `FlightTracker` under the hood to
17
+ * block until all relevant requests finish.
18
+ *
19
+ * **How to disable** (if a specific test must opt out):
20
+ * Set `featureSettings.InflightRequests.waitForRequestsToComplete: false` in
21
+ * `Testwise.json` — but this is rarely needed.
22
+ */
10
23
  export class ClickOverride {
11
24
  private _test: Test;
12
- private _page: Page | null = null;
13
- private flightTracker: FlightTracker = new FlightTracker();
14
25
 
26
+ /**
27
+ * Extends the Playwright `Test` fixture to wrap every locator's `click` method with
28
+ * in-flight XHR tracking via `FlightTracker`, waiting for all relevant requests to
29
+ * settle after each click. Behaviour is configurable via `featureSettings.InflightRequests`.
30
+ * @param test - The Playwright `Test` fixture to extend.
31
+ */
15
32
  constructor(test: Test) {
16
33
  this._test = test.extend({
17
34
  page: async ({ page }, use) => {
18
- this._page = page;
35
+ const flightTracker = new FlightTracker();
19
36
 
20
- const isTrackable = (url: string, resourceType: string) => {
21
- const lowerUrl = url.toLowerCase();
37
+ page.on('request', (request) => {
38
+ flightTracker.handleRequestStarted(request.url(), request.resourceType());
39
+ });
22
40
 
23
- return (
24
- resourceType === 'xhr' &&
25
- !lowerUrl.includes('/detect_change(') &&
26
- !lowerUrl.includes('/set_gui_start_use_log_session') &&
27
- !lowerUrl.includes('download_icon') &&
28
- !lowerUrl.includes('download_list_bar_grp_icon') &&
29
- !lowerUrl.includes('/badge()')
30
- );
31
- };
41
+ page.on('response', (response) => {
42
+ flightTracker.handleRequestFinished(response.request().url());
43
+ });
44
+
45
+ page.on('requestfailed', (request) => {
46
+ flightTracker.handleRequestFailed(request.url());
47
+ });
32
48
 
33
49
  const overrideClickMethod = (locator: Locator): Locator => {
34
50
  const originalClickMethod = locator.click.bind(locator);
35
51
 
36
- page.on('request', (request) => {
37
- if (isTrackable(request.url(), request.resourceType())) {
38
- this.flightTracker.requestsInFlight++;
39
- }
40
- });
41
-
42
- page.on('response', (response) => {
43
- if (isTrackable(response.request().url(), response.request().resourceType())) {
44
- if (this.flightTracker.requestsInFlight > 0) {
45
- this.flightTracker.requestsInFlight--;
46
- }
47
- if (this.flightTracker.requestsInFlight === 0) {
48
- this.flightTracker.eventEmitter.emit('idle');
49
- }
50
- }
51
- });
52
-
53
52
  locator.click = async (options) => {
54
53
  await originalClickMethod(options);
55
54
  if (waitForRequestsToComplete) {
56
- try {
57
- await this.flightTracker.waitToContinue();
58
- } catch (error) {
59
- console.warn('Exception while waiting for inflight requests to finish:', error);
60
- if (this._page) {
61
- const inflightRequests = await this._page.evaluate(() => {
62
- return performance
63
- .getEntriesByType('resource')
64
- .filter((entry) => {
65
- const res = entry as PerformanceResourceTiming;
66
- return (
67
- res.initiatorType === 'xmlhttprequest' &&
68
- !res.name.includes('/detect_change(') &&
69
- !res.name.includes('/set_gui_start_use_log_session')
70
- );
71
- })
72
- .map((entry) => (entry as PerformanceResourceTiming).name);
73
- });
74
- console.debug('Current inflight XHR requests:', inflightRequests);
75
- }
76
- if (!continueOnError) throw error;
77
- }
55
+ await flightTracker.waitToContinue();
78
56
  }
79
57
  return;
80
58
  };
@@ -122,6 +100,9 @@ export class ClickOverride {
122
100
  });
123
101
  }
124
102
 
103
+ /**
104
+ * Returns the extended `Test` fixture with the click override active.
105
+ */
125
106
  get test() {
126
107
  return this._test;
127
108
  }
@@ -7,10 +7,41 @@ const requestWatchlist: string[] = testwiseConfig().get<string[]>('featureSettin
7
7
  const waitForRequestsToComplete =
8
8
  testwiseConfig().get<boolean>('featureSettings.InflightRequests.waitForRequestsToComplete') ?? true;
9
9
 
10
+ const locatorMethods = [
11
+ 'locator',
12
+ 'getByText',
13
+ 'getByTestId',
14
+ 'getByAltText',
15
+ 'getByLabel',
16
+ 'getByRole',
17
+ 'getByPlaceholder',
18
+ 'getByTitle'
19
+ ] as const;
20
+
21
+ /**
22
+ * Playwright fixture layer that wraps every Locator `fill()` call to wait
23
+ * for in-flight XHR requests to settle before returning control to the test.
24
+ *
25
+ * **Why this exists:** After filling a lookup or auto-complete field the
26
+ * Thinkwise application fires XHR calls to search/resolve the typed value.
27
+ * Without this override, subsequent assertions or interactions race against
28
+ * those server responses. `FillOverride` uses `FlightTracker` to block until
29
+ * all relevant requests on the watchlist finish.
30
+ *
31
+ * The `featureSettings.InflightRequests.paths` list in `Testwise.json`
32
+ * controls which API endpoints are watched during fill operations.
33
+ */
10
34
  export class FillOverride {
11
35
  private _test: Test;
12
36
  private flightTracker: FlightTracker = new FlightTracker();
13
37
 
38
+ /**
39
+ * Extends the Playwright `Test` fixture to wrap every locator's `fill` method:
40
+ * waits for watched in-flight requests to settle, fills the element, and — for
41
+ * qualifying form fields — triggers a `/staged` response wait and blurs the element
42
+ * if the value changed. Watchlist and behaviour are configurable via `featureSettings`.
43
+ * @param test - The Playwright `Test` fixture to extend.
44
+ */
14
45
  constructor(test: Test) {
15
46
  this._test = test.extend({
16
47
  page: async ({ page }, use) => {
@@ -35,101 +66,56 @@ export class FillOverride {
35
66
  }
36
67
 
37
68
  const overrideFillMethod = (locator: Locator) => {
38
- const originalFillMethod = locator.fill.bind(locator);
69
+ const originalFill = locator.fill.bind(locator);
39
70
 
40
71
  locator.fill = async (value, options) => {
41
- try {
42
- if (waitForRequestsToComplete) await this.flightTracker.waitToContinue();
43
- } catch (e) {
44
- console.warn('Exception:', e);
45
- this.flightTracker.requestsInFlight = 0;
46
- }
47
-
48
- const currentValue = await locator.inputValue();
49
- const valueIsDifferent = currentValue !== value;
50
-
51
- const formFieldTestIdPrefix: string = 'form-field__';
52
-
53
- const isQualifyingFormField = await locator.evaluate((el, formFieldTestIdPrefix) => {
54
- const elementTestId = el.getAttribute('data-testid');
72
+ if (waitForRequestsToComplete) await this.flightTracker.waitToContinue();
55
73
 
56
- const parentWithFormSectionTestId = el.closest('[data-testid^="form-section__"]');
74
+ const [valueIsDifferent, isQualifyingFormField] = await Promise.all([
75
+ locator.inputValue().then((v) => v !== value),
76
+ locator.evaluate((el) => {
77
+ const testId = el.getAttribute('data-testid');
78
+ return (
79
+ !!testId && testId.includes('form-field__') && el.closest('[data-testid^="form-section__"]') !== null
80
+ );
81
+ })
82
+ ]);
57
83
 
58
- if (elementTestId) {
59
- return elementTestId.includes(formFieldTestIdPrefix) && parentWithFormSectionTestId !== null;
60
- }
61
- return false;
62
- }, formFieldTestIdPrefix);
63
-
64
- if (valueIsDifferent && isQualifyingFormField) {
65
- await page.waitEventHandler.waitForCanContinue();
66
- page.waitEventHandler.waitForResponse('/staged');
67
- }
84
+ await page.waitEventHandler.waitForCanContinue();
68
85
 
69
- await originalFillMethod(value, options);
86
+ await originalFill(value, options);
70
87
 
71
88
  if (isQualifyingFormField) {
89
+ if (valueIsDifferent) page.waitEventHandler.waitForResponse('/staged');
72
90
  await locator.evaluate((el) => {
73
- const ariaExpanded = el.getAttribute('aria-expanded');
74
-
75
- if (!ariaExpanded) el.blur();
91
+ if (!el.getAttribute('aria-expanded')) el.blur();
76
92
  });
77
93
  }
78
94
  };
79
95
 
80
- const originalLocatorMethod = locator.locator.bind(locator);
81
- locator.locator = (...args) => overrideFillMethod(originalLocatorMethod(...args));
82
-
83
- const originalGetByTextMethod = locator.getByText.bind(locator);
84
- locator.getByText = (...args) => overrideFillMethod(originalGetByTextMethod(...args));
85
-
86
- const originalGetByTestIdMethod = locator.getByTestId.bind(locator);
87
- locator.getByTestId = (...args) => overrideFillMethod(originalGetByTestIdMethod(...args));
88
-
89
- const originalGetByAltTextMethod = locator.getByAltText.bind(locator);
90
- locator.getByAltText = (...args) => overrideFillMethod(originalGetByAltTextMethod(...args));
91
-
92
- const originalGetByLabelMethod = locator.getByLabel.bind(locator);
93
- locator.getByLabel = (...args) => overrideFillMethod(originalGetByLabelMethod(...args));
94
-
95
- const originalGetByRoleMethod = locator.getByRole.bind(locator);
96
- locator.getByRole = (...args) => overrideFillMethod(originalGetByRoleMethod(...args));
97
-
98
- const originalGetByPlaceholderMethod = locator.getByPlaceholder.bind(locator);
99
- locator.getByPlaceholder = (...args) => overrideFillMethod(originalGetByPlaceholderMethod(...args));
100
-
101
- const originalGetByTitleMethod = locator.getByTitle.bind(locator);
102
- locator.getByTitle = (...args) => overrideFillMethod(originalGetByTitleMethod(...args));
96
+ for (const method of locatorMethods) {
97
+ const original = (locator[method] as (...args: unknown[]) => Locator).bind(locator);
98
+ (locator as unknown as Record<string, (...args: unknown[]) => Locator>)[method] = (...args: unknown[]) =>
99
+ overrideFillMethod(original(...args));
100
+ }
103
101
 
104
102
  return locator;
105
103
  };
106
104
 
107
- // Override the locator method on the page object
108
- const originalLocator = page.locator.bind(page);
109
- page.locator = (...args) => overrideFillMethod(originalLocator(...args));
110
-
111
- const originalGetByTestId = page.getByTestId.bind(page);
112
- const originalGetByAltText = page.getByAltText.bind(page);
113
- const originalGetByLabel = page.getByLabel.bind(page);
114
- const originalGetByRole = page.getByRole.bind(page);
115
- const originalGetByPlaceholder = page.getByPlaceholder.bind(page);
116
- const originalGetByText = page.getByText.bind(page);
117
- const originalGetByTitle = page.getByTitle.bind(page);
118
-
119
- // Override other top-level methods as before
120
- page.getByTestId = (...args) => overrideFillMethod(originalGetByTestId(...args));
121
- page.getByAltText = (...args) => overrideFillMethod(originalGetByAltText(...args));
122
- page.getByLabel = (...args) => overrideFillMethod(originalGetByLabel(...args));
123
- page.getByRole = (...args) => overrideFillMethod(originalGetByRole(...args));
124
- page.getByPlaceholder = (...args) => overrideFillMethod(originalGetByPlaceholder(...args));
125
- page.getByText = (...args) => overrideFillMethod(originalGetByText(...args));
126
- page.getByTitle = (...args) => overrideFillMethod(originalGetByTitle(...args));
105
+ for (const method of locatorMethods) {
106
+ const original = (page[method] as (...args: unknown[]) => Locator).bind(page);
107
+ (page as unknown as Record<string, (...args: unknown[]) => Locator>)[method] = (...args: unknown[]) =>
108
+ overrideFillMethod(original(...args));
109
+ }
127
110
 
128
111
  await use(page);
129
112
  }
130
113
  });
131
114
  }
132
115
 
116
+ /**
117
+ * Returns the extended `Test` fixture with the fill override active.
118
+ */
133
119
  get test() {
134
120
  return this._test;
135
121
  }
@@ -84,7 +84,7 @@ const questions = [
84
84
  (async () => {
85
85
  const credentialsResponse = await prompts(questions);
86
86
 
87
- if (!credentialsResponse || !credentialsResponse.username || !credentialsResponse.password) {
87
+ if (!credentialsResponse?.username || !credentialsResponse.password) {
88
88
  exitWithError('Username or password was not given');
89
89
  }
90
90
 
@@ -22,7 +22,7 @@
22
22
  "paths" : ["/stage", "/layout()", "/context()"]
23
23
  },
24
24
  "other" : {
25
- "loginTimeout" : 30000
25
+ "loginTimeout" : 60000
26
26
  }
27
27
  }
28
28
  }