@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.
- package/AGENTS.md +148 -0
- package/CLAUDE.md +544 -0
- package/README.md +22 -0
- package/bin/generate-reports.js +363 -0
- package/bin/init-varbase-e2e.js +330 -0
- package/bin/postinstall.js +26 -0
- package/cucumber.js +125 -0
- package/docs/00-quick-start.md +102 -0
- package/docs/01-getting-started.md +102 -0
- package/docs/02-bbr-smart-waits.md +77 -0
- package/docs/03-selector-registry.md +95 -0
- package/docs/04-step-reference.md +801 -0
- package/docs/05-web-first-assertions.md +91 -0
- package/docs/06-network-and-dialogs.md +83 -0
- package/docs/07-auth-state.md +75 -0
- package/docs/08-clock-mocking.md +59 -0
- package/docs/09-api-testing.md +114 -0
- package/docs/10-accessibility.md +167 -0
- package/docs/11-debugging.md +129 -0
- package/docs/12-ai-agent-guide.md +338 -0
- package/docs/13-faq.md +236 -0
- package/docs/14-recipes-cookbook.md +255 -0
- package/docs/15-tag-conventions.md +76 -0
- package/docs/16-ci-cd.md +90 -0
- package/docs/README.md +125 -0
- package/docs/advanced-screenshots/then-i-save-fullscreen-screenshot.md +36 -0
- package/docs/advanced-screenshots/then-i-save-width-x-height-screenshot.md +34 -0
- package/docs/advanced-screenshots/when-i-save-screenshot-name-filename.md +45 -0
- package/docs/advanced-screenshots.md +52 -0
- package/docs/advanced-selectors.md +18 -0
- package/docs/api-step-definitions.md +45 -0
- package/docs/global-settings.md +267 -0
- package/docs/install-varbase-e2e/ddev-varbase-e2e.md +52 -0
- package/docs/install-varbase-e2e.md +34 -0
- package/docs/overview.md +40 -0
- package/docs/step-definitions/given-i-am-anonymous-user.md +67 -0
- package/docs/step-definitions/given-i-am-homepage.md +68 -0
- package/docs/step-definitions/given-i-am-specific-page.md +72 -0
- package/docs/step-definitions/then-i-should-be.md +56 -0
- package/docs/step-definitions/then-i-should-see.md +62 -0
- package/docs/step-definitions/then-item-checkbox.md +54 -0
- package/docs/step-definitions/then-item-link-should-contain-url.md +84 -0
- package/docs/step-definitions/then-item-should-contain.md +67 -0
- package/docs/step-definitions/then-radio-button-value-should-be-selected.md +68 -0
- package/docs/step-definitions/then-response-status-code-should-be-number.md +69 -0
- package/docs/step-definitions/then-value-radio-button-selected.md +62 -0
- package/docs/step-definitions/when-i-attach-file-file-name-element.md +71 -0
- package/docs/step-definitions/when-i-check-checkbox.md +60 -0
- package/docs/step-definitions/when-i-click-link.md +51 -0
- package/docs/step-definitions/when-i-click-operation-text-row.md +71 -0
- package/docs/step-definitions/when-i-fill.md +59 -0
- package/docs/step-definitions/when-i-go-homepage.md +60 -0
- package/docs/step-definitions/when-i-go-specific-page.md +67 -0
- package/docs/step-definitions/when-i-move-backward-one-page.md +49 -0
- package/docs/step-definitions/when-i-move-forward-one-page.md +58 -0
- package/docs/step-definitions/when-i-press-button.md +58 -0
- package/docs/step-definitions/when-i-reload-page.md +51 -0
- package/docs/step-definitions/when-i-scroll.md +73 -0
- package/docs/step-definitions/when-i-select-option-select-list.md +53 -0
- package/docs/step-definitions/when-i-select-radio-button-value.md +62 -0
- package/docs/step-definitions/when-i-uncheck-checkbox.md +57 -0
- package/docs/step-definitions/when-i-wait-ajax-finish.md +64 -0
- package/docs/step-definitions/when-i-wait.md +62 -0
- package/docs/step-definitions.md +82 -0
- package/docs/steps/README.md +137 -0
- package/docs/steps/a11y.md +731 -0
- package/docs/steps/action.md +181 -0
- package/docs/steps/api.md +679 -0
- package/docs/steps/assertion.md +328 -0
- package/docs/steps/auth.md +108 -0
- package/docs/steps/clock.md +171 -0
- package/docs/steps/cookie.md +293 -0
- package/docs/steps/debug.md +52 -0
- package/docs/steps/dialog.md +226 -0
- package/docs/steps/drupal-canvas.md +414 -0
- package/docs/steps/drupal-ckeditor.md +118 -0
- package/docs/steps/drupal-core.md +688 -0
- package/docs/steps/drupal-layout-builder.md +437 -0
- package/docs/steps/drupal-media.md +107 -0
- package/docs/steps/drupal-moderation.md +81 -0
- package/docs/steps/drupal-paragraphs.md +36 -0
- package/docs/steps/element.md +455 -0
- package/docs/steps/field.md +648 -0
- package/docs/steps/file-download.md +235 -0
- package/docs/steps/form.md +344 -0
- package/docs/steps/iframe.md +248 -0
- package/docs/steps/input.md +220 -0
- package/docs/steps/javascript.md +111 -0
- package/docs/steps/keyboard.md +107 -0
- package/docs/steps/link.md +217 -0
- package/docs/steps/metatag.md +99 -0
- package/docs/steps/modal.md +232 -0
- package/docs/steps/navigation.md +275 -0
- package/docs/steps/network.md +284 -0
- package/docs/steps/path.md +203 -0
- package/docs/steps/response.md +102 -0
- package/docs/steps/responsive.md +139 -0
- package/docs/steps/rest.md +140 -0
- package/docs/steps/screenshot.md +211 -0
- package/docs/steps/scroll.md +266 -0
- package/docs/steps/selectors.md +848 -0
- package/docs/steps/storage.md +254 -0
- package/docs/steps/table.md +216 -0
- package/docs/steps/varbase.md +391 -0
- package/docs/steps/video.md +111 -0
- package/docs/steps/wait.md +553 -0
- package/docs/steps/web-first.md +289 -0
- package/docs/steps/xml.md +505 -0
- package/docs/steps/yaml.md +951 -0
- package/examples/a11y.html +31 -0
- package/examples/about-us.html +11 -0
- package/examples/account.html +32 -0
- package/examples/ajax-wait-examples.html +147 -0
- package/examples/contact-us.html +10 -0
- package/examples/cookies.html +10 -0
- package/examples/date.html +12 -0
- package/examples/dynamic-examples.html +498 -0
- package/examples/element.html +11 -0
- package/examples/example-api.json +28 -0
- package/examples/existing-page.html +11 -0
- package/examples/field.html +24 -0
- package/examples/index.html +37 -0
- package/examples/keyboard.html +11 -0
- package/examples/links.html +9 -0
- package/examples/modal.html +14 -0
- package/examples/path.html +3 -0
- package/examples/table.html +13 -0
- package/examples/test--modal-dialogs.html +252 -0
- package/examples/test--then--i-should--not--see-text-in-element.html +48 -0
- package/examples/test--then--i-should--see-text-in-element.html +48 -0
- package/examples/test--then--i-should--see-text-matching-pattern.html +31 -0
- package/examples/test--then--i-should-see-text-in-table-row.html +232 -0
- package/examples/test--then--the-checkbox-checked.html +68 -0
- package/examples/test--then--the-element-should_not-contain-cssproperty.html +47 -0
- package/examples/test--then--the-link-should-contain.html +21 -0
- package/examples/test--when--i-additionally-select.html +27 -0
- package/examples/test--when--i-attach-file-to-feild.html +50 -0
- package/examples/test--when--i-check-uncheck-checkbox.html +47 -0
- package/examples/test--when--i-click-link.html +18 -0
- package/examples/test--when--i-click-text-in-table-row.html +178 -0
- package/examples/test--when--i-fill-in.html +48 -0
- package/examples/test--when--i-press-button.html +31 -0
- package/examples/test--when--i-reload-page.html +27 -0
- package/examples/test--when--i-scroll-functionality.html +177 -0
- package/examples/test--when--i-scroll-left-right-functionality.html +149 -0
- package/examples/test--when--i-select-option-from-dropdownlist.html +35 -0
- package/examples/test--when--i-select-radio-button.html +95 -0
- package/examples/test--when-i-wait-max-of-time.html +39 -0
- package/examples/test--when-i-wait-page-until-is-loaded.html +47 -0
- package/examples/test--when-i-wait-specific-time.html +39 -0
- package/examples/test-acceptable-url-path.html +11 -0
- package/examples/video-demo.html +43 -0
- package/package.json +56 -0
- package/playwright.config.ts +39 -0
- package/tests/assets/test-document.pdf +14 -0
- package/tests/assets/vardot.png +0 -0
- package/tests/features/a11y.feature +39 -0
- package/tests/features/ajax-wait-examples.feature +24 -0
- package/tests/features/api-step-definitions-individual.feature +185 -0
- package/tests/features/complete-api-testing-examples.feature +205 -0
- package/tests/features/cookie.feature +13 -0
- package/tests/features/date.feature +11 -0
- package/tests/features/dynamic-content-examples.feature +156 -0
- package/tests/features/element.feature +16 -0
- package/tests/features/field.feature +25 -0
- package/tests/features/keyboard.feature +10 -0
- package/tests/features/link.feature +11 -0
- package/tests/features/modal-advanced-example.feature +54 -0
- package/tests/features/modal-basic-example.feature +42 -0
- package/tests/features/modal-error-handling-example.feature +37 -0
- package/tests/features/modal.feature +11 -0
- package/tests/features/path.feature +16 -0
- package/tests/features/response.feature +8 -0
- package/tests/features/responsive.feature +10 -0
- package/tests/features/table.feature +18 -0
- package/tests/features/test--given--i-am-an-anonymous-user.feature +10 -0
- package/tests/features/test--given--i-am-on-homepage.feature +16 -0
- package/tests/features/test--then--i-save-screenshot.feature +33 -0
- package/tests/features/test--then--i-see-locator.feature +320 -0
- package/tests/features/test--then--i-should--not--see-text-in-element.feature +13 -0
- package/tests/features/test--then--i-should--see-text-in-element-by-attr.feature +10 -0
- package/tests/features/test--then--i-should--see-text-in-element.feature +10 -0
- package/tests/features/test--then--i-should--see-text-matching-pattern-in-element.feature +13 -0
- package/tests/features/test--then--i-should--see-text-matching-pattern.feature +18 -0
- package/tests/features/test--then--i-should-be-on-page.feature +10 -0
- package/tests/features/test--then--i-should-be-on-the-homepage.feature +10 -0
- package/tests/features/test--then--i-should-not-see-an-element-by-attr.feature +8 -0
- package/tests/features/test--then--i-should-not-see-an-element.feature +8 -0
- package/tests/features/test--then--i-should-see-an-element-by-attr.feature +8 -0
- package/tests/features/test--then--i-should-see-an-element.feature +8 -0
- package/tests/features/test--then--i-should-see-n-elements.feature +24 -0
- package/tests/features/test--then--i-should-see-text-in-table-row.feature +96 -0
- package/tests/features/test--then--print-current-url-and-response.feature +21 -0
- package/tests/features/test--then--the-checkbox-is-checked.feature +18 -0
- package/tests/features/test--then--the-checkbox-should-be-checked.feature +16 -0
- package/tests/features/test--then--the-element-should-contain-cssproperty.feature +9 -0
- package/tests/features/test--then--the-element-should-not-contain-cssproperty.feature +10 -0
- package/tests/features/test--then--the-field-should-contain-value.feature +11 -0
- package/tests/features/test--then--the-response-should-contain.feature +11 -0
- package/tests/features/test--then--the-response-status-code-should-be.feature +31 -0
- package/tests/features/test--then--the-url-should-match.feature +7 -0
- package/tests/features/test--then-the-link-should-contain-by-attribute.feature +18 -0
- package/tests/features/test--then-the-link-should-contain.feature +7 -0
- package/tests/features/test--when--i-additionally-select.feature +30 -0
- package/tests/features/test--when--i-attach-file-to-feild.feature +9 -0
- package/tests/features/test--when--i-check-checkbox.feature +21 -0
- package/tests/features/test--when--i-click-link-by-attribute.feature +21 -0
- package/tests/features/test--when--i-click-link.feature +9 -0
- package/tests/features/test--when--i-click-text-in-table-row.feature +37 -0
- package/tests/features/test--when--i-fill-in-by-attr.feature +31 -0
- package/tests/features/test--when--i-fill-in-table-by-attr.feature +19 -0
- package/tests/features/test--when--i-fill-in.feature +32 -0
- package/tests/features/test--when--i-follow.feature +22 -0
- package/tests/features/test--when--i-go-to-homepage.feature +9 -0
- package/tests/features/test--when--i-move-forward-backward-one-page.feature +14 -0
- package/tests/features/test--when--i-press-button-by-attribute.feature +18 -0
- package/tests/features/test--when--i-press-button.feature +13 -0
- package/tests/features/test--when--i-reload-page.feature +11 -0
- package/tests/features/test--when--i-scroll-left-right.feature +48 -0
- package/tests/features/test--when--i-scroll.feature +48 -0
- package/tests/features/test--when--i-select-option-from-dropdownlist.feature +21 -0
- package/tests/features/test--when--i-select-radio-button.feature +37 -0
- package/tests/features/test--when--i-wait-page-is-loaded.feature +8 -0
- package/tests/features/test--when--i-wait-time.feature +21 -0
- package/tests/features/video.feature +18 -0
- package/tests/features/wait.feature +7 -0
- package/tests/features/yaml.feature +102 -0
- package/tests/selectors/_canonical-keys.json +113 -0
- package/tests/selectors/back-end-selectors.json +19 -0
- package/tests/selectors/cms-contentful-admin.json +35 -0
- package/tests/selectors/cms-craft-admin.json +39 -0
- package/tests/selectors/cms-drupal-cms-gin.json +56 -0
- package/tests/selectors/cms-drupal-core-claro.json +50 -0
- package/tests/selectors/cms-generic-admin.json +34 -0
- package/tests/selectors/cms-ghost-admin.json +34 -0
- package/tests/selectors/cms-joomla-admin.json +41 -0
- package/tests/selectors/cms-magento2-admin.json +32 -0
- package/tests/selectors/cms-prestashop-admin.json +38 -0
- package/tests/selectors/cms-shopify-admin.json +25 -0
- package/tests/selectors/cms-strapi-admin.json +42 -0
- package/tests/selectors/cms-typo3-admin.json +41 -0
- package/tests/selectors/cms-woocommerce-front.json +50 -0
- package/tests/selectors/cms-wordpress-admin.json +31 -0
- package/tests/selectors/framework-ant-design.json +80 -0
- package/tests/selectors/framework-bootstrap.json +86 -0
- package/tests/selectors/framework-bulma.json +74 -0
- package/tests/selectors/framework-chakra.json +58 -0
- package/tests/selectors/framework-foundation.json +51 -0
- package/tests/selectors/framework-material-ui.json +72 -0
- package/tests/selectors/framework-shadcn.json +51 -0
- package/tests/selectors/framework-tailwind.json +40 -0
- package/tests/selectors/framework-vuetify.json +61 -0
- package/tests/selectors/front-end-selectors.json +16 -0
- package/tests/selectors/homepage-selectors.json +13 -0
- package/tests/step-definitions/a11y.steps.js +800 -0
- package/tests/step-definitions/action.steps.js +167 -0
- package/tests/step-definitions/api.steps.js +732 -0
- package/tests/step-definitions/assertion.steps.js +352 -0
- package/tests/step-definitions/auth.steps.js +126 -0
- package/tests/step-definitions/clock.steps.js +128 -0
- package/tests/step-definitions/cookie.steps.js +216 -0
- package/tests/step-definitions/debug.steps.js +39 -0
- package/tests/step-definitions/dialog.steps.js +193 -0
- package/tests/step-definitions/drupal-canvas.steps.js +764 -0
- package/tests/step-definitions/drupal-ckeditor.steps.js +108 -0
- package/tests/step-definitions/drupal-core.steps.js +665 -0
- package/tests/step-definitions/drupal-helpers.js +371 -0
- package/tests/step-definitions/drupal-layout-builder.steps.js +466 -0
- package/tests/step-definitions/drupal-media.steps.js +99 -0
- package/tests/step-definitions/drupal-moderation.steps.js +71 -0
- package/tests/step-definitions/drupal-paragraphs.steps.js +50 -0
- package/tests/step-definitions/element.steps.js +356 -0
- package/tests/step-definitions/field.steps.js +653 -0
- package/tests/step-definitions/file-download.steps.js +211 -0
- package/tests/step-definitions/form.steps.js +333 -0
- package/tests/step-definitions/iframe.steps.js +228 -0
- package/tests/step-definitions/input.steps.js +202 -0
- package/tests/step-definitions/javascript.steps.js +232 -0
- package/tests/step-definitions/keyboard.steps.js +112 -0
- package/tests/step-definitions/link.steps.js +142 -0
- package/tests/step-definitions/metatag.steps.js +91 -0
- package/tests/step-definitions/modal.steps.js +244 -0
- package/tests/step-definitions/navigation.steps.js +218 -0
- package/tests/step-definitions/network.steps.js +280 -0
- package/tests/step-definitions/path.steps.js +141 -0
- package/tests/step-definitions/response.steps.js +98 -0
- package/tests/step-definitions/responsive.steps.js +125 -0
- package/tests/step-definitions/rest.steps.js +111 -0
- package/tests/step-definitions/screenshot.steps.js +423 -0
- package/tests/step-definitions/scroll.steps.js +189 -0
- package/tests/step-definitions/selectors.steps.js +1003 -0
- package/tests/step-definitions/storage.steps.js +194 -0
- package/tests/step-definitions/table.steps.js +181 -0
- package/tests/step-definitions/varbase-e2e.js +897 -0
- package/tests/step-definitions/varbase.steps.js +458 -0
- package/tests/step-definitions/video.steps.js +178 -0
- package/tests/step-definitions/wait.steps.js +400 -0
- package/tests/step-definitions/web-first.steps.js +298 -0
- package/tests/step-definitions/xml.steps.js +411 -0
- package/tests/step-definitions/yaml.steps.js +913 -0
- package/tsconfig.json +26 -0
|
@@ -0,0 +1,414 @@
|
|
|
1
|
+
# Drupal Canvas steps
|
|
2
|
+
|
|
3
|
+
12 steps, defined in `tests/step-definitions/drupal-canvas.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 | `When I add the "Contact Us" webform to the bottom of the "Contact" Canvas page` |
|
|
10
|
+
| 2 | `Then the Drupal Canvas component library should list the "Hero" component` |
|
|
11
|
+
| 3 | `When I create a Canvas page "Landing" at "/landing" with the "Hero" component:` |
|
|
12
|
+
| 4 | `When I add the "Hero" component to the "Landing" Canvas page using the editor` |
|
|
13
|
+
| 5 | `When I publish the Canvas page changes` |
|
|
14
|
+
| 6 | `Given there is a new Canvas page "Landing" at "/landing"` |
|
|
15
|
+
| 7 | `When I set the Canvas component option "Heading" to "Welcome"` |
|
|
16
|
+
| 8 | `When I open the "Landing" Canvas page in the editor` |
|
|
17
|
+
| 9 | `When I open the "Patterns" tab in the Canvas Library` |
|
|
18
|
+
| 10 | `When I insert the "Hero Slider" pattern from the Canvas Library` |
|
|
19
|
+
| 11 | `When I publish the Canvas page changes through the editor` |
|
|
20
|
+
| 12 | `Then the Canvas Library "Patterns" tab should list "Hero Slider"` |
|
|
21
|
+
|
|
22
|
+
---
|
|
23
|
+
|
|
24
|
+
## 1. When I add the "Contact Us" webform to the bottom of the "Contact" Canvas page
|
|
25
|
+
|
|
26
|
+
Add a Webform block component to the bottom of a Drupal Canvas page and
|
|
27
|
+
publish the page. Drupal Canvas builds pages from a React editor whose
|
|
28
|
+
drag-and-drop cannot be driven by a browser test (the drop target lives in a
|
|
29
|
+
cross-document iframe), so this step performs the same change the editor
|
|
30
|
+
makes by calling Canvas's own authoring API:
|
|
31
|
+
1. resolve the canvas_page id by title,
|
|
32
|
+
2. append a `block.webform_block` component to the page's main content,
|
|
33
|
+
3. POST the updated layout (creates an auto-save),
|
|
34
|
+
4. publish the pending auto-save.
|
|
35
|
+
|
|
36
|
+
Requires an authenticated user with "publish auto-saves" access (e.g. the
|
|
37
|
+
webmaster) — run a login step first. The webform value is the entity
|
|
38
|
+
autocomplete format "Label (machine_name)".
|
|
39
|
+
|
|
40
|
+
Example:
|
|
41
|
+
Given I am a logged in user with the "webmaster" user
|
|
42
|
+
When I add the "Newsletter Subscribe (newsletter_subscribe)" webform to the bottom of the "Home" Canvas page and publish it
|
|
43
|
+
|
|
44
|
+
**Keyword**: `When`
|
|
45
|
+
|
|
46
|
+
**Pattern**
|
|
47
|
+
|
|
48
|
+
```js
|
|
49
|
+
/^(?:I |we )*add the "([^"]*)" webform to the bottom of the "([^"]*)" (?:Canvas )?page(?: and publish(?: it)?)?$/
|
|
50
|
+
```
|
|
51
|
+
|
|
52
|
+
**Examples**
|
|
53
|
+
|
|
54
|
+
```gherkin
|
|
55
|
+
When I add the "Contact Us" webform to the bottom of the "Contact" Canvas page
|
|
56
|
+
And I add the "Newsletter" webform to the bottom of the "Home" page and publish it
|
|
57
|
+
When we add the "Business Contact" webform to the bottom of the "About Us" Canvas page and publish
|
|
58
|
+
And I add the "Feedback" webform to the bottom of the "Support" page
|
|
59
|
+
When I add the "Careers" webform to the bottom of the "Jobs" Canvas page and publish it
|
|
60
|
+
```
|
|
61
|
+
|
|
62
|
+
## 2. Then the Drupal Canvas component library should list the "Hero" component
|
|
63
|
+
|
|
64
|
+
Assert that a component is (or is not) offered in the Drupal Canvas editor's
|
|
65
|
+
component library. The editor populates its library from the same
|
|
66
|
+
`/canvas/api/v0/config/component` endpoint queried here, so this verifies
|
|
67
|
+
what an editor sees when building a page - without driving the React editor.
|
|
68
|
+
|
|
69
|
+
Requires an authenticated user who can edit Canvas pages (run a login step
|
|
70
|
+
and navigate to an admin page first so the request is same-origin).
|
|
71
|
+
|
|
72
|
+
Example:
|
|
73
|
+
Then the Drupal Canvas component library should list the "block.system_menu_block.main" component
|
|
74
|
+
|
|
75
|
+
**Keyword**: `Then`
|
|
76
|
+
|
|
77
|
+
**Pattern**
|
|
78
|
+
|
|
79
|
+
```js
|
|
80
|
+
/^the Drupal Canvas component library should( not)? list the "([^"]*)" component$/
|
|
81
|
+
```
|
|
82
|
+
|
|
83
|
+
**Examples**
|
|
84
|
+
|
|
85
|
+
```gherkin
|
|
86
|
+
Then the Drupal Canvas component library should list the "Hero" component
|
|
87
|
+
And the Drupal Canvas component library should list the "Card" component
|
|
88
|
+
Then the Drupal Canvas component library should not list the "Legacy Slider" component
|
|
89
|
+
And the Drupal Canvas component library should list the "Accordion" component
|
|
90
|
+
Then the Drupal Canvas component library should not list the "Deprecated Banner" component
|
|
91
|
+
```
|
|
92
|
+
|
|
93
|
+
## 3. When I create a Canvas page "Landing" at "/landing" with the "Hero" component:
|
|
94
|
+
|
|
95
|
+
Create (or replace) a published Drupal Canvas page that contains a single
|
|
96
|
+
component, configured from a Gherkin data table of input/value rows. The
|
|
97
|
+
Canvas editor's drag-and-drop cannot be driven by a browser test, so this
|
|
98
|
+
builds the page through Canvas's own content API:
|
|
99
|
+
1. delete any existing page at the same path (idempotent re-runs),
|
|
100
|
+
2. read the live component version (never hard-coded),
|
|
101
|
+
3. POST a new published page whose component tree is that one component
|
|
102
|
+
with the given inputs.
|
|
103
|
+
|
|
104
|
+
This step is generic: pass any Canvas component id (e.g.
|
|
105
|
+
"sdc.vartheme_bs5.card-hero", "block.webform_block"). Boolean-looking values
|
|
106
|
+
("true"/"false") are coerced so checkbox props work. Requires a logged-in
|
|
107
|
+
user who can create Canvas pages (run a login step first).
|
|
108
|
+
|
|
109
|
+
Example:
|
|
110
|
+
When I create a Canvas page "Hero - primary" at "/test-hero-primary" with the "sdc.vartheme_bs5.card-hero" component:
|
|
111
|
+
| title | Primary hero |
|
|
112
|
+
| background_color | bg-primary |
|
|
113
|
+
| card_border | true |
|
|
114
|
+
|
|
115
|
+
**Keyword**: `When`
|
|
116
|
+
|
|
117
|
+
**Pattern**
|
|
118
|
+
|
|
119
|
+
```js
|
|
120
|
+
/^(?:I |we )*create a Canvas page "([^"]*)" at "([^"]*)" with the "([^"]*)" component:$/
|
|
121
|
+
```
|
|
122
|
+
|
|
123
|
+
**Examples**
|
|
124
|
+
|
|
125
|
+
```gherkin
|
|
126
|
+
When I create a Canvas page "Landing" at "/landing" with the "Hero" component:
|
|
127
|
+
And I create a Canvas page "Pricing" at "/pricing" with the "Card" component:
|
|
128
|
+
When we create a Canvas page "Team" at "/about/team" with the "Grid" component:
|
|
129
|
+
And I create a Canvas page "Events" at "/events" with the "Listing" component:
|
|
130
|
+
When I create a Canvas page "Support" at "/support" with the "Accordion" component:
|
|
131
|
+
```
|
|
132
|
+
|
|
133
|
+
## 4. When I add the "Hero" component to the "Landing" Canvas page using the editor
|
|
134
|
+
|
|
135
|
+
Add a component to a Drupal Canvas page the way a human site builder does:
|
|
136
|
+
open the page in the Canvas editor, open the Library, find the named
|
|
137
|
+
component, and drag it onto the (empty) canvas drop zone. The dropped
|
|
138
|
+
component is left selected with its Settings panel open, ready for option
|
|
139
|
+
steps. Drupal Canvas renders its drop zones in the top document during an
|
|
140
|
+
active drag, so the drag is performed with real pointer moves and only
|
|
141
|
+
released once a drop zone reports it is being hovered.
|
|
142
|
+
|
|
143
|
+
Run a login step first (e.g. the webmaster). Use the component's visible
|
|
144
|
+
Library name (e.g. "Hero Card").
|
|
145
|
+
|
|
146
|
+
Example:
|
|
147
|
+
When I add the "Hero Card" component to the "Test Hero Editor" Canvas page using the editor
|
|
148
|
+
|
|
149
|
+
**Keyword**: `When`
|
|
150
|
+
|
|
151
|
+
**Pattern**
|
|
152
|
+
|
|
153
|
+
```js
|
|
154
|
+
/^(?:I |we )*add the "([^"]*)" component to the "([^"]*)" Canvas page using the editor$/
|
|
155
|
+
```
|
|
156
|
+
|
|
157
|
+
**Examples**
|
|
158
|
+
|
|
159
|
+
```gherkin
|
|
160
|
+
When I add the "Hero" component to the "Landing" Canvas page using the editor
|
|
161
|
+
And I add the "Card" component to the "Pricing" Canvas page using the editor
|
|
162
|
+
When we add the "Accordion" component to the "Support" Canvas page using the editor
|
|
163
|
+
And I add the "Grid" component to the "Team" Canvas page using the editor
|
|
164
|
+
When I add the "Listing" component to the "Events" Canvas page using the editor
|
|
165
|
+
```
|
|
166
|
+
|
|
167
|
+
## 5. When I publish the Canvas page changes
|
|
168
|
+
|
|
169
|
+
Publish the pending changes for the Canvas page currently open in the editor.
|
|
170
|
+
|
|
171
|
+
The editor's React "Review changes" publish widget is not reliable to drive
|
|
172
|
+
headless on CI (it can hang), so this commits through Canvas's own authoring
|
|
173
|
+
API - the same endpoints the widget calls: re-POST the page's auto-saved
|
|
174
|
+
layout (which the editor's drag-and-drop and Settings-panel edits have
|
|
175
|
+
populated) to guarantee a pending auto-save, then POST it to the publish
|
|
176
|
+
endpoint. Deterministic and fast, with no editor-UI timing.
|
|
177
|
+
|
|
178
|
+
Example: When I publish the Canvas page changes
|
|
179
|
+
|
|
180
|
+
**Keyword**: `When`
|
|
181
|
+
|
|
182
|
+
**Pattern**
|
|
183
|
+
|
|
184
|
+
```js
|
|
185
|
+
/^(?:I |we )*publish the Canvas page changes$/
|
|
186
|
+
```
|
|
187
|
+
|
|
188
|
+
**Examples**
|
|
189
|
+
|
|
190
|
+
```gherkin
|
|
191
|
+
When I publish the Canvas page changes
|
|
192
|
+
And I publish the Canvas page changes
|
|
193
|
+
When we publish the Canvas page changes
|
|
194
|
+
Given I publish the Canvas page changes
|
|
195
|
+
And we publish the Canvas page changes
|
|
196
|
+
```
|
|
197
|
+
|
|
198
|
+
## 6. Given there is a new Canvas page "Landing" at "/landing"
|
|
199
|
+
|
|
200
|
+
Create (or replace) an empty published Drupal Canvas page, so a later editor
|
|
201
|
+
step can add a component to it the human way. This only sets up the page
|
|
202
|
+
container; it does not add components. Idempotent by path.
|
|
203
|
+
|
|
204
|
+
Example: Given a new Canvas page "Test Hero Editor" at "/test-hero-editor"
|
|
205
|
+
|
|
206
|
+
**Keyword**: `When`
|
|
207
|
+
|
|
208
|
+
**Pattern**
|
|
209
|
+
|
|
210
|
+
```js
|
|
211
|
+
/^(?:there is |I have )?a new Canvas page "([^"]*)" at "([^"]*)"$/
|
|
212
|
+
```
|
|
213
|
+
|
|
214
|
+
**Examples**
|
|
215
|
+
|
|
216
|
+
```gherkin
|
|
217
|
+
Given there is a new Canvas page "Landing" at "/landing"
|
|
218
|
+
And I have a new Canvas page "Pricing" at "/pricing"
|
|
219
|
+
Given a new Canvas page "Team" at "/about/team"
|
|
220
|
+
And there is a new Canvas page "Events" at "/events"
|
|
221
|
+
Given I have a new Canvas page "Support" at "/support"
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
## 7. When I set the Canvas component option "Heading" to "Welcome"
|
|
225
|
+
|
|
226
|
+
Set an option on the component currently selected in the Drupal Canvas editor
|
|
227
|
+
Settings panel, by its visible field label. Scoped to the component props
|
|
228
|
+
form so it never clashes with same-named page fields (e.g. "Title").
|
|
229
|
+
Dispatches input/change so Canvas auto-saves the change. Works for text
|
|
230
|
+
inputs, textareas and select dropdowns (match the option by its visible text
|
|
231
|
+
or its value).
|
|
232
|
+
|
|
233
|
+
Example:
|
|
234
|
+
When I set the Canvas component option "Background color" to "Primary"
|
|
235
|
+
And I set the Canvas component option "Title" to "Configured hero"
|
|
236
|
+
|
|
237
|
+
**Keyword**: `When`
|
|
238
|
+
|
|
239
|
+
**Pattern**
|
|
240
|
+
|
|
241
|
+
```js
|
|
242
|
+
/^(?:I |we )*set the Canvas component option "([^"]*)" to "([^"]*)"$/
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
**Examples**
|
|
246
|
+
|
|
247
|
+
```gherkin
|
|
248
|
+
When I set the Canvas component option "Heading" to "Welcome"
|
|
249
|
+
And I set the Canvas component option "Style" to "Primary"
|
|
250
|
+
When we set the Canvas component option "Alignment" to "Center"
|
|
251
|
+
And I set the Canvas component option "Background" to "Light"
|
|
252
|
+
When I set the Canvas component option "Link text" to "Read more"
|
|
253
|
+
```
|
|
254
|
+
|
|
255
|
+
## 8. When I open the "Landing" Canvas page in the editor
|
|
256
|
+
|
|
257
|
+
Open a Canvas page in the real Drupal Canvas editor the way a site builder
|
|
258
|
+
does: navigate to /canvas/editor/canvas_page/<id> and wait until the editor
|
|
259
|
+
is ready to drive. Drupal Canvas is a heavy React SPA, so readiness is polled
|
|
260
|
+
off the left toolbar "Library" button (it can take several seconds to mount)
|
|
261
|
+
rather than a fixed sleep.
|
|
262
|
+
|
|
263
|
+
Resolves the page id by its title, so create the page first (e.g. with a
|
|
264
|
+
"a new Canvas page ..." step) and run a login step as a user who can edit
|
|
265
|
+
Canvas pages (e.g. the webmaster).
|
|
266
|
+
|
|
267
|
+
**Keyword**: `When`
|
|
268
|
+
|
|
269
|
+
**Pattern**
|
|
270
|
+
|
|
271
|
+
```js
|
|
272
|
+
/^(?:I |we )*open the "([^"]*)" Canvas page in the editor$/
|
|
273
|
+
```
|
|
274
|
+
|
|
275
|
+
**Examples**
|
|
276
|
+
|
|
277
|
+
```gherkin
|
|
278
|
+
When I open the "Landing" Canvas page in the editor
|
|
279
|
+
And I open the "Test Pattern Counters" Canvas page in the editor
|
|
280
|
+
When we open the "Home" Canvas page in the editor
|
|
281
|
+
And we open the "Test Pattern Header Footer" Canvas page in the editor
|
|
282
|
+
Given I open the "Pattern Library Check" Canvas page in the editor
|
|
283
|
+
```
|
|
284
|
+
|
|
285
|
+
## 9. When I open the "Patterns" tab in the Canvas Library
|
|
286
|
+
|
|
287
|
+
Open a named tab in the Drupal Canvas editor Library panel, the way a site
|
|
288
|
+
builder browses ready-made sections. Opens the Library panel if it is closed
|
|
289
|
+
(idempotent - it never toggles an already-open panel shut), activates the
|
|
290
|
+
requested tab, and waits until the tab's list has actually populated (a known
|
|
291
|
+
item is visible) so a following assertion or insert reads real, on-screen
|
|
292
|
+
content - not an empty, still-loading panel.
|
|
293
|
+
|
|
294
|
+
Only "Patterns" and "Components" are valid tab names. Open a page in the
|
|
295
|
+
editor first.
|
|
296
|
+
|
|
297
|
+
**Keyword**: `When`
|
|
298
|
+
|
|
299
|
+
**Pattern**
|
|
300
|
+
|
|
301
|
+
```js
|
|
302
|
+
/^(?:I |we )*open the "(Patterns|Components)" tab in the Canvas Library$/
|
|
303
|
+
```
|
|
304
|
+
|
|
305
|
+
**Examples**
|
|
306
|
+
|
|
307
|
+
```gherkin
|
|
308
|
+
When I open the "Patterns" tab in the Canvas Library
|
|
309
|
+
And I open the "Components" tab in the Canvas Library
|
|
310
|
+
When we open the "Patterns" tab in the Canvas Library
|
|
311
|
+
And we open the "Components" tab in the Canvas Library
|
|
312
|
+
Given I open the "Patterns" tab in the Canvas Library
|
|
313
|
+
```
|
|
314
|
+
|
|
315
|
+
## 10. When I insert the "Hero Slider" pattern from the Canvas Library
|
|
316
|
+
|
|
317
|
+
Insert a default Canvas Pattern into the page open in the editor, exactly as a
|
|
318
|
+
site builder does: right-click the pattern's row in the Library > Patterns
|
|
319
|
+
list (a context-menu trigger) and choose "Insert". The whole section is added
|
|
320
|
+
and the just-inserted component becomes selected, so the editor URL gains a
|
|
321
|
+
fresh /component/<uuid>; the step waits for that uuid to change to confirm the
|
|
322
|
+
insert registered. Inserting the same pattern twice therefore lands two
|
|
323
|
+
independent copies (each gets its own uuid).
|
|
324
|
+
|
|
325
|
+
Open the page in the editor and open the "Patterns" Library tab first. Use the
|
|
326
|
+
pattern's visible human label (e.g. "Hero Slider", "Counters", "Site Header").
|
|
327
|
+
|
|
328
|
+
**Keyword**: `When`
|
|
329
|
+
|
|
330
|
+
**Pattern**
|
|
331
|
+
|
|
332
|
+
```js
|
|
333
|
+
/^(?:I |we )*insert the "([^"]*)" pattern from the Canvas Library$/
|
|
334
|
+
```
|
|
335
|
+
|
|
336
|
+
**Examples**
|
|
337
|
+
|
|
338
|
+
```gherkin
|
|
339
|
+
When I insert the "Hero Slider" pattern from the Canvas Library
|
|
340
|
+
And I insert the "Counters" pattern from the Canvas Library
|
|
341
|
+
And I insert the "Counters" pattern from the Canvas Library
|
|
342
|
+
When we insert the "Site Header" pattern from the Canvas Library
|
|
343
|
+
And we insert the "Site Footer" pattern from the Canvas Library
|
|
344
|
+
```
|
|
345
|
+
|
|
346
|
+
## 11. When I publish the Canvas page changes through the editor
|
|
347
|
+
|
|
348
|
+
Publish the pending Canvas changes through the editor's own Review/Publish
|
|
349
|
+
widget, the way a site builder ships a page: click the topbar "Review N
|
|
350
|
+
change(s)" button, "Select All" in the review list, then "Publish N selected".
|
|
351
|
+
The step waits until the topbar widget resets to "No changes", confirming the
|
|
352
|
+
publish landed. Drupal Canvas's review list is site-wide, so "Select All"
|
|
353
|
+
publishes every pending change; drive this right after inserting on the page
|
|
354
|
+
under test so only that page's changes are pending.
|
|
355
|
+
|
|
356
|
+
Open a page in the editor and make at least one change (e.g. insert a pattern)
|
|
357
|
+
first.
|
|
358
|
+
|
|
359
|
+
**Keyword**: `When`
|
|
360
|
+
|
|
361
|
+
**Pattern**
|
|
362
|
+
|
|
363
|
+
```js
|
|
364
|
+
/^(?:I |we )*publish the Canvas page changes through the editor$/
|
|
365
|
+
```
|
|
366
|
+
|
|
367
|
+
**Examples**
|
|
368
|
+
|
|
369
|
+
```gherkin
|
|
370
|
+
When I publish the Canvas page changes through the editor
|
|
371
|
+
And I publish the Canvas page changes through the editor
|
|
372
|
+
When we publish the Canvas page changes through the editor
|
|
373
|
+
And we publish the Canvas page changes through the editor
|
|
374
|
+
Then I publish the Canvas page changes through the editor
|
|
375
|
+
```
|
|
376
|
+
|
|
377
|
+
## 12. Then the Canvas Library "Patterns" tab should list "Hero Slider"
|
|
378
|
+
|
|
379
|
+
Assert that a Drupal Canvas Library panel does (or does not) list an item by
|
|
380
|
+
its visible label. Scoped to the panel element by CSS selector (e.g. the
|
|
381
|
+
Patterns or Components tab content) and read straight from the panel's
|
|
382
|
+
on-screen text - the labels a site builder actually sees, not any API dump.
|
|
383
|
+
|
|
384
|
+
This is the fast, panel-scoped counterpart of the generic "I should see ... in
|
|
385
|
+
the ... element" assertion: it reads the panel's innerText once and checks the
|
|
386
|
+
label against the panel's line items, so a library with a dozen checks stays
|
|
387
|
+
quick and never trips a step timeout. Matches a whole line item exactly (so
|
|
388
|
+
"Share" does not match "Social media menu" and an absent admin label is never
|
|
389
|
+
a false positive from a longer entry).
|
|
390
|
+
|
|
391
|
+
The panel selector is resolved from the named-selector registry
|
|
392
|
+
(tests/selectors/<preset>.json): the "Patterns" tab maps to the
|
|
393
|
+
"canvas patterns library" selector and "Components" to
|
|
394
|
+
"canvas components library", so the feature reads by tab name and the CSS
|
|
395
|
+
lives in one place. Open the page in the editor and open that Library tab
|
|
396
|
+
first.
|
|
397
|
+
|
|
398
|
+
**Keyword**: `Then`
|
|
399
|
+
|
|
400
|
+
**Pattern**
|
|
401
|
+
|
|
402
|
+
```js
|
|
403
|
+
/^the Canvas Library "(Patterns|Components)" tab should( not)? list "([^"]*)"$/
|
|
404
|
+
```
|
|
405
|
+
|
|
406
|
+
**Examples**
|
|
407
|
+
|
|
408
|
+
```gherkin
|
|
409
|
+
Then the Canvas Library "Patterns" tab should list "Hero Slider"
|
|
410
|
+
And the Canvas Library "Patterns" tab should list "Counters"
|
|
411
|
+
Then the Canvas Library "Components" tab should list "Webform"
|
|
412
|
+
And the Canvas Library "Components" tab should not list "Events Feed"
|
|
413
|
+
And the Canvas Library "Components" tab should not list "Recent pages"
|
|
414
|
+
```
|
|
@@ -0,0 +1,118 @@
|
|
|
1
|
+
# CKEditor 5 steps
|
|
2
|
+
|
|
3
|
+
4 steps, defined in `tests/step-definitions/drupal-ckeditor.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 | `When I fill in the rich text editor field "Body" with "Test Body text"` |
|
|
10
|
+
| 2 | `When I append the rich text editor field "Body" with "More text"` |
|
|
11
|
+
| 3 | `When I click on "media" command button in the rich text editor field "Body"` |
|
|
12
|
+
| 4 | `When I fill in the link URL "Linking to"` |
|
|
13
|
+
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
## 1. When I fill in the rich text editor field "Body" with "Test Body text"
|
|
17
|
+
|
|
18
|
+
Set the value of a CKEditor 5 rich text editor field by the field label/name.
|
|
19
|
+
|
|
20
|
+
Ports VarbaseContext::iFillInTheRichTextEditorField. Resolves the form field
|
|
21
|
+
(label, name, or id), reads its CKEditor 5 instance id from the data
|
|
22
|
+
attribute, and calls setData(). No Varbase E2E equivalent (Varbase E2E's
|
|
23
|
+
"WYSIWYG field" step is CKEditor-version agnostic and may not target CK5).
|
|
24
|
+
|
|
25
|
+
**Keyword**: `When`
|
|
26
|
+
|
|
27
|
+
**Pattern**
|
|
28
|
+
|
|
29
|
+
```js
|
|
30
|
+
/^(?:I |we )*fill in the rich text editor field "([^"]*)" with(?: the)? "([^"]*)"$/
|
|
31
|
+
```
|
|
32
|
+
|
|
33
|
+
**Examples**
|
|
34
|
+
|
|
35
|
+
```gherkin
|
|
36
|
+
When I fill in the rich text editor field "Body" with "Test Body text"
|
|
37
|
+
And I fill in the rich text editor field "Body" with "<p>Hello</p>"
|
|
38
|
+
When we fill in the rich text editor field "Description" with "Text"
|
|
39
|
+
And I fill in the rich text editor field "Summary" with "Intro"
|
|
40
|
+
Given I fill in the rich text editor field "Body" with "Content"
|
|
41
|
+
```
|
|
42
|
+
|
|
43
|
+
## 2. When I append the rich text editor field "Body" with "More text"
|
|
44
|
+
|
|
45
|
+
Append text to the end of a CKEditor 5 rich text editor field.
|
|
46
|
+
|
|
47
|
+
Ports VarbaseContext::appendTheRichTextEditorField.
|
|
48
|
+
|
|
49
|
+
**Keyword**: `When`
|
|
50
|
+
|
|
51
|
+
**Pattern**
|
|
52
|
+
|
|
53
|
+
```js
|
|
54
|
+
/^(?:I |we )*append(?: after)? the rich text editor field "([^"]*)" with "([^"]*)"$/
|
|
55
|
+
```
|
|
56
|
+
|
|
57
|
+
**Examples**
|
|
58
|
+
|
|
59
|
+
```gherkin
|
|
60
|
+
When I append the rich text editor field "Body" with "More text"
|
|
61
|
+
And I append after the rich text editor field "Body" with "End"
|
|
62
|
+
When we append the rich text editor field "Body" with "Tail"
|
|
63
|
+
And I append after the rich text editor field "Description" with "!"
|
|
64
|
+
Given I append the rich text editor field "Body" with "Extra"
|
|
65
|
+
```
|
|
66
|
+
|
|
67
|
+
## 3. When I click on "media" command button in the rich text editor field "Body"
|
|
68
|
+
|
|
69
|
+
Click a toolbar command button inside a CKEditor 5 field.
|
|
70
|
+
|
|
71
|
+
Ports VarbaseContext::iClickOnCommandButtonInTheRichTextEditorField and
|
|
72
|
+
iClickOnTheSaveButtonInTheEditor. Matches both:
|
|
73
|
+
When I click on "bold" command button in the rich text editor field "Body"
|
|
74
|
+
When I click on the insert button in "Body" rich text editor field
|
|
75
|
+
|
|
76
|
+
**Keyword**: `When`
|
|
77
|
+
|
|
78
|
+
**Pattern**
|
|
79
|
+
|
|
80
|
+
```js
|
|
81
|
+
/^(?:I |we )*click on (?:"([^"]*)" command button in the rich text editor field "([^"]*)"|the (save|insert|action|apply) button in "([^"]*)" rich text editor field)$/
|
|
82
|
+
```
|
|
83
|
+
|
|
84
|
+
**Examples**
|
|
85
|
+
|
|
86
|
+
```gherkin
|
|
87
|
+
When I click on "media" command button in the rich text editor field "Body"
|
|
88
|
+
And I click on "bold" command button in the rich text editor field "Body"
|
|
89
|
+
When I click on the insert button in "Body" rich text editor field
|
|
90
|
+
And I click on the save button in "Body" rich text editor field
|
|
91
|
+
When we click on "link" command button in the rich text editor field "Body"
|
|
92
|
+
```
|
|
93
|
+
|
|
94
|
+
## 4. When I fill in the link URL "Linking to"
|
|
95
|
+
|
|
96
|
+
Type a query into the open CKEditor 5 Drupal-link balloon's "Link URL" field
|
|
97
|
+
so Linkit's autocomplete (ul.ui-autocomplete) searches for internal content.
|
|
98
|
+
|
|
99
|
+
The balloon holds several inputs (Displayed text, Title, ARIA label, CSS
|
|
100
|
+
classes … from editor_advanced_link), so target the one whose label is
|
|
101
|
+
"Link URL". CKEditor 5's input reacts only to real per-character typing (a
|
|
102
|
+
value assignment is ignored), so type with a small delay to let Linkit
|
|
103
|
+
debounce and query. This replaces the CKEditor-4-era "fill in … for
|
|
104
|
+
'Link URL'" + keypress steps.
|
|
105
|
+
|
|
106
|
+
**Keyword**: `When`
|
|
107
|
+
|
|
108
|
+
**Pattern**
|
|
109
|
+
|
|
110
|
+
```js
|
|
111
|
+
/^(?:I |we )*fill in the link URL "([^"]*)"$/
|
|
112
|
+
```
|
|
113
|
+
|
|
114
|
+
**Examples**
|
|
115
|
+
|
|
116
|
+
```gherkin
|
|
117
|
+
When I fill in the link URL "Linking to"
|
|
118
|
+
```
|