@camunda/e2e-test-suite 0.0.1629 → 0.0.1630

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.
@@ -42,6 +42,8 @@ declare class ModelerHomePage {
42
42
  readonly formNameBreadcrumb: (formName: string) => Locator;
43
43
  readonly formBreadcrumbButton: Locator;
44
44
  readonly formActionsButton: Locator;
45
+ readonly newFormActionsButton: Locator;
46
+ readonly formCreateLoadErrorToast: Locator;
45
47
  readonly renameFormMenuItem: Locator;
46
48
  readonly renameInput: Locator;
47
49
  readonly renameSubmitButton: Locator;
@@ -76,6 +78,7 @@ declare class ModelerHomePage {
76
78
  clickHomeBreadcrumb(): Promise<void>;
77
79
  clickOpenOrganizationsButton(): Promise<void>;
78
80
  createForm(formName: string): Promise<void>;
81
+ createFormWithRetry(formName: string): Promise<void>;
79
82
  clickCreateIdpApplicationButton(): Promise<void>;
80
83
  clickCrossComponentProjectFolder(): Promise<void>;
81
84
  createCrossComponentProjectFolder(): Promise<void>;
@@ -66,6 +66,8 @@ class ModelerHomePage {
66
66
  formNameBreadcrumb;
67
67
  formBreadcrumbButton;
68
68
  formActionsButton;
69
+ newFormActionsButton;
70
+ formCreateLoadErrorToast;
69
71
  renameFormMenuItem;
70
72
  renameInput;
71
73
  renameSubmitButton;
@@ -230,6 +232,23 @@ class ModelerHomePage {
230
232
  .or(page.getByRole('navigation', { name: 'Breadcrumb', exact: true }))
231
233
  .getByRole('button', { name: / actions$/ })
232
234
  .last();
235
+ // Readiness signal for a freshly created form: its own crumb's kebab reads
236
+ // exactly "New form actions" until renamed. Distinct from formActionsButton
237
+ // (any " actions" kebab), which still resolves to the parent container's
238
+ // crumb while the form is loading or failed to load.
239
+ this.newFormActionsButton = page
240
+ .getByRole('navigation', { name: 'Context navigation' })
241
+ .or(page.getByRole('navigation', { name: 'Breadcrumb', exact: true }))
242
+ .getByRole('button', { name: 'New form actions', exact: true });
243
+ // Web Modeler's SaaS backend intermittently fails the create-file POST
244
+ // (camunda-hub api/files/use-create-file.ts) or the follow-up form-data
245
+ // fetch (camunda-hub stores/form-store.tsx loadFileFolderAndProject), both
246
+ // of which the product surfaces as a transient "Try again later" toast and
247
+ // leave the form editor unopened. Matched by text so it resolves whether hub
248
+ // renders the Carbon alert or the design-system (sonner) toast variant.
249
+ this.formCreateLoadErrorToast = page
250
+ .getByText(/Could not (create the file|load your form data)\. Try again later\.|Something went wrong while (parsing|validating) the form\./)
251
+ .first();
233
252
  this.renameFormMenuItem = page
234
253
  .locator('[data-test="rename-form"]')
235
254
  .or(page.getByRole('menuitem', { name: 'Rename', exact: true }))
@@ -714,6 +733,37 @@ class ModelerHomePage {
714
733
  await this.enterFormName(formName);
715
734
  await (0, sleep_1.sleep)(10000);
716
735
  }
736
+ // Creates a form, recovering from Web Modeler's intermittent server-side
737
+ // failures. The create-file POST and the subsequent form-data fetch each fail
738
+ // on the SaaS backend often enough to break the smoke run while the full-suite
739
+ // pass against the same cluster stays green -- a transient fault, not a product
740
+ // defect, which the product itself reports with "Try again later." Either one
741
+ // leaves the editor unopened so the "New form actions" crumb never renders.
742
+ // Wait for that crumb or for the transient toast, and on the toast re-enter the
743
+ // container and recreate, rather than waiting longer on a form that never
744
+ // loaded.
745
+ async createFormWithRetry(formName) {
746
+ const maxAttempts = 3;
747
+ for (let attempt = 1; attempt <= maxAttempts; attempt++) {
748
+ await this.clickDiagramTypeDropdown();
749
+ await this.clickFormOption();
750
+ await this.becameVisible(this.newFormActionsButton.or(this.formCreateLoadErrorToast).first(), 60000);
751
+ const transientError = await this.formCreateLoadErrorToast
752
+ .isVisible()
753
+ .catch(() => false);
754
+ if (!transientError) {
755
+ await this.enterFormName(formName);
756
+ return;
757
+ }
758
+ if (attempt === maxAttempts) {
759
+ throw new Error('Web Modeler kept raising a transient "Try again later" error while ' +
760
+ `creating the form, after ${maxAttempts} attempts`);
761
+ }
762
+ console.warn('Form creation hit a transient Web Modeler error ' +
763
+ `(attempt ${attempt}/${maxAttempts}); re-entering the container to retry`);
764
+ await this.returnToResourceContainer();
765
+ }
766
+ }
717
767
  async clickCreateIdpApplicationButton() {
718
768
  await this.createIdpApplicationButton.click();
719
769
  }
@@ -61,9 +61,7 @@ _8_9_1.test.describe('Smoke Tests', () => {
61
61
  });
62
62
  await _8_9_1.test.step('Create form to be linked for Zeebe user task', async () => {
63
63
  await modelerHomePage.clickCrossComponentProjectFolder();
64
- await modelerHomePage.clickDiagramTypeDropdown();
65
- await modelerHomePage.clickFormOption();
66
- await modelerHomePage.enterFormName(formName);
64
+ await modelerHomePage.createFormWithRetry(formName);
67
65
  await modelerHomePage.assertFormBreadcrumbVisible(formName);
68
66
  await formJsPage.deployForm(CLUSTER_NAME);
69
67
  // Wait for the form to propagate to the cluster before it can be embedded
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camunda/e2e-test-suite",
3
- "version": "0.0.1629",
3
+ "version": "0.0.1630",
4
4
  "description": "End-to-end test helpers for Camunda 8",
5
5
  "repository": {
6
6
  "type": "git",