@camunda/e2e-test-suite 0.0.1595 → 0.0.1597

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.
@@ -58,6 +58,7 @@ declare class ConsoleOrganizationPage {
58
58
  clickSettingsTab(): Promise<void>;
59
59
  clickOptInButton(): Promise<void>;
60
60
  enableAlphaFeature(name: string): Promise<void>;
61
+ closeTermsDialog(): Promise<void>;
61
62
  scrollToOptInCheckbox(): Promise<void>;
62
63
  checkOptInCheckbox(): Promise<void>;
63
64
  clickMainUser(): Promise<void>;
@@ -2,7 +2,6 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.ConsoleOrganizationPage = void 0;
4
4
  const test_1 = require("@playwright/test");
5
- const sleep_1 = require("../../utils/sleep");
6
5
  const expectLocatorWithRetry_1 = require("../../utils/assertionHelpers/expectLocatorWithRetry");
7
6
  class ConsoleOrganizationPage {
8
7
  page;
@@ -86,7 +85,7 @@ class ConsoleOrganizationPage {
86
85
  this.startProcessIPermissionCheckbox = page.getByRole('checkbox', {
87
86
  name: 'Start process instance',
88
87
  });
89
- this.optInAICheckbox = page.getByLabel('I understand and agree to Terms for AI Usage');
88
+ this.optInAICheckbox = this.dialog.first().getByRole('checkbox');
90
89
  this.rows = this.page.getByRole('row');
91
90
  this.groupsTab = page.getByRole('tab', { name: 'Groups' });
92
91
  this.createGroupButton = page.getByRole('button', {
@@ -283,70 +282,85 @@ class ConsoleOrganizationPage {
283
282
  await this.optInButton.click({ timeout: 60000 });
284
283
  }
285
284
  async enableAlphaFeature(name) {
286
- const maxRetries = 3;
287
- for (let retries = 0; retries < maxRetries; retries++) {
288
- try {
289
- await this.clickSettingsTab();
290
- await this.optInToAlphaFeatures();
291
- await (0, sleep_1.sleep)(30000);
285
+ await this.clickSettingsTab();
286
+ await this.optInToAlphaFeatures();
287
+ await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, this.rows.first(), {
288
+ visibilityTimeout: 60000,
289
+ totalTimeout: 300000,
290
+ maxRetries: 5,
291
+ postAction: async () => {
292
292
  await this.page.reload();
293
293
  await this.clickSettingsTab();
294
- await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, this.rows.first(), {
295
- visibilityTimeout: 15000,
296
- totalTimeout: 90000,
297
- postAction: async () => {
298
- await this.page.reload();
299
- },
300
- });
301
- const alphaFeature = this.rows.filter({ hasText: name }).first();
302
- if ((await alphaFeature.count()) < 1) {
303
- // Returning here used to report the feature as enabled while nothing
304
- // had been enabled at all, so the org silently stayed opted out and
305
- // every dependent spec failed later on a missing UI affordance.
306
- // Throw instead: the surrounding loop reloads and retries, and a
307
- // genuinely absent row fails this step where the cause is visible.
308
- throw new Error(`No alpha feature(${name}) is found.`);
309
- }
310
- //Opt-in The Alpha Feature
311
- const alphaFeatureOptInButton = alphaFeature.getByRole('button', {
312
- name: 'Opt in to enable',
313
- });
314
- if (await alphaFeatureOptInButton.isVisible({ timeout: 10000 })) {
315
- await alphaFeatureOptInButton.click({ timeout: 30000 });
316
- await this.optInAICheckbox.scrollIntoViewIfNeeded();
317
- await this.optInAICheckbox.check({ timeout: 30000 });
318
- await (0, sleep_1.sleep)(3000);
319
- }
320
- //Enable Alpha Feature
321
- const toggleText = await alphaFeature
322
- .locator('[class= "cds--toggle__text"]')
323
- .textContent();
324
- console.info(`Previous feature(${name}) setting is ${toggleText}.`);
325
- if (toggleText == 'Enabled') {
326
- console.log(`Feature ${name} is already enabled.`);
327
- return;
328
- }
329
- if (toggleText == 'Disabled') {
330
- await alphaFeature
331
- .locator('[class= "cds--toggle__switch"]')
332
- .first()
333
- .click();
334
- await (0, sleep_1.sleep)(10000);
335
- }
336
- await (0, test_1.expect)(alphaFeature.locator('[class= "cds--toggle__text"]')).toHaveText('Enabled');
337
- return;
294
+ },
295
+ });
296
+ const alphaFeature = this.rows.filter({ hasText: name }).first();
297
+ if ((await alphaFeature.count()) < 1) {
298
+ throw new Error(`No alpha feature(${name}) is found.`);
299
+ }
300
+ const alphaFeatureOptInButton = alphaFeature.getByRole('button', {
301
+ name: 'Opt in to enable',
302
+ });
303
+ if (await alphaFeatureOptInButton.isVisible({ timeout: 10000 })) {
304
+ if (await alphaFeatureOptInButton.isEnabled()) {
305
+ await alphaFeatureOptInButton.click({ timeout: 90000 });
306
+ await (0, test_1.expect)(this.dialog.first()).toBeVisible({ timeout: 60000 });
307
+ await this.scrollToOptInCheckbox();
308
+ await this.optInAICheckbox.check({ timeout: 90000 });
309
+ await this.closeTermsDialog();
338
310
  }
339
- catch (error) {
340
- console.error(`Click attempt ${retries + 1} failed: ${error}`);
311
+ }
312
+ const toggle = alphaFeature.getByRole('switch').first();
313
+ await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, toggle, {
314
+ visibilityTimeout: 30000,
315
+ totalTimeout: 180000,
316
+ maxRetries: 5,
317
+ postAction: async () => {
341
318
  await this.page.reload();
342
- await (0, sleep_1.sleep)(10000);
343
- }
319
+ await this.clickSettingsTab();
320
+ },
321
+ });
322
+ if (await toggle.isChecked()) {
323
+ console.log(`Feature ${name} is already enabled.`);
324
+ return;
344
325
  }
345
- throw new Error(`Failed to eanble alpha feature ${name} after ${maxRetries} attempts.`);
326
+ await toggle.click();
327
+ await (0, test_1.expect)(toggle).toBeChecked({ timeout: 60000 });
328
+ }
329
+ async closeTermsDialog() {
330
+ const closeButton = this.dialog
331
+ .first()
332
+ .getByRole('button', { name: 'Close' });
333
+ if (await closeButton.isVisible({ timeout: 10000 }).catch(() => false)) {
334
+ await closeButton.click();
335
+ }
336
+ await (0, test_1.expect)(this.dialog.first()).toBeHidden({ timeout: 60000 });
346
337
  }
347
338
  async scrollToOptInCheckbox() {
348
- await this.page.locator('.ps-contract-scroll').evaluate((el) => {
349
- el.scrollTop = el.scrollHeight;
339
+ const dialog = this.dialog.first();
340
+ await (0, test_1.expect)(dialog).toBeVisible({ timeout: 30000 });
341
+ const contractScroll = this.page.locator('.ps-contract-scroll').first();
342
+ if (await contractScroll.isVisible({ timeout: 5000 }).catch(() => false)) {
343
+ await contractScroll.evaluate((el) => {
344
+ el.scrollTop = el.scrollHeight;
345
+ el.dispatchEvent(new Event('scroll', { bubbles: true }));
346
+ });
347
+ return;
348
+ }
349
+ const box = await dialog.boundingBox();
350
+ if (box) {
351
+ await this.page.mouse.move(box.x + box.width / 2, box.y + box.height * 0.6);
352
+ for (let i = 0; i < 20; i++) {
353
+ await this.page.mouse.wheel(0, 300);
354
+ }
355
+ }
356
+ await dialog.evaluate((dlg) => {
357
+ const all = [dlg, ...Array.from(dlg.querySelectorAll('*'))];
358
+ for (const node of all) {
359
+ if (!(node instanceof HTMLElement))
360
+ continue;
361
+ node.scrollTop = node.scrollHeight;
362
+ node.dispatchEvent(new Event('scroll', { bubbles: true }));
363
+ }
350
364
  });
351
365
  }
352
366
  async checkOptInCheckbox() {
@@ -378,15 +392,17 @@ class ConsoleOrganizationPage {
378
392
  await this.page.reload();
379
393
  },
380
394
  });
381
- try {
382
- await (0, test_1.expect)(this.optInButton).toBeVisible({ timeout: 30000 });
383
- await this.clickOptInButton();
384
- await this.scrollToOptInCheckbox();
385
- await this.checkOptInCheckbox();
386
- }
387
- catch {
388
- await (0, test_1.expect)(this.optInButton).not.toBeVisible();
395
+ if (!(await this.optInButton.isVisible({ timeout: 30000 }).catch(() => false))) {
396
+ return;
389
397
  }
398
+ await this.clickOptInButton();
399
+ await (0, test_1.expect)(this.dialog.first()).toBeVisible({ timeout: 60000 });
400
+ await this.scrollToOptInCheckbox();
401
+ await this.optInCheckbox.check({ timeout: 90000 });
402
+ await this.closeTermsDialog();
403
+ await this.page.reload();
404
+ await this.clickSettingsTab();
405
+ await (0, test_1.expect)(this.optInButton).not.toBeVisible({ timeout: 60000 });
390
406
  }
391
407
  async clickGroupsTab() {
392
408
  await this.groupsTab.click({ timeout: 60000 });
@@ -302,8 +302,17 @@ class ModelerCreatePage {
302
302
  this.processIdInput = page.getByLabel('ID', { exact: true });
303
303
  this.payloadNameInput = page.getByLabel('Full Name');
304
304
  this.payloadDateInput = page.getByLabel('Date of Birth');
305
- this.payloadCheckboxInput = this.form.getByLabel('Agree');
306
- this.payloadNumberInput = this.form.getByLabel('Count');
305
+ // Scoped to the deploy/run dialog and matched by role, not through the
306
+ // exact-class form container: the start form renders inside the dialog
307
+ // and `[class="fjs-container"]` only matches when that element carries
308
+ // no other class, so an extra class on the form root silently empties
309
+ // every locator built on it.
310
+ this.payloadCheckboxInput = this.dialog
311
+ .first()
312
+ .getByRole('checkbox', { name: 'Agree' });
313
+ this.payloadNumberInput = this.dialog
314
+ .first()
315
+ .getByRole('textbox', { name: 'Count' });
307
316
  this.formPropertySection = page.locator('[data-group-id="group-form"]');
308
317
  this.formLinkingTypeDropdown = page.getByLabel('Type');
309
318
  this.formLinkTypeOptions = page.locator('#bio-properties-panel-formType');
@@ -67,6 +67,7 @@ declare class ConsoleOrganizationPage {
67
67
  clickSettingsTab(): Promise<void>;
68
68
  clickOptInButton(): Promise<void>;
69
69
  enableAlphaFeature(name: string): Promise<void>;
70
+ closeTermsDialog(): Promise<void>;
70
71
  scrollToOptInCheckbox(): Promise<void>;
71
72
  checkOptInCheckbox(): Promise<void>;
72
73
  clickMainUser(email: string): Promise<void>;
@@ -120,7 +120,7 @@ class ConsoleOrganizationPage {
120
120
  this.startProcessIPermissionCheckbox = page.getByRole('checkbox', {
121
121
  name: 'Start process instance',
122
122
  });
123
- this.optInAICheckbox = page.getByLabel('I understand and agree to Terms for AI Usage');
123
+ this.optInAICheckbox = this.dialog.first().getByRole('checkbox');
124
124
  this.rows = this.page.getByRole('row');
125
125
  this.groupsTab = page.getByRole('tab', { name: 'Groups' });
126
126
  this.createGroupButton = page.getByRole('button', {
@@ -369,66 +369,85 @@ class ConsoleOrganizationPage {
369
369
  await this.optInButton.click({ timeout: 60000 });
370
370
  }
371
371
  async enableAlphaFeature(name) {
372
- const maxRetries = 3;
373
- for (let retries = 0; retries < maxRetries; retries++) {
374
- try {
375
- await this.clickSettingsTab();
376
- await this.optInToAlphaFeatures();
377
- await (0, sleep_1.sleep)(30000);
372
+ await this.clickSettingsTab();
373
+ await this.optInToAlphaFeatures();
374
+ await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, this.rows.first(), {
375
+ visibilityTimeout: 60000,
376
+ totalTimeout: 300000,
377
+ maxRetries: 5,
378
+ postAction: async () => {
378
379
  await this.page.reload();
379
380
  await this.clickSettingsTab();
380
- await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, this.rows.first(), {
381
- visibilityTimeout: 15000,
382
- totalTimeout: 90000,
383
- postAction: async () => {
384
- await this.page.reload();
385
- },
386
- });
387
- const alphaFeature = this.rows.filter({ hasText: name }).first();
388
- if ((await alphaFeature.count()) < 1) {
389
- console.error(`No alpha feature(${name}) is found.`);
390
- return;
391
- }
392
- //Opt-in The Alpha Feature
393
- const alphaFeatureOptInButton = alphaFeature.getByRole('button', {
394
- name: 'Opt in to enable',
395
- });
396
- if (await alphaFeatureOptInButton.isVisible({ timeout: 10000 })) {
397
- await alphaFeatureOptInButton.click({ timeout: 30000 });
398
- await this.optInAICheckbox.scrollIntoViewIfNeeded();
399
- await this.optInAICheckbox.check({ timeout: 30000 });
400
- await (0, sleep_1.sleep)(3000);
401
- }
402
- //Enable Alpha Feature
403
- const toggleText = await alphaFeature
404
- .locator('[class= "cds--toggle__text"]')
405
- .textContent();
406
- console.info(`Previous feature(${name}) setting is ${toggleText}.`);
407
- if (toggleText == 'Enabled') {
408
- console.log(`Feature ${name} is already enabled.`);
409
- return;
410
- }
411
- if (toggleText == 'Disabled') {
412
- await alphaFeature
413
- .locator('[class= "cds--toggle__switch"]')
414
- .first()
415
- .click();
416
- await (0, sleep_1.sleep)(10000);
417
- }
418
- await (0, test_1.expect)(alphaFeature.locator('[class= "cds--toggle__text"]')).toHaveText('Enabled');
419
- return;
381
+ },
382
+ });
383
+ const alphaFeature = this.rows.filter({ hasText: name }).first();
384
+ if ((await alphaFeature.count()) < 1) {
385
+ throw new Error(`No alpha feature(${name}) is found.`);
386
+ }
387
+ const alphaFeatureOptInButton = alphaFeature.getByRole('button', {
388
+ name: 'Opt in to enable',
389
+ });
390
+ if (await alphaFeatureOptInButton.isVisible({ timeout: 10000 })) {
391
+ if (await alphaFeatureOptInButton.isEnabled()) {
392
+ await alphaFeatureOptInButton.click({ timeout: 90000 });
393
+ await (0, test_1.expect)(this.dialog.first()).toBeVisible({ timeout: 60000 });
394
+ await this.scrollToOptInCheckbox();
395
+ await this.optInAICheckbox.check({ timeout: 90000 });
396
+ await this.closeTermsDialog();
420
397
  }
421
- catch (error) {
422
- console.error(`Click attempt ${retries + 1} failed: ${error}`);
398
+ }
399
+ const toggle = alphaFeature.getByRole('switch').first();
400
+ await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, toggle, {
401
+ visibilityTimeout: 30000,
402
+ totalTimeout: 180000,
403
+ maxRetries: 5,
404
+ postAction: async () => {
423
405
  await this.page.reload();
424
- await (0, sleep_1.sleep)(10000);
425
- }
406
+ await this.clickSettingsTab();
407
+ },
408
+ });
409
+ if (await toggle.isChecked()) {
410
+ console.log(`Feature ${name} is already enabled.`);
411
+ return;
426
412
  }
427
- throw new Error(`Failed to eanble alpha feature ${name} after ${maxRetries} attempts.`);
413
+ await toggle.click();
414
+ await (0, test_1.expect)(toggle).toBeChecked({ timeout: 60000 });
415
+ }
416
+ async closeTermsDialog() {
417
+ const closeButton = this.dialog
418
+ .first()
419
+ .getByRole('button', { name: 'Close' });
420
+ if (await closeButton.isVisible({ timeout: 10000 }).catch(() => false)) {
421
+ await closeButton.click();
422
+ }
423
+ await (0, test_1.expect)(this.dialog.first()).toBeHidden({ timeout: 60000 });
428
424
  }
429
425
  async scrollToOptInCheckbox() {
430
- await this.page.locator('.ps-contract-scroll').evaluate((el) => {
431
- el.scrollTop = el.scrollHeight;
426
+ const dialog = this.dialog.first();
427
+ await (0, test_1.expect)(dialog).toBeVisible({ timeout: 30000 });
428
+ const contractScroll = this.page.locator('.ps-contract-scroll').first();
429
+ if (await contractScroll.isVisible({ timeout: 5000 }).catch(() => false)) {
430
+ await contractScroll.evaluate((el) => {
431
+ el.scrollTop = el.scrollHeight;
432
+ el.dispatchEvent(new Event('scroll', { bubbles: true }));
433
+ });
434
+ return;
435
+ }
436
+ const box = await dialog.boundingBox();
437
+ if (box) {
438
+ await this.page.mouse.move(box.x + box.width / 2, box.y + box.height * 0.6);
439
+ for (let i = 0; i < 20; i++) {
440
+ await this.page.mouse.wheel(0, 300);
441
+ }
442
+ }
443
+ await dialog.evaluate((dlg) => {
444
+ const all = [dlg, ...Array.from(dlg.querySelectorAll('*'))];
445
+ for (const node of all) {
446
+ if (!(node instanceof HTMLElement))
447
+ continue;
448
+ node.scrollTop = node.scrollHeight;
449
+ node.dispatchEvent(new Event('scroll', { bubbles: true }));
450
+ }
432
451
  });
433
452
  }
434
453
  async checkOptInCheckbox() {
@@ -523,15 +542,17 @@ class ConsoleOrganizationPage {
523
542
  await this.page.reload();
524
543
  },
525
544
  });
526
- try {
527
- await (0, test_1.expect)(this.optInButton).toBeVisible({ timeout: 30000 });
528
- await this.clickOptInButton();
529
- await this.scrollToOptInCheckbox();
530
- await this.checkOptInCheckbox();
531
- }
532
- catch {
533
- await (0, test_1.expect)(this.optInButton).not.toBeVisible();
545
+ if (!(await this.optInButton.isVisible({ timeout: 30000 }).catch(() => false))) {
546
+ return;
534
547
  }
548
+ await this.clickOptInButton();
549
+ await (0, test_1.expect)(this.dialog.first()).toBeVisible({ timeout: 60000 });
550
+ await this.scrollToOptInCheckbox();
551
+ await this.optInCheckbox.check({ timeout: 90000 });
552
+ await this.closeTermsDialog();
553
+ await this.page.reload();
554
+ await this.clickSettingsTab();
555
+ await (0, test_1.expect)(this.optInButton).not.toBeVisible({ timeout: 60000 });
535
556
  }
536
557
  async clickGroupsTab() {
537
558
  for (let attempt = 0; attempt < 3; attempt++) {
@@ -262,8 +262,17 @@ class ModelerCreatePage {
262
262
  this.processIdInput = page.getByLabel('ID', { exact: true });
263
263
  this.payloadNameInput = page.getByLabel('Full Name');
264
264
  this.payloadDateInput = page.getByLabel('Date of Birth');
265
- this.payloadCheckboxInput = this.form.getByLabel('Agree');
266
- this.payloadNumberInput = this.form.getByLabel('Count');
265
+ // Scoped to the deploy/run dialog and matched by role, not through the
266
+ // exact-class form container: the start form renders inside the dialog
267
+ // and `[class="fjs-container"]` only matches when that element carries
268
+ // no other class, so an extra class on the form root silently empties
269
+ // every locator built on it.
270
+ this.payloadCheckboxInput = this.dialog
271
+ .first()
272
+ .getByRole('checkbox', { name: 'Agree' });
273
+ this.payloadNumberInput = this.dialog
274
+ .first()
275
+ .getByRole('textbox', { name: 'Count' });
267
276
  this.formPropertySection = page.locator('[data-group-id="group-form"]');
268
277
  this.formLinkingTypeDropdown = page.getByLabel('Type');
269
278
  this.formLinkTypeOptions = page.locator('#bio-properties-panel-formType');
@@ -58,6 +58,7 @@ declare class ConsoleOrganizationPage {
58
58
  clickSettingsTab(): Promise<void>;
59
59
  clickOptInButton(): Promise<void>;
60
60
  enableAlphaFeature(name: string): Promise<void>;
61
+ closeTermsDialog(): Promise<void>;
61
62
  scrollToOptInCheckbox(): Promise<void>;
62
63
  checkOptInCheckbox(): Promise<void>;
63
64
  clickMainUser(): Promise<void>;
@@ -2,7 +2,6 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.ConsoleOrganizationPage = void 0;
4
4
  const test_1 = require("@playwright/test");
5
- const sleep_1 = require("../../utils/sleep");
6
5
  const expectLocatorWithRetry_1 = require("../../utils/assertionHelpers/expectLocatorWithRetry");
7
6
  class ConsoleOrganizationPage {
8
7
  page;
@@ -99,7 +98,7 @@ class ConsoleOrganizationPage {
99
98
  this.startProcessIPermissionCheckbox = page.getByRole('checkbox', {
100
99
  name: 'Start process instance',
101
100
  });
102
- this.optInAICheckbox = page.getByLabel('I understand and agree to Terms for AI Usage');
101
+ this.optInAICheckbox = this.dialog.first().getByRole('checkbox');
103
102
  this.rows = this.page.getByRole('row');
104
103
  this.groupsTab = page.getByRole('tab', { name: 'Groups' });
105
104
  this.createGroupButton = page.getByRole('button', {
@@ -297,66 +296,85 @@ class ConsoleOrganizationPage {
297
296
  await this.optInButton.click({ timeout: 60000 });
298
297
  }
299
298
  async enableAlphaFeature(name) {
300
- const maxRetries = 3;
301
- for (let retries = 0; retries < maxRetries; retries++) {
302
- try {
303
- await this.clickSettingsTab();
304
- await this.optInToAlphaFeatures();
305
- await (0, sleep_1.sleep)(30000);
299
+ await this.clickSettingsTab();
300
+ await this.optInToAlphaFeatures();
301
+ await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, this.rows.first(), {
302
+ visibilityTimeout: 60000,
303
+ totalTimeout: 300000,
304
+ maxRetries: 5,
305
+ postAction: async () => {
306
306
  await this.page.reload();
307
307
  await this.clickSettingsTab();
308
- await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, this.rows.first(), {
309
- visibilityTimeout: 15000,
310
- totalTimeout: 90000,
311
- postAction: async () => {
312
- await this.page.reload();
313
- },
314
- });
315
- const alphaFeature = this.rows.filter({ hasText: name }).first();
316
- if ((await alphaFeature.count()) < 1) {
317
- console.error(`No alpha feature(${name}) is found.`);
318
- return;
319
- }
320
- //Opt-in The Alpha Feature
321
- const alphaFeatureOptInButton = alphaFeature.getByRole('button', {
322
- name: 'Opt in to enable',
323
- });
324
- if (await alphaFeatureOptInButton.isVisible({ timeout: 10000 })) {
325
- await alphaFeatureOptInButton.click({ timeout: 20000 });
326
- await this.optInAICheckbox.scrollIntoViewIfNeeded();
327
- await this.optInAICheckbox.check({ timeout: 20000 });
328
- await (0, sleep_1.sleep)(3000);
329
- }
330
- //Enable Alpha Feature
331
- const toggleText = await alphaFeature
332
- .locator('[class= "cds--toggle__text"]')
333
- .textContent();
334
- console.info(`Previous feature(${name}) setting is ${toggleText}.`);
335
- if (toggleText == 'Enabled') {
336
- console.log(`Feature ${name} is already enabled.`);
337
- return;
338
- }
339
- if (toggleText == 'Disabled') {
340
- await alphaFeature
341
- .locator('[class= "cds--toggle__switch"]')
342
- .first()
343
- .click();
344
- await (0, sleep_1.sleep)(10000);
345
- }
346
- await (0, test_1.expect)(alphaFeature.locator('[class= "cds--toggle__text"]')).toHaveText('Enabled');
347
- return;
308
+ },
309
+ });
310
+ const alphaFeature = this.rows.filter({ hasText: name }).first();
311
+ if ((await alphaFeature.count()) < 1) {
312
+ throw new Error(`No alpha feature(${name}) is found.`);
313
+ }
314
+ const alphaFeatureOptInButton = alphaFeature.getByRole('button', {
315
+ name: 'Opt in to enable',
316
+ });
317
+ if (await alphaFeatureOptInButton.isVisible({ timeout: 10000 })) {
318
+ if (await alphaFeatureOptInButton.isEnabled()) {
319
+ await alphaFeatureOptInButton.click({ timeout: 90000 });
320
+ await (0, test_1.expect)(this.dialog.first()).toBeVisible({ timeout: 60000 });
321
+ await this.scrollToOptInCheckbox();
322
+ await this.optInAICheckbox.check({ timeout: 90000 });
323
+ await this.closeTermsDialog();
348
324
  }
349
- catch (error) {
350
- console.error(`Click attempt ${retries + 1} failed: ${error}`);
325
+ }
326
+ const toggle = alphaFeature.getByRole('switch').first();
327
+ await (0, expectLocatorWithRetry_1.expectLocatorWithRetry)(this.page, toggle, {
328
+ visibilityTimeout: 30000,
329
+ totalTimeout: 180000,
330
+ maxRetries: 5,
331
+ postAction: async () => {
351
332
  await this.page.reload();
352
- await (0, sleep_1.sleep)(10000);
353
- }
333
+ await this.clickSettingsTab();
334
+ },
335
+ });
336
+ if (await toggle.isChecked()) {
337
+ console.log(`Feature ${name} is already enabled.`);
338
+ return;
354
339
  }
355
- throw new Error(`Failed to eanble alpha feature ${name} after ${maxRetries} attempts.`);
340
+ await toggle.click();
341
+ await (0, test_1.expect)(toggle).toBeChecked({ timeout: 60000 });
342
+ }
343
+ async closeTermsDialog() {
344
+ const closeButton = this.dialog
345
+ .first()
346
+ .getByRole('button', { name: 'Close' });
347
+ if (await closeButton.isVisible({ timeout: 10000 }).catch(() => false)) {
348
+ await closeButton.click();
349
+ }
350
+ await (0, test_1.expect)(this.dialog.first()).toBeHidden({ timeout: 60000 });
356
351
  }
357
352
  async scrollToOptInCheckbox() {
358
- await this.page.locator('.ps-contract-scroll').evaluate((el) => {
359
- el.scrollTop = el.scrollHeight;
353
+ const dialog = this.dialog.first();
354
+ await (0, test_1.expect)(dialog).toBeVisible({ timeout: 30000 });
355
+ const contractScroll = this.page.locator('.ps-contract-scroll').first();
356
+ if (await contractScroll.isVisible({ timeout: 5000 }).catch(() => false)) {
357
+ await contractScroll.evaluate((el) => {
358
+ el.scrollTop = el.scrollHeight;
359
+ el.dispatchEvent(new Event('scroll', { bubbles: true }));
360
+ });
361
+ return;
362
+ }
363
+ const box = await dialog.boundingBox();
364
+ if (box) {
365
+ await this.page.mouse.move(box.x + box.width / 2, box.y + box.height * 0.6);
366
+ for (let i = 0; i < 20; i++) {
367
+ await this.page.mouse.wheel(0, 300);
368
+ }
369
+ }
370
+ await dialog.evaluate((dlg) => {
371
+ const all = [dlg, ...Array.from(dlg.querySelectorAll('*'))];
372
+ for (const node of all) {
373
+ if (!(node instanceof HTMLElement))
374
+ continue;
375
+ node.scrollTop = node.scrollHeight;
376
+ node.dispatchEvent(new Event('scroll', { bubbles: true }));
377
+ }
360
378
  });
361
379
  }
362
380
  async checkOptInCheckbox() {
@@ -388,15 +406,17 @@ class ConsoleOrganizationPage {
388
406
  await this.page.reload();
389
407
  },
390
408
  });
391
- try {
392
- await (0, test_1.expect)(this.optInButton).toBeVisible({ timeout: 30000 });
393
- await this.clickOptInButton();
394
- await this.scrollToOptInCheckbox();
395
- await this.checkOptInCheckbox();
396
- }
397
- catch {
398
- await (0, test_1.expect)(this.optInButton).not.toBeVisible();
409
+ if (!(await this.optInButton.isVisible({ timeout: 30000 }).catch(() => false))) {
410
+ return;
399
411
  }
412
+ await this.clickOptInButton();
413
+ await (0, test_1.expect)(this.dialog.first()).toBeVisible({ timeout: 60000 });
414
+ await this.scrollToOptInCheckbox();
415
+ await this.optInCheckbox.check({ timeout: 90000 });
416
+ await this.closeTermsDialog();
417
+ await this.page.reload();
418
+ await this.clickSettingsTab();
419
+ await (0, test_1.expect)(this.optInButton).not.toBeVisible({ timeout: 60000 });
400
420
  }
401
421
  async clickGroupsTab() {
402
422
  await this.groupsTab.click({ timeout: 60000 });
@@ -287,8 +287,17 @@ class ModelerCreatePage {
287
287
  this.processIdInput = page.getByLabel('ID', { exact: true });
288
288
  this.payloadNameInput = page.getByLabel('Full Name');
289
289
  this.payloadDateInput = page.getByLabel('Date of Birth');
290
- this.payloadCheckboxInput = this.form.getByLabel('Agree');
291
- this.payloadNumberInput = this.form.getByLabel('Count');
290
+ // Scoped to the deploy/run dialog and matched by role, not through the
291
+ // exact-class form container: the start form renders inside the dialog
292
+ // and `[class="fjs-container"]` only matches when that element carries
293
+ // no other class, so an extra class on the form root silently empties
294
+ // every locator built on it.
295
+ this.payloadCheckboxInput = this.dialog
296
+ .first()
297
+ .getByRole('checkbox', { name: 'Agree' });
298
+ this.payloadNumberInput = this.dialog
299
+ .first()
300
+ .getByRole('textbox', { name: 'Count' });
292
301
  this.formPropertySection = page.locator('[data-group-id="group-form"]');
293
302
  this.formLinkingTypeDropdown = page.getByLabel('Type');
294
303
  this.formLinkTypeOptions = page.locator('#bio-properties-panel-formType');
@@ -18,8 +18,7 @@ _8_10_1.test.describe('Cluster Setup Tests', () => {
18
18
  await (0, _setup_1.captureScreenshot)(page, testInfo);
19
19
  await (0, _setup_1.captureFailureVideo)(page, testInfo);
20
20
  });
21
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
22
- _8_10_1.test.skip('Enable Alpha Features', async ({ page, loginPage, consoleOrganizationsPage, homePage, }, testInfo) => {
21
+ (0, _8_10_1.test)('Enable Alpha Features', async ({ page, loginPage, consoleOrganizationsPage, homePage, }, testInfo) => {
23
22
  _8_10_1.test.skip(process.env.IS_PROD === 'true', 'Skipping test because not required on PROD test org');
24
23
  _8_10_1.test.skip(process.env.IS_AG === 'true', 'Skipping test because not required when IS_AG is true');
25
24
  await (0, UtilitiesPage_1.loginWithRetry)(page, loginPage, users_1.testUsers.mainUser, (testInfo.workerIndex + 1) * 1000);
@@ -35,8 +35,7 @@ _8_10_1.test.describe('Web Modeler User Flow Tests', () => {
35
35
  await (0, mailSlurpClient_1.deleteInbox)(inboxes[testInfo.title]);
36
36
  }
37
37
  });
38
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
39
- _8_10_1.test.skip('Form.js Integration with User Task and AI Generated Form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, consoleOrganizationsPage, loginPage, }, testInfo) => {
38
+ (0, _8_10_1.test)('Form.js Integration with User Task and AI Generated Form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, consoleOrganizationsPage, loginPage, }, testInfo) => {
40
39
  _8_10_1.test.slow();
41
40
  const randomString = await (0, _setup_1.generateRandomStringAsync)(3);
42
41
  const processName = 'User_Task_Process_With_AI_Form' + randomString;
@@ -75,7 +74,7 @@ _8_10_1.test.describe('Web Modeler User Flow Tests', () => {
75
74
  // identity-provider page, and if so signs back in before trying once
76
75
  // more (run 35562939552, "Camunda Modeler" banner absent 90s after 3
77
76
  // such retries).
78
- await (0, UtilitiesPage_1.withSessionRecovery)(page, loginPage, appsPage, modelerHomePage.modelerPageBanner, testUser, (testInfo.workerIndex + 1) * 1000, () => appsPage.openModelerWithRetry(modelerHomePage.modelerPageBanner, 90000, 3, modelerHomePage.createNewProjectButton));
77
+ await (0, UtilitiesPage_1.withSessionRecovery)(page, loginPage, appsPage, modelerHomePage.modelerPageBanner, testUser, (testInfo.workerIndex + 1) * 1000, () => appsPage.openModelerWithRetry(modelerHomePage.modelerPageBanner, 90000, 3, modelerHomePage.createNewProjectButton.or(modelerHomePage.createWorkspaceButton)));
79
78
  });
80
79
  await _8_10_1.test.step('Open Cross Component Test Project', async () => {
81
80
  await modelerHomePage.clickCrossComponentProjectFolder();
@@ -141,8 +140,7 @@ _8_10_1.test.describe('Web Modeler User Flow Tests', () => {
141
140
  await operateTabTaskDetailsPage.clickCompleteTaskButton();
142
141
  });
143
142
  });
144
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
145
- _8_10_1.test.skip('Form.js Integration with AI generated Start form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
143
+ (0, _8_10_1.test)('Form.js Integration with AI generated Start form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
146
144
  _8_10_1.test.slow();
147
145
  const randomString = await (0, _setup_1.generateRandomStringAsync)(3);
148
146
  const processName = 'AI-generated-Start-form' + randomString;
@@ -12,8 +12,7 @@ _8_7_1.test.describe('Cluster Setup Tests', () => {
12
12
  await (0, _setup_1.captureScreenshot)(page, testInfo);
13
13
  await (0, _setup_1.captureFailureVideo)(page, testInfo);
14
14
  });
15
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
16
- _8_7_1.test.skip('Enable Alpha Features', async ({ page, loginPage, consoleOrganizationsPage, homePage, }, testInfo) => {
15
+ (0, _8_7_1.test)('Enable Alpha Features', async ({ page, loginPage, consoleOrganizationsPage, homePage, }, testInfo) => {
17
16
  _8_7_1.test.skip(process.env.IS_PROD === 'true', 'Skipping test because not required on PROD test org');
18
17
  _8_7_1.test.skip(process.env.IS_AG === 'true', 'Skipping test because not required when IS_AG is true');
19
18
  await (0, UtilitiesPage_1.loginWithRetry)(page, loginPage, users_1.testUsers.mainUser, (testInfo.workerIndex + 1) * 1000);
@@ -42,9 +42,8 @@ _8_7_1.test.describe('Web Modeler User Flow Tests', () => {
42
42
  await (0, mailSlurpClient_1.deleteInbox)(inboxes[testInfo.title]);
43
43
  }
44
44
  });
45
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
46
45
  // Also tracked in https://github.com/camunda/product-hub/issues/3655
47
- _8_7_1.test.skip('Form.js Integration with User Task and AI Generated Form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
46
+ (0, _8_7_1.test)('Form.js Integration with User Task and AI Generated Form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
48
47
  _8_7_1.test.slow();
49
48
  const randomString = await (0, _setup_1.generateRandomStringAsync)(3);
50
49
  const processName = 'User_Task_Process_With_AI_Form' + randomString;
@@ -314,9 +313,8 @@ _8_7_1.test.describe('Web Modeler User Flow Tests', () => {
314
313
  });
315
314
  });
316
315
  });
317
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
318
316
  // Also tracked in https://github.com/camunda/product-hub/issues/3655
319
- _8_7_1.test.skip('Form.js Integration with AI generated Start form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
317
+ (0, _8_7_1.test)('Form.js Integration with AI generated Start form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
320
318
  _8_7_1.test.slow();
321
319
  const randomString = await (0, _setup_1.generateRandomStringAsync)(3);
322
320
  const processName = 'AI-generated-Start-form' + randomString;
@@ -18,8 +18,7 @@ _8_9_1.test.describe('Cluster Setup Tests', () => {
18
18
  await (0, _setup_1.captureScreenshot)(page, testInfo);
19
19
  await (0, _setup_1.captureFailureVideo)(page, testInfo);
20
20
  });
21
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
22
- _8_9_1.test.skip('Enable Alpha Features', async ({ page, loginPage, consoleOrganizationsPage, homePage, }, testInfo) => {
21
+ (0, _8_9_1.test)('Enable Alpha Features', async ({ page, loginPage, consoleOrganizationsPage, homePage, }, testInfo) => {
23
22
  _8_9_1.test.skip(process.env.IS_PROD === 'true', 'Skipping test because not required on PROD test org');
24
23
  _8_9_1.test.skip(process.env.IS_AG === 'true', 'Skipping test because not required when IS_AG is true');
25
24
  await (0, UtilitiesPage_1.loginWithRetry)(page, loginPage, users_1.testUsers.mainUser, (testInfo.workerIndex + 1) * 1000);
@@ -34,9 +34,8 @@ _8_9_1.test.describe('Web Modeler User Flow Tests', () => {
34
34
  await (0, mailSlurpClient_1.deleteInbox)(inboxes[testInfo.title]);
35
35
  }
36
36
  });
37
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
38
37
  // Also tracked in https://github.com/camunda/product-hub/issues/3655
39
- _8_9_1.test.skip('Form.js Integration with User Task and AI Generated Form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
38
+ (0, _8_9_1.test)('Form.js Integration with User Task and AI Generated Form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
40
39
  _8_9_1.test.slow();
41
40
  const randomString = await (0, _setup_1.generateRandomStringAsync)(3);
42
41
  const processName = 'User_Task_Process_With_AI_Form' + randomString;
@@ -94,9 +93,8 @@ _8_9_1.test.describe('Web Modeler User Flow Tests', () => {
94
93
  await operateTabTaskDetailsPage.clickCompleteTaskButton();
95
94
  });
96
95
  });
97
- // Skipped due to bug #29346: https://github.com/camunda/camunda-hub/issues/29346
98
96
  // Also tracked in https://github.com/camunda/product-hub/issues/3655
99
- _8_9_1.test.skip('Form.js Integration with AI generated Start form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
97
+ (0, _8_9_1.test)('Form.js Integration with AI generated Start form @ai-external', async ({ page, homePage, modelerHomePage, appsPage, modelerCreatePage, formJsPage, }) => {
100
98
  _8_9_1.test.slow();
101
99
  const randomString = await (0, _setup_1.generateRandomStringAsync)(3);
102
100
  const processName = 'AI-generated-Start-form' + randomString;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camunda/e2e-test-suite",
3
- "version": "0.0.1595",
3
+ "version": "0.0.1597",
4
4
  "description": "End-to-end test helpers for Camunda 8",
5
5
  "repository": {
6
6
  "type": "git",