@vardot/varbase-e2e 2.0.0

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 (301) hide show
  1. package/AGENTS.md +148 -0
  2. package/CLAUDE.md +544 -0
  3. package/README.md +22 -0
  4. package/bin/generate-reports.js +363 -0
  5. package/bin/init-varbase-e2e.js +330 -0
  6. package/bin/postinstall.js +26 -0
  7. package/cucumber.js +125 -0
  8. package/docs/00-quick-start.md +102 -0
  9. package/docs/01-getting-started.md +102 -0
  10. package/docs/02-bbr-smart-waits.md +77 -0
  11. package/docs/03-selector-registry.md +95 -0
  12. package/docs/04-step-reference.md +801 -0
  13. package/docs/05-web-first-assertions.md +91 -0
  14. package/docs/06-network-and-dialogs.md +83 -0
  15. package/docs/07-auth-state.md +75 -0
  16. package/docs/08-clock-mocking.md +59 -0
  17. package/docs/09-api-testing.md +114 -0
  18. package/docs/10-accessibility.md +167 -0
  19. package/docs/11-debugging.md +129 -0
  20. package/docs/12-ai-agent-guide.md +338 -0
  21. package/docs/13-faq.md +236 -0
  22. package/docs/14-recipes-cookbook.md +255 -0
  23. package/docs/15-tag-conventions.md +76 -0
  24. package/docs/16-ci-cd.md +90 -0
  25. package/docs/README.md +125 -0
  26. package/docs/advanced-screenshots/then-i-save-fullscreen-screenshot.md +36 -0
  27. package/docs/advanced-screenshots/then-i-save-width-x-height-screenshot.md +34 -0
  28. package/docs/advanced-screenshots/when-i-save-screenshot-name-filename.md +45 -0
  29. package/docs/advanced-screenshots.md +52 -0
  30. package/docs/advanced-selectors.md +18 -0
  31. package/docs/api-step-definitions.md +45 -0
  32. package/docs/global-settings.md +267 -0
  33. package/docs/install-varbase-e2e/ddev-varbase-e2e.md +52 -0
  34. package/docs/install-varbase-e2e.md +34 -0
  35. package/docs/overview.md +40 -0
  36. package/docs/step-definitions/given-i-am-anonymous-user.md +67 -0
  37. package/docs/step-definitions/given-i-am-homepage.md +68 -0
  38. package/docs/step-definitions/given-i-am-specific-page.md +72 -0
  39. package/docs/step-definitions/then-i-should-be.md +56 -0
  40. package/docs/step-definitions/then-i-should-see.md +62 -0
  41. package/docs/step-definitions/then-item-checkbox.md +54 -0
  42. package/docs/step-definitions/then-item-link-should-contain-url.md +84 -0
  43. package/docs/step-definitions/then-item-should-contain.md +67 -0
  44. package/docs/step-definitions/then-radio-button-value-should-be-selected.md +68 -0
  45. package/docs/step-definitions/then-response-status-code-should-be-number.md +69 -0
  46. package/docs/step-definitions/then-value-radio-button-selected.md +62 -0
  47. package/docs/step-definitions/when-i-attach-file-file-name-element.md +71 -0
  48. package/docs/step-definitions/when-i-check-checkbox.md +60 -0
  49. package/docs/step-definitions/when-i-click-link.md +51 -0
  50. package/docs/step-definitions/when-i-click-operation-text-row.md +71 -0
  51. package/docs/step-definitions/when-i-fill.md +59 -0
  52. package/docs/step-definitions/when-i-go-homepage.md +60 -0
  53. package/docs/step-definitions/when-i-go-specific-page.md +67 -0
  54. package/docs/step-definitions/when-i-move-backward-one-page.md +49 -0
  55. package/docs/step-definitions/when-i-move-forward-one-page.md +58 -0
  56. package/docs/step-definitions/when-i-press-button.md +58 -0
  57. package/docs/step-definitions/when-i-reload-page.md +51 -0
  58. package/docs/step-definitions/when-i-scroll.md +73 -0
  59. package/docs/step-definitions/when-i-select-option-select-list.md +53 -0
  60. package/docs/step-definitions/when-i-select-radio-button-value.md +62 -0
  61. package/docs/step-definitions/when-i-uncheck-checkbox.md +57 -0
  62. package/docs/step-definitions/when-i-wait-ajax-finish.md +64 -0
  63. package/docs/step-definitions/when-i-wait.md +62 -0
  64. package/docs/step-definitions.md +82 -0
  65. package/docs/steps/README.md +137 -0
  66. package/docs/steps/a11y.md +731 -0
  67. package/docs/steps/action.md +181 -0
  68. package/docs/steps/api.md +679 -0
  69. package/docs/steps/assertion.md +328 -0
  70. package/docs/steps/auth.md +108 -0
  71. package/docs/steps/clock.md +171 -0
  72. package/docs/steps/cookie.md +293 -0
  73. package/docs/steps/debug.md +52 -0
  74. package/docs/steps/dialog.md +226 -0
  75. package/docs/steps/drupal-canvas.md +414 -0
  76. package/docs/steps/drupal-ckeditor.md +118 -0
  77. package/docs/steps/drupal-core.md +688 -0
  78. package/docs/steps/drupal-layout-builder.md +437 -0
  79. package/docs/steps/drupal-media.md +107 -0
  80. package/docs/steps/drupal-moderation.md +81 -0
  81. package/docs/steps/drupal-paragraphs.md +36 -0
  82. package/docs/steps/element.md +455 -0
  83. package/docs/steps/field.md +648 -0
  84. package/docs/steps/file-download.md +235 -0
  85. package/docs/steps/form.md +344 -0
  86. package/docs/steps/iframe.md +248 -0
  87. package/docs/steps/input.md +220 -0
  88. package/docs/steps/javascript.md +111 -0
  89. package/docs/steps/keyboard.md +107 -0
  90. package/docs/steps/link.md +217 -0
  91. package/docs/steps/metatag.md +99 -0
  92. package/docs/steps/modal.md +232 -0
  93. package/docs/steps/navigation.md +275 -0
  94. package/docs/steps/network.md +284 -0
  95. package/docs/steps/path.md +203 -0
  96. package/docs/steps/response.md +102 -0
  97. package/docs/steps/responsive.md +139 -0
  98. package/docs/steps/rest.md +140 -0
  99. package/docs/steps/screenshot.md +211 -0
  100. package/docs/steps/scroll.md +266 -0
  101. package/docs/steps/selectors.md +848 -0
  102. package/docs/steps/storage.md +254 -0
  103. package/docs/steps/table.md +216 -0
  104. package/docs/steps/varbase.md +391 -0
  105. package/docs/steps/video.md +111 -0
  106. package/docs/steps/wait.md +553 -0
  107. package/docs/steps/web-first.md +289 -0
  108. package/docs/steps/xml.md +505 -0
  109. package/docs/steps/yaml.md +951 -0
  110. package/examples/a11y.html +31 -0
  111. package/examples/about-us.html +11 -0
  112. package/examples/account.html +32 -0
  113. package/examples/ajax-wait-examples.html +147 -0
  114. package/examples/contact-us.html +10 -0
  115. package/examples/cookies.html +10 -0
  116. package/examples/date.html +12 -0
  117. package/examples/dynamic-examples.html +498 -0
  118. package/examples/element.html +11 -0
  119. package/examples/example-api.json +28 -0
  120. package/examples/existing-page.html +11 -0
  121. package/examples/field.html +24 -0
  122. package/examples/index.html +37 -0
  123. package/examples/keyboard.html +11 -0
  124. package/examples/links.html +9 -0
  125. package/examples/modal.html +14 -0
  126. package/examples/path.html +3 -0
  127. package/examples/table.html +13 -0
  128. package/examples/test--modal-dialogs.html +252 -0
  129. package/examples/test--then--i-should--not--see-text-in-element.html +48 -0
  130. package/examples/test--then--i-should--see-text-in-element.html +48 -0
  131. package/examples/test--then--i-should--see-text-matching-pattern.html +31 -0
  132. package/examples/test--then--i-should-see-text-in-table-row.html +232 -0
  133. package/examples/test--then--the-checkbox-checked.html +68 -0
  134. package/examples/test--then--the-element-should_not-contain-cssproperty.html +47 -0
  135. package/examples/test--then--the-link-should-contain.html +21 -0
  136. package/examples/test--when--i-additionally-select.html +27 -0
  137. package/examples/test--when--i-attach-file-to-feild.html +50 -0
  138. package/examples/test--when--i-check-uncheck-checkbox.html +47 -0
  139. package/examples/test--when--i-click-link.html +18 -0
  140. package/examples/test--when--i-click-text-in-table-row.html +178 -0
  141. package/examples/test--when--i-fill-in.html +48 -0
  142. package/examples/test--when--i-press-button.html +31 -0
  143. package/examples/test--when--i-reload-page.html +27 -0
  144. package/examples/test--when--i-scroll-functionality.html +177 -0
  145. package/examples/test--when--i-scroll-left-right-functionality.html +149 -0
  146. package/examples/test--when--i-select-option-from-dropdownlist.html +35 -0
  147. package/examples/test--when--i-select-radio-button.html +95 -0
  148. package/examples/test--when-i-wait-max-of-time.html +39 -0
  149. package/examples/test--when-i-wait-page-until-is-loaded.html +47 -0
  150. package/examples/test--when-i-wait-specific-time.html +39 -0
  151. package/examples/test-acceptable-url-path.html +11 -0
  152. package/examples/video-demo.html +43 -0
  153. package/package.json +56 -0
  154. package/playwright.config.ts +39 -0
  155. package/tests/assets/test-document.pdf +14 -0
  156. package/tests/assets/vardot.png +0 -0
  157. package/tests/features/a11y.feature +39 -0
  158. package/tests/features/ajax-wait-examples.feature +24 -0
  159. package/tests/features/api-step-definitions-individual.feature +185 -0
  160. package/tests/features/complete-api-testing-examples.feature +205 -0
  161. package/tests/features/cookie.feature +13 -0
  162. package/tests/features/date.feature +11 -0
  163. package/tests/features/dynamic-content-examples.feature +156 -0
  164. package/tests/features/element.feature +16 -0
  165. package/tests/features/field.feature +25 -0
  166. package/tests/features/keyboard.feature +10 -0
  167. package/tests/features/link.feature +11 -0
  168. package/tests/features/modal-advanced-example.feature +54 -0
  169. package/tests/features/modal-basic-example.feature +42 -0
  170. package/tests/features/modal-error-handling-example.feature +37 -0
  171. package/tests/features/modal.feature +11 -0
  172. package/tests/features/path.feature +16 -0
  173. package/tests/features/response.feature +8 -0
  174. package/tests/features/responsive.feature +10 -0
  175. package/tests/features/table.feature +18 -0
  176. package/tests/features/test--given--i-am-an-anonymous-user.feature +10 -0
  177. package/tests/features/test--given--i-am-on-homepage.feature +16 -0
  178. package/tests/features/test--then--i-save-screenshot.feature +33 -0
  179. package/tests/features/test--then--i-see-locator.feature +320 -0
  180. package/tests/features/test--then--i-should--not--see-text-in-element.feature +13 -0
  181. package/tests/features/test--then--i-should--see-text-in-element-by-attr.feature +10 -0
  182. package/tests/features/test--then--i-should--see-text-in-element.feature +10 -0
  183. package/tests/features/test--then--i-should--see-text-matching-pattern-in-element.feature +13 -0
  184. package/tests/features/test--then--i-should--see-text-matching-pattern.feature +18 -0
  185. package/tests/features/test--then--i-should-be-on-page.feature +10 -0
  186. package/tests/features/test--then--i-should-be-on-the-homepage.feature +10 -0
  187. package/tests/features/test--then--i-should-not-see-an-element-by-attr.feature +8 -0
  188. package/tests/features/test--then--i-should-not-see-an-element.feature +8 -0
  189. package/tests/features/test--then--i-should-see-an-element-by-attr.feature +8 -0
  190. package/tests/features/test--then--i-should-see-an-element.feature +8 -0
  191. package/tests/features/test--then--i-should-see-n-elements.feature +24 -0
  192. package/tests/features/test--then--i-should-see-text-in-table-row.feature +96 -0
  193. package/tests/features/test--then--print-current-url-and-response.feature +21 -0
  194. package/tests/features/test--then--the-checkbox-is-checked.feature +18 -0
  195. package/tests/features/test--then--the-checkbox-should-be-checked.feature +16 -0
  196. package/tests/features/test--then--the-element-should-contain-cssproperty.feature +9 -0
  197. package/tests/features/test--then--the-element-should-not-contain-cssproperty.feature +10 -0
  198. package/tests/features/test--then--the-field-should-contain-value.feature +11 -0
  199. package/tests/features/test--then--the-response-should-contain.feature +11 -0
  200. package/tests/features/test--then--the-response-status-code-should-be.feature +31 -0
  201. package/tests/features/test--then--the-url-should-match.feature +7 -0
  202. package/tests/features/test--then-the-link-should-contain-by-attribute.feature +18 -0
  203. package/tests/features/test--then-the-link-should-contain.feature +7 -0
  204. package/tests/features/test--when--i-additionally-select.feature +30 -0
  205. package/tests/features/test--when--i-attach-file-to-feild.feature +9 -0
  206. package/tests/features/test--when--i-check-checkbox.feature +21 -0
  207. package/tests/features/test--when--i-click-link-by-attribute.feature +21 -0
  208. package/tests/features/test--when--i-click-link.feature +9 -0
  209. package/tests/features/test--when--i-click-text-in-table-row.feature +37 -0
  210. package/tests/features/test--when--i-fill-in-by-attr.feature +31 -0
  211. package/tests/features/test--when--i-fill-in-table-by-attr.feature +19 -0
  212. package/tests/features/test--when--i-fill-in.feature +32 -0
  213. package/tests/features/test--when--i-follow.feature +22 -0
  214. package/tests/features/test--when--i-go-to-homepage.feature +9 -0
  215. package/tests/features/test--when--i-move-forward-backward-one-page.feature +14 -0
  216. package/tests/features/test--when--i-press-button-by-attribute.feature +18 -0
  217. package/tests/features/test--when--i-press-button.feature +13 -0
  218. package/tests/features/test--when--i-reload-page.feature +11 -0
  219. package/tests/features/test--when--i-scroll-left-right.feature +48 -0
  220. package/tests/features/test--when--i-scroll.feature +48 -0
  221. package/tests/features/test--when--i-select-option-from-dropdownlist.feature +21 -0
  222. package/tests/features/test--when--i-select-radio-button.feature +37 -0
  223. package/tests/features/test--when--i-wait-page-is-loaded.feature +8 -0
  224. package/tests/features/test--when--i-wait-time.feature +21 -0
  225. package/tests/features/video.feature +18 -0
  226. package/tests/features/wait.feature +7 -0
  227. package/tests/features/yaml.feature +102 -0
  228. package/tests/selectors/_canonical-keys.json +113 -0
  229. package/tests/selectors/back-end-selectors.json +19 -0
  230. package/tests/selectors/cms-contentful-admin.json +35 -0
  231. package/tests/selectors/cms-craft-admin.json +39 -0
  232. package/tests/selectors/cms-drupal-cms-gin.json +56 -0
  233. package/tests/selectors/cms-drupal-core-claro.json +50 -0
  234. package/tests/selectors/cms-generic-admin.json +34 -0
  235. package/tests/selectors/cms-ghost-admin.json +34 -0
  236. package/tests/selectors/cms-joomla-admin.json +41 -0
  237. package/tests/selectors/cms-magento2-admin.json +32 -0
  238. package/tests/selectors/cms-prestashop-admin.json +38 -0
  239. package/tests/selectors/cms-shopify-admin.json +25 -0
  240. package/tests/selectors/cms-strapi-admin.json +42 -0
  241. package/tests/selectors/cms-typo3-admin.json +41 -0
  242. package/tests/selectors/cms-woocommerce-front.json +50 -0
  243. package/tests/selectors/cms-wordpress-admin.json +31 -0
  244. package/tests/selectors/framework-ant-design.json +80 -0
  245. package/tests/selectors/framework-bootstrap.json +86 -0
  246. package/tests/selectors/framework-bulma.json +74 -0
  247. package/tests/selectors/framework-chakra.json +58 -0
  248. package/tests/selectors/framework-foundation.json +51 -0
  249. package/tests/selectors/framework-material-ui.json +72 -0
  250. package/tests/selectors/framework-shadcn.json +51 -0
  251. package/tests/selectors/framework-tailwind.json +40 -0
  252. package/tests/selectors/framework-vuetify.json +61 -0
  253. package/tests/selectors/front-end-selectors.json +16 -0
  254. package/tests/selectors/homepage-selectors.json +13 -0
  255. package/tests/step-definitions/a11y.steps.js +800 -0
  256. package/tests/step-definitions/action.steps.js +167 -0
  257. package/tests/step-definitions/api.steps.js +732 -0
  258. package/tests/step-definitions/assertion.steps.js +352 -0
  259. package/tests/step-definitions/auth.steps.js +126 -0
  260. package/tests/step-definitions/clock.steps.js +128 -0
  261. package/tests/step-definitions/cookie.steps.js +216 -0
  262. package/tests/step-definitions/debug.steps.js +39 -0
  263. package/tests/step-definitions/dialog.steps.js +193 -0
  264. package/tests/step-definitions/drupal-canvas.steps.js +764 -0
  265. package/tests/step-definitions/drupal-ckeditor.steps.js +108 -0
  266. package/tests/step-definitions/drupal-core.steps.js +665 -0
  267. package/tests/step-definitions/drupal-helpers.js +371 -0
  268. package/tests/step-definitions/drupal-layout-builder.steps.js +466 -0
  269. package/tests/step-definitions/drupal-media.steps.js +99 -0
  270. package/tests/step-definitions/drupal-moderation.steps.js +71 -0
  271. package/tests/step-definitions/drupal-paragraphs.steps.js +50 -0
  272. package/tests/step-definitions/element.steps.js +356 -0
  273. package/tests/step-definitions/field.steps.js +653 -0
  274. package/tests/step-definitions/file-download.steps.js +211 -0
  275. package/tests/step-definitions/form.steps.js +333 -0
  276. package/tests/step-definitions/iframe.steps.js +228 -0
  277. package/tests/step-definitions/input.steps.js +202 -0
  278. package/tests/step-definitions/javascript.steps.js +232 -0
  279. package/tests/step-definitions/keyboard.steps.js +112 -0
  280. package/tests/step-definitions/link.steps.js +142 -0
  281. package/tests/step-definitions/metatag.steps.js +91 -0
  282. package/tests/step-definitions/modal.steps.js +244 -0
  283. package/tests/step-definitions/navigation.steps.js +218 -0
  284. package/tests/step-definitions/network.steps.js +280 -0
  285. package/tests/step-definitions/path.steps.js +141 -0
  286. package/tests/step-definitions/response.steps.js +98 -0
  287. package/tests/step-definitions/responsive.steps.js +125 -0
  288. package/tests/step-definitions/rest.steps.js +111 -0
  289. package/tests/step-definitions/screenshot.steps.js +423 -0
  290. package/tests/step-definitions/scroll.steps.js +189 -0
  291. package/tests/step-definitions/selectors.steps.js +1003 -0
  292. package/tests/step-definitions/storage.steps.js +194 -0
  293. package/tests/step-definitions/table.steps.js +181 -0
  294. package/tests/step-definitions/varbase-e2e.js +897 -0
  295. package/tests/step-definitions/varbase.steps.js +458 -0
  296. package/tests/step-definitions/video.steps.js +178 -0
  297. package/tests/step-definitions/wait.steps.js +400 -0
  298. package/tests/step-definitions/web-first.steps.js +298 -0
  299. package/tests/step-definitions/xml.steps.js +411 -0
  300. package/tests/step-definitions/yaml.steps.js +913 -0
  301. package/tsconfig.json +26 -0
@@ -0,0 +1,688 @@
1
+ # Drupal core steps
2
+
3
+ 27 steps, defined in `tests/step-definitions/drupal-core.steps.js`.
4
+
5
+ Cucumber-js loads every `*.steps.js` in that directory automatically — you never `require()` a step file from a feature.
6
+
7
+ | # | Step |
8
+ | --- | --- |
9
+ | 1 | `And wait` |
10
+ | 2 | `Then the page should load in less than 3 seconds` |
11
+ | 3 | `When I submit by id "edit-submit"` |
12
+ | 4 | `When I open the "Edit" link in the "Test Unpublished Page" row` |
13
+ | 5 | `When I flush all caches` |
14
+ | 6 | `When I logout` |
15
+ | 7 | `Given I am not logged in` |
16
+ | 8 | `When I go to "https://www.drupal.org" website` |
17
+ | 9 | `Then I should see the "Edit" operation for the "Homepage" entity` |
18
+ | 10 | `Then I should see the "copyright" element in the "footer"` |
19
+ | 11 | `Then I should see "Home" in the "ol" element with the "class" attribute set to "breadcrumb"` |
20
+ | 12 | `When I click "Next" in the "button" element with the "class" attribute set to "shepherd-button"` |
21
+ | 13 | `Then I should see "Location property" value in the "edit-name" input element` |
22
+ | 14 | `When I click "Homepage" value in the "edit-items-2-target-id" input element` |
23
+ | 15 | `When I keypress "enter" in "#body" field` |
24
+ | 16 | `Then "Home" should be in the breadcrumb` |
25
+ | 17 | `When I open the top bar page actions menu` |
26
+ | 18 | `When I wait` |
27
+ | 19 | `When I wait for 5s` |
28
+ | 20 | `When I wait for ajax to finish` |
29
+ | 21 | `When I wait max of 30s for the page to be ready and loaded` |
30
+ | 22 | `Then I should see the "Edit" in the "Sample title" row` |
31
+ | 23 | `Then the checkbox labeled "Editor" should be checked` |
32
+ | 24 | `Then the Drupal checkbox "edit-enable" is checked` |
33
+ | 25 | `Then I should see image with the "Flag Earth all earth in space" title text` |
34
+ | 26 | `And I should see image with the "Embed Flag Earth in space" alt text` |
35
+ | 27 | `When I check the first "Test hero slider #1"` |
36
+
37
+ ---
38
+
39
+ ## 1. And wait
40
+
41
+ Smart wait for the current page to reach a quiet edge — the same
42
+ `smartSettle` used by Varbase E2E navigation steps (DOM ready + network
43
+ idle + no pending AJAX/timers). Replaces the bare "And wait" used
44
+ throughout the suite after a navigation or action.
45
+
46
+ **Keyword**: `When`
47
+
48
+ **Pattern**
49
+
50
+ ```js
51
+ /^wait$/
52
+ ```
53
+
54
+ **Examples**
55
+
56
+ ```gherkin
57
+ And wait
58
+ When wait
59
+ Then wait
60
+ Given wait
61
+ But wait
62
+ ```
63
+
64
+ ## 2. Then the page should load in less than 3 seconds
65
+
66
+ Performance budget — assert the current page's full load time (Navigation
67
+ Timing `duration` = navigationStart → loadEventEnd) is under a budget.
68
+ No equivalent ships in Varbase E2E.
69
+
70
+ **Keyword**: `Then`
71
+
72
+ **Pattern**
73
+
74
+ ```js
75
+ /^the page should (?:load|respond) in less than (\d+) (ms|milliseconds?|seconds?)$/
76
+ ```
77
+
78
+ **Examples**
79
+
80
+ ```gherkin
81
+ Then the page should load in less than 3 seconds
82
+ And the page should load in less than 5 seconds
83
+ Then the page should respond in less than 800 ms
84
+ Then the page should load in less than 1500 milliseconds
85
+ And the page should respond in less than 2 seconds
86
+ ```
87
+
88
+ ## 3. When I submit by id "edit-submit"
89
+
90
+ Submit a form by triggering the in-page native click on a button id.
91
+ Gin moves the primary submit into a sticky action bar that overlays the
92
+ original button, so a Playwright click on it times out on actionability.
93
+ Dispatching the click in-page bypasses the overlay.
94
+
95
+ **Keyword**: `When`
96
+
97
+ **Pattern**
98
+
99
+ ```js
100
+ /^(?:I |we )*submit by id "([^"]*)"$/
101
+ ```
102
+
103
+ **Examples**
104
+
105
+ ```gherkin
106
+ When I submit by id "edit-submit"
107
+ And I submit by id "edit-submit"
108
+ When we submit by id "edit-submit"
109
+ And we submit by id "edit-submit"
110
+ Given I submit by id "edit-submit"
111
+ ```
112
+
113
+ ## 4. When I open the "Edit" link in the "Test Unpublished Page" row
114
+
115
+ Open a row action link (e.g. "Edit") by navigating to its href rather than
116
+ clicking it. A Playwright click waits for the heavy node-edit page (CKEditor
117
+ 5 + AI widgets) `load` event which can exceed the step timeout; reading the
118
+ href and `goto` with domcontentloaded avoids that hang.
119
+
120
+ **Keyword**: `When`
121
+
122
+ **Pattern**
123
+
124
+ ```js
125
+ /^(?:I |we )*open the "([^"]*)" link in the "([^"]*)" row$/
126
+ ```
127
+
128
+ **Examples**
129
+
130
+ ```gherkin
131
+ When I open the "Edit" link in the "Test Unpublished Page" row
132
+ And I open the "Delete" link in the "Draft article" row
133
+ When we open the "Edit" link in the "Homepage" row
134
+ And we open the "Translate" link in the "About" row
135
+ Given I open the "Edit" link in the "News" row
136
+ ```
137
+
138
+ ## 5. When I flush all caches
139
+
140
+ Flush all caches from the back end as an administrator.
141
+
142
+ Drives the Drupal core Performance page and clicks its "Clear all caches"
143
+ button, mirroring what an administrator does after changing configuration so
144
+ a following anonymous request renders fresh from the real homepage. Uses the
145
+ core form only (no contrib Tools page), targeting the core submit selector.
146
+
147
+ The click is dispatched in-page: Gin moves the primary submit into a sticky
148
+ action bar that overlays the original button, so a Playwright click can be
149
+ intercepted by the overlay and silently not submit (the cache is then never
150
+ cleared). A native in-page click submits the form regardless.
151
+
152
+ **Keyword**: `When`
153
+
154
+ **Pattern**
155
+
156
+ ```js
157
+ /^(?:I |we )*flush all caches$/
158
+ ```
159
+
160
+ **Examples**
161
+
162
+ ```gherkin
163
+ When I flush all caches
164
+ And I flush all caches
165
+ When we flush all caches
166
+ Given I flush all caches
167
+ And we flush all caches
168
+ ```
169
+
170
+ ## 6. When I logout
171
+
172
+ Log out of the current session.
173
+
174
+ Ports VarbaseContext::iLogout (`@When /^I logout$/`). Varbase E2E has no
175
+ logout step. Visits Drupal's /user/logout confirm route; on Drupal 11 the
176
+ logout form needs a confirm submit, so it submits the form if present.
177
+
178
+ **Keyword**: `When`
179
+
180
+ **Pattern**
181
+
182
+ ```js
183
+ /^(?:I |we )*logout$/
184
+ ```
185
+
186
+ **Examples**
187
+
188
+ ```gherkin
189
+ When I logout
190
+ And I logout
191
+ When we logout
192
+ Given I logout
193
+ And we logout
194
+ ```
195
+
196
+ ## 7. Given I am not logged in
197
+
198
+ Assert the current visitor is not authenticated (anonymous).
199
+
200
+ Ports the Behat/DrupalExtension `Given I am not logged in`. Varbase E2E ships
201
+ `Given I am an anonymous user` (clears storage + reloads); "not logged in"
202
+ additionally verifies there is no active Drupal session by visiting /user
203
+ and confirming it is the login form, not the user profile.
204
+
205
+ **Keyword**: `Given`
206
+
207
+ **Pattern**
208
+
209
+ ```js
210
+ /^(?:I am |we are )?not logged in$/
211
+ ```
212
+
213
+ **Examples**
214
+
215
+ ```gherkin
216
+ Given I am not logged in
217
+ And I am not logged in
218
+ Given we are not logged in
219
+ But I am not logged in
220
+ Given I am not logged in
221
+ ```
222
+
223
+ ## 8. When I go to "https://www.drupal.org" website
224
+
225
+ Navigate directly to an external website (absolute URL).
226
+
227
+ Ports VarbaseContext::iGoToWebsite (`@When /^I go to "..." website$/`). The
228
+ Varbase E2E `I go to "..."` step joins the path onto launchUrl; this variant
229
+ visits the given absolute URL verbatim (used for external OAuth / social
230
+ providers, e.g. LinkedIn, Facebook).
231
+
232
+ **Keyword**: `When`
233
+
234
+ **Pattern**
235
+
236
+ ```js
237
+ /^(?:I |we )*go to "([^"]*)" website$/
238
+ ```
239
+
240
+ **Examples**
241
+
242
+ ```gherkin
243
+ When I go to "https://www.drupal.org" website
244
+ And I go to "https://www.linkedin.com" website
245
+ When we go to "https://accounts.google.com" website
246
+ Given I go to "https://www.facebook.com" website
247
+ And I go to "https://x.com" website
248
+ ```
249
+
250
+ ## 9. Then I should see the "Edit" operation for the "Homepage" entity
251
+
252
+ Assert an entity row exposes (or does not expose) an operation link.
253
+
254
+ Ports VarbaseContext::iShouldSeetheOperationForTheEntity /
255
+ iShouldNotSeetheOperationForTheEntity. Finds the table row containing the
256
+ entity text and checks its operations cell for the named link. The trailing
257
+ noun (entity/content/media/file/term/user) is cosmetic.
258
+
259
+ **Keyword**: `Then`
260
+
261
+ **Pattern**
262
+
263
+ ```js
264
+ /^(?:I |we )*(?:should )?(not )?see (?:the )?"([^"]*)" operation for the "([^"]*)"(?: (?:entity|content|media|file|term|user))?$/
265
+ ```
266
+
267
+ **Examples**
268
+
269
+ ```gherkin
270
+ Then I should see the "Edit" operation for the "Homepage" entity
271
+ And I should not see the "Delete" operation for the "Blog" content
272
+ Then should see "Clone" operation for the "Homepage" entity
273
+ And I should not see the "View API" operation for the "About" media
274
+ Then I should see the "Translate" operation for the "News" term
275
+ ```
276
+
277
+ ## 10. Then I should see the "copyright" element in the "footer"
278
+
279
+ Assert a named (or css) element exists / does not exist within another named
280
+ (or css) container.
281
+
282
+ Ports the suite's `I should see the "X" element in the "Y"` /
283
+ `I should not see the "X" element in the "Y"`. Resolves both the child and
284
+ the container against the selector registry (this.__selectorsCss), falling
285
+ back to raw CSS.
286
+
287
+ **Keyword**: `Then`
288
+
289
+ **Pattern**
290
+
291
+ ```js
292
+ /^(?:I |we )*should( not)? see the "([^"]*)" element in the "([^"]*)"$/
293
+ ```
294
+
295
+ **Examples**
296
+
297
+ ```gherkin
298
+ Then I should see the "copyright" element in the "footer"
299
+ And I should not see the "edit link" element in the "sidebar"
300
+ Then should see the "logo" element in the "header bar"
301
+ And I should see the "search input" element in the "main nav"
302
+ Then I should not see the "banner" element in the "main content"
303
+ ```
304
+
305
+ ## 11. Then I should see "Home" in the "ol" element with the "class" attribute set to "breadcrumb"
306
+
307
+ Assert text is (or is not) present in an element matched by tag + attribute.
308
+
309
+ Ports VarbaseContext::iShouldSeeTextInTheHtmlTagElement /
310
+ iShouldNotSeeTextInTheHtmlTagElement.
311
+
312
+ **Keyword**: `Then`
313
+
314
+ **Pattern**
315
+
316
+ ```js
317
+ /^(?:I |we )*should( not)? see "([^"]*)" in the "([^"]*)" element with the "([^"]*)" attribute set to "([^"]*)"$/
318
+ ```
319
+
320
+ **Examples**
321
+
322
+ ```gherkin
323
+ Then I should see "Home" in the "ol" element with the "class" attribute set to "breadcrumb"
324
+ And I should not see "Error" in the "div" element with the "id" attribute set to "right-panel"
325
+ Then I should see "Draft" in the "span" element with the "class" attribute set to "state"
326
+ And I should see "Published" in the "td" element with the "class" attribute set to "status"
327
+ Then I should not see "Trash" in the "ul" element with the "class" attribute set to "menu"
328
+ ```
329
+
330
+ ## 12. When I click "Next" in the "button" element with the "class" attribute set to "shepherd-button"
331
+
332
+ Click the element of a given HTML tag whose <attr> attribute contains <value>
333
+ and whose visible text matches <text>. Covers the Shepherd tour "Next"
334
+ button (tag=button, class "... shepherd-button"), the moderation-sidebar
335
+ Translate link (tag=a, class "moderation-sidebar-link ...") and the Linkit
336
+ autocomplete suggestion (tag=ul, class "ui-autocomplete").
337
+
338
+ **Keyword**: `When`
339
+
340
+ **Pattern**
341
+
342
+ ```js
343
+ /^(?:I |we )*click "([^"]*)" in the "([^"]*)" element with the "([^"]*)" attribute set to "([^"]*)"$/
344
+ ```
345
+
346
+ **Examples**
347
+
348
+ ```gherkin
349
+ When I click "Next" in the "button" element with the "class" attribute set to "shepherd-button"
350
+ When I click "Translate" in the "a" element with the "class" attribute set to "moderation-sidebar-link button use-ajax"
351
+ ```
352
+
353
+ ## 13. Then I should see "Location property" value in the "edit-name" input element
354
+
355
+ Assert an input element (matched by data-drupal-selector) has a value.
356
+
357
+ Ports VarbaseContext::iShouldSeeValueInTheInputElement.
358
+
359
+ **Keyword**: `Then`
360
+
361
+ **Pattern**
362
+
363
+ ```js
364
+ /^(?:I |we )*should see "([^"]*)" value in the "([^"]*)" input element$/
365
+ ```
366
+
367
+ **Examples**
368
+
369
+ ```gherkin
370
+ Then I should see "Location property" value in the "edit-name" input element
371
+ And I should see "42" value in the "edit-items-2-target-id" input element
372
+ Then I should see "Homepage" value in the "edit-title-0-value" input element
373
+ And I should see "en" value in the "edit-langcode-0-value" input element
374
+ Then I should see "Draft" value in the "edit-moderation-state-0-state" input element
375
+ ```
376
+
377
+ ## 14. When I click "Homepage" value in the "edit-items-2-target-id" input element
378
+
379
+ Click an input element (matched by data-drupal-selector) whose value matches.
380
+
381
+ Ports VarbaseContext::iClickValueInTheInputElement.
382
+
383
+ **Keyword**: `When`
384
+
385
+ **Pattern**
386
+
387
+ ```js
388
+ /^(?:I |we )*click "([^"]*)" value in the "([^"]*)" input element$/
389
+ ```
390
+
391
+ **Examples**
392
+
393
+ ```gherkin
394
+ When I click "Homepage" value in the "edit-items-2-target-id" input element
395
+ And I click "Location property" value in the "edit-name" input element
396
+ When we click "News" value in the "edit-title" input element
397
+ And I click "Blog" value in the "edit-target-id" input element
398
+ When I click "About" value in the "edit-name" input element
399
+ ```
400
+
401
+ ## 15. When I keypress "enter" in "#body" field
402
+
403
+ Press a keyboard key while focused in a field (label / name / id / css).
404
+
405
+ Ports VarbaseContext::iPressKeyboardKeyInField (`@When I keypress :char in
406
+ :field field`). Maps the legacy key words to Playwright key identifiers.
407
+
408
+ **Keyword**: `When`
409
+
410
+ **Pattern**
411
+
412
+ ```js
413
+ /^(?:I |we )*keypress "([^"]*)" in "([^"]*)" field$/
414
+ ```
415
+
416
+ **Examples**
417
+
418
+ ```gherkin
419
+ When I keypress "enter" in "#body" field
420
+ And I keypress "tab" in "#first-name" field
421
+ When I keypress " " in "#search" field
422
+ And I keypress "escape" in "Title" field
423
+ When we keypress "down" in "#country" field
424
+ ```
425
+
426
+ ## 16. Then "Home" should be in the breadcrumb
427
+
428
+ Assert text appears in the breadcrumb trail.
429
+
430
+ Ports VarbaseContext::shouldBeInTheBreadcrumb (`@Then :text should be in the
431
+ breadcrumb`).
432
+
433
+ **Keyword**: `Then`
434
+
435
+ **Pattern**
436
+
437
+ ```js
438
+ /^"([^"]*)" should be in the breadcrumb$/
439
+ ```
440
+
441
+ **Examples**
442
+
443
+ ```gherkin
444
+ Then "Home" should be in the breadcrumb
445
+ And "Blog" should be in the breadcrumb
446
+ Then "About Varbase" should be in the breadcrumb
447
+ And "News" should be in the breadcrumb
448
+ Then "Contact Us" should be in the breadcrumb
449
+ ```
450
+
451
+ ## 17. When I open the top bar page actions menu
452
+
453
+ Open the top-bar page actions (the "more actions" dots) in the Gin/Navigation
454
+ top bar.
455
+
456
+ Ports VarbaseContext::iOpenTopBarPageActions.
457
+
458
+ **Keyword**: `When`
459
+
460
+ **Pattern**
461
+
462
+ ```js
463
+ /^(?:I |we )*(?:open (?:the )?top bar page actions(?: menu)?|hit (?:the )?more actions(?: button)?)$/
464
+ ```
465
+
466
+ **Examples**
467
+
468
+ ```gherkin
469
+ When I open the top bar page actions menu
470
+ And I open top bar page actions
471
+ When we open the top bar page actions
472
+ And I hit the more actions button
473
+ When I hit more actions
474
+ ```
475
+
476
+ ## 18. When I wait
477
+
478
+ Settle the page with the configured wait budget — DOM ready, network idle, no pending AJAX or timers.
479
+
480
+ **Keyword**: `When`
481
+
482
+ **Pattern**
483
+
484
+ ```js
485
+ /^(?:I |we )+wait$/
486
+ ```
487
+
488
+ **Examples**
489
+
490
+ ```gherkin
491
+ When I wait
492
+ And I wait
493
+ When we wait
494
+ And we wait
495
+ Given I wait
496
+ ```
497
+
498
+ ## 19. When I wait for 5s
499
+
500
+ Settle the page with an explicit budget in seconds instead of the configured default.
501
+
502
+ **Keyword**: `When`
503
+
504
+ **Pattern**
505
+
506
+ ```js
507
+ /^(?:I |we )*wait for (\d+)s$/
508
+ ```
509
+
510
+ **Examples**
511
+
512
+ ```gherkin
513
+ When I wait for 5s
514
+ And I wait for 2s
515
+ When we wait for 10s
516
+ And wait for 1s
517
+ Given I wait for 3s
518
+ ```
519
+
520
+ ## 20. When I wait for ajax to finish
521
+
522
+ Wait until every in-flight AJAX request has settled and the DOM has stopped mutating.
523
+
524
+ **Keyword**: `When`
525
+
526
+ **Pattern**
527
+
528
+ ```js
529
+ /^(?:I |we )*wait for ajax to finish$/
530
+ ```
531
+
532
+ **Examples**
533
+
534
+ ```gherkin
535
+ When I wait for ajax to finish
536
+ And I wait for ajax to finish
537
+ When we wait for ajax to finish
538
+ And wait for ajax to finish
539
+ Given I wait for ajax to finish
540
+ ```
541
+
542
+ ## 21. When I wait max of 30s for the page to be ready and loaded
543
+
544
+ Wait up to the given number of seconds for the page to be ready and fully loaded.
545
+
546
+ **Keyword**: `When`
547
+
548
+ **Pattern**
549
+
550
+ ```js
551
+ /^(?:I |we )*wait max of (\d+)s for the page to be ready and loaded$/
552
+ ```
553
+
554
+ **Examples**
555
+
556
+ ```gherkin
557
+ When I wait max of 30s for the page to be ready and loaded
558
+ And I wait max of 10s for the page to be ready and loaded
559
+ When we wait max of 60s for the page to be ready and loaded
560
+ And wait max of 15s for the page to be ready and loaded
561
+ Given I wait max of 45s for the page to be ready and loaded
562
+ ```
563
+
564
+ ## 22. Then I should see the "Edit" in the "Sample title" row
565
+
566
+ Assert an operation link or text is present in the administration listing row whose text matches.
567
+
568
+ **Keyword**: `Then`
569
+
570
+ **Pattern**
571
+
572
+ ```js
573
+ /^(?:I |we )*should( not)? see the "([^"]*)" in(?: the)? "([^"]*)" row$/
574
+ ```
575
+
576
+ **Examples**
577
+
578
+ ```gherkin
579
+ Then I should see the "Edit" in the "Sample title" row
580
+ And I should see the "Delete" in "Sample title" row
581
+ Then I should not see the "Delete" in the "Locked page" row
582
+ And we should see the "Published" in the "Sample title" row
583
+ Then I should not see the "Translate" in "Sample title" row
584
+ ```
585
+
586
+ ## 23. Then the checkbox labeled "Editor" should be checked
587
+
588
+ Assert a checkbox is checked / unchecked, found by its visible label text
589
+ (alternate phrasing).
590
+
591
+ **Keyword**: `Then`
592
+
593
+ **Pattern**
594
+
595
+ ```js
596
+ /^the checkbox labeled "([^"]*)" should be (checked|unchecked)$/
597
+ ```
598
+
599
+ **Examples**
600
+
601
+ ```gherkin
602
+ Then the checkbox labeled "Editor" should be checked
603
+ And the checkbox labeled "Site Admin" should be unchecked
604
+ Then the checkbox labeled "Published" should be checked
605
+ And the checkbox labeled "Promoted to front page" should be unchecked
606
+ Then the checkbox labeled "Sticky at top of lists" should be unchecked
607
+ ```
608
+
609
+ ## 24. Then the Drupal checkbox "edit-enable" is checked
610
+
611
+ Assert a checkbox is checked / unchecked, resolved by a machine handle
612
+ (DOM id, data-drupal-selector, or name attribute).
613
+
614
+ **Keyword**: `Then`
615
+
616
+ **Pattern**
617
+
618
+ ```js
619
+ /^the Drupal checkbox "([^"]*)" is (checked|unchecked)$/
620
+ ```
621
+
622
+ **Examples**
623
+
624
+ ```gherkin
625
+ Then the Drupal checkbox "edit-enable" is checked
626
+ And the Drupal checkbox "entity_json" is checked
627
+ Then the Drupal checkbox "edit-status-value" is checked
628
+ And the Drupal checkbox "edit-promote-value" is unchecked
629
+ Then the Drupal checkbox "edit-sticky-value" is unchecked
630
+ ```
631
+
632
+ ## 25. Then I should see image with the "Flag Earth all earth in space" title text
633
+
634
+ Assert an <img> whose title attribute contains the given text exists.
635
+
636
+ **Keyword**: `Then`
637
+
638
+ **Pattern**
639
+
640
+ ```js
641
+ /^(?:I |we )*should see image with the "([^"]*)" title text$/
642
+ ```
643
+
644
+ **Examples**
645
+
646
+ ```gherkin
647
+ Then I should see image with the "Flag Earth all earth in space" title text
648
+ ```
649
+
650
+ ## 26. And I should see image with the "Embed Flag Earth in space" alt text
651
+
652
+ Assert an <img> whose alt attribute contains the given text exists.
653
+
654
+ **Keyword**: `Then`
655
+
656
+ **Pattern**
657
+
658
+ ```js
659
+ /^(?:I |we )*should see image with the "([^"]*)" alt text$/
660
+ ```
661
+
662
+ **Examples**
663
+
664
+ ```gherkin
665
+ And I should see image with the "Embed Flag Earth in space" alt text
666
+ ```
667
+
668
+ ## 27. When I check the first "Test hero slider #1"
669
+
670
+ Check the first checkbox matching a label, tolerating duplicates. A retried
671
+ scenario (cucumber `retry: 1`) can leave two identically titled nodes, so
672
+ two checkboxes carry the same label (e.g. the entityqueue widget) and the
673
+ built-in "I check" strict-fails; the duplicates are equivalent - pick the
674
+ first.
675
+
676
+ **Keyword**: `When`
677
+
678
+ **Pattern**
679
+
680
+ ```js
681
+ /^(?:I |we )*check the first "([^"]*)"$/
682
+ ```
683
+
684
+ **Examples**
685
+
686
+ ```gherkin
687
+ When I check the first "Test hero slider #1"
688
+ ```