@camunda/e2e-test-suite 0.0.427 → 0.0.429

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.
@@ -21,6 +21,7 @@ declare class IdentityTenantPage {
21
21
  readonly cancelButton: Locator;
22
22
  readonly dialog: Locator;
23
23
  readonly row: (name: string) => Locator;
24
+ readonly usersTab: Locator;
24
25
  constructor(page: Page);
25
26
  clickCreateTenantMainButton(): Promise<void>;
26
27
  clickCreateTenantSubButton(): Promise<void>;
@@ -27,11 +27,13 @@ class IdentityTenantPage {
27
27
  cancelButton;
28
28
  dialog;
29
29
  row;
30
+ usersTab;
30
31
  constructor(page) {
31
32
  this.page = page;
32
33
  this.createTenantMainButton = page.getByRole('button', {
33
34
  name: 'Create Tenant',
34
35
  });
36
+ this.usersTab = page.getByRole('tab', { name: 'Users' });
35
37
  this.enterTenantNameInput = page.getByPlaceholder('Enter tenant name');
36
38
  this.enterTenantIdInput = page.getByPlaceholder('Enter tenant ID');
37
39
  this.createTenantSubButton = page.getByRole('button', {
@@ -145,9 +147,25 @@ class IdentityTenantPage {
145
147
  await (0, sleep_1.sleep)(30000);
146
148
  }
147
149
  async clickTenant(tenantName) {
148
- const tenant = this.page.getByText(tenantName).first();
149
- await (0, expectLocatorWithPagination_1.expectLocatorWithPagination)(this.page, tenant);
150
- await tenant.click({ timeout: 30000 });
150
+ const maxRetries = 5;
151
+ for (let attempt = 1; attempt <= maxRetries; attempt++) {
152
+ try {
153
+ await this.page.waitForLoadState('domcontentloaded').catch(() => { });
154
+ const tenantRow = this.row(tenantName);
155
+ await (0, expectLocatorWithPagination_1.expectLocatorWithPagination)(this.page, tenantRow);
156
+ await tenantRow.locator('td').first().click({ timeout: 30000 });
157
+ await this.usersTab.waitFor({ state: 'visible', timeout: 30000 });
158
+ return;
159
+ }
160
+ catch (error) {
161
+ console.warn(`Attempt ${attempt} to click tenant '${tenantName}' failed. Retrying...`, error);
162
+ if (attempt === maxRetries) {
163
+ throw new Error(`Failed to click tenant '${tenantName}' after ${maxRetries} attempts.`);
164
+ }
165
+ await this.page.reload({ timeout: 30000 }).catch(() => { });
166
+ await (0, sleep_1.sleep)(3000);
167
+ }
168
+ }
151
169
  }
152
170
  async isRowVisible(name) {
153
171
  await (0, sleep_1.sleep)(1000);
@@ -188,12 +206,16 @@ class IdentityTenantPage {
188
206
  }
189
207
  async assignClientToTenant(clientName) {
190
208
  await this.clickAssignedApplicationsTab();
209
+ await (0, sleep_1.sleep)(3000);
191
210
  if (await this.isRowVisible(clientName)) {
192
211
  return;
193
212
  }
194
213
  await this.clickAssignApplicationsButton();
195
214
  await this.clickSearchApplicationsInput();
196
215
  await this.fillSearchApplicationsInput(clientName);
216
+ await (0, test_1.expect)(this.page.getByText(clientName, { exact: true })).toBeVisible({
217
+ timeout: 15000,
218
+ });
197
219
  await this.page.getByText(clientName, { exact: true }).click();
198
220
  await this.clickAssignApplicationsFinalButton();
199
221
  await (0, test_1.expect)(this.page.getByText('Applications assigned').first()).toBeVisible({
@@ -4,11 +4,12 @@ import { KeycloakLoginPage } from '../SM-8.9/KeycloakLoginPage';
4
4
  import { KeycloakAdminPage } from '../SM-8.9/KeycloakAdminPage';
5
5
  import { OCIdentityHomePage } from './OCIdentityHomePage';
6
6
  import { OCIdentityRolesPage } from './OCIdentityRolesPage';
7
+ import { IdentityTenantPage } from './IdentityTenantPage';
7
8
  export declare const keycloakAdminCredentials: () => {
8
9
  username: string;
9
10
  password: string;
10
11
  };
11
- export declare const setupKeycloakUser: (navigationPage: NavigationPage, identityPage: ManagementIdentityPage, keycloakLoginPage: KeycloakLoginPage, keycloakAdminPage: KeycloakAdminPage, ocIdentityHomePage: OCIdentityHomePage, ocIdentityRolesPage: OCIdentityRolesPage) => Promise<{
12
+ export declare const setupKeycloakUser: (navigationPage: NavigationPage, identityPage: ManagementIdentityPage, keycloakLoginPage: KeycloakLoginPage, keycloakAdminPage: KeycloakAdminPage, ocIdentityHomePage: OCIdentityHomePage, ocIdentityRolesPage: OCIdentityRolesPage, assignToDefaultTenant?: boolean, managementIdentityTenantPage?: IdentityTenantPage) => Promise<{
12
13
  testUsername: string;
13
14
  testPassword: string;
14
15
  }>;
@@ -1,6 +1,7 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.createKeycloakUser = exports.createUser = exports.setupKeycloakUser = exports.keycloakAdminCredentials = void 0;
4
+ const test_1 = require("@playwright/test");
4
5
  const keycloakAdminCredentials = () => {
5
6
  return {
6
7
  username: process.env.DISTRO_QA_E2E_TESTS_KEYCLOAK_USERNAME || 'admin',
@@ -8,13 +9,21 @@ const keycloakAdminCredentials = () => {
8
9
  };
9
10
  };
10
11
  exports.keycloakAdminCredentials = keycloakAdminCredentials;
11
- const setupKeycloakUser = async (navigationPage, identityPage, keycloakLoginPage, keycloakAdminPage, ocIdentityHomePage, ocIdentityRolesPage) => {
12
+ const setupKeycloakUser = async (navigationPage, identityPage, keycloakLoginPage, keycloakAdminPage, ocIdentityHomePage, ocIdentityRolesPage, assignToDefaultTenant = false, managementIdentityTenantPage) => {
12
13
  const testUsername = `test-user-${new Date().getTime()}-${Math.random()
13
14
  .toString(36)
14
15
  .substring(7)}`;
15
16
  const testPassword = 'test-password';
16
17
  await createKeycloakUser(navigationPage, keycloakLoginPage, keycloakAdminPage, testUsername, testPassword);
17
18
  await createIdentityUser(navigationPage, identityPage, testUsername);
19
+ if (assignToDefaultTenant && managementIdentityTenantPage) {
20
+ const userEmail = `qacamunda+${testUsername}@gmail.com`;
21
+ await navigationPage.goToManagementIdentity();
22
+ await (0, test_1.expect)(identityPage.usersLink).toBeVisible({ timeout: 10000 });
23
+ if (await identityPage.tenantTab.isVisible()) {
24
+ await managementIdentityTenantPage.assignUserToTenant('Default', testUsername, userEmail);
25
+ }
26
+ }
18
27
  await createOCUser(navigationPage, ocIdentityHomePage, ocIdentityRolesPage, testUsername);
19
28
  return { testUsername, testPassword };
20
29
  };
@@ -32,7 +32,10 @@ class ManagementIdentityPage {
32
32
  name: 'Camunda logo Management Identity',
33
33
  });
34
34
  this.usersLink = page.locator('a').filter({ hasText: 'Users' });
35
- this.tenantTab = page.getByRole('link', { name: 'Tenants' });
35
+ this.tenantTab = page
36
+ .getByRole('link', { name: 'Tenants' })
37
+ .or(page.locator('a').filter({ hasText: 'Tenants' }))
38
+ .first();
36
39
  this.assignedRolesTab = page.getByRole('tab', { name: 'Assigned roles' });
37
40
  this.demoUser = page.getByRole('cell', { name: 'demo' }).first();
38
41
  this.confirmDeleteButton = page.getByRole('button', {
@@ -0,0 +1,48 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const test_1 = require("@playwright/test");
4
+ const _8_10_1 = require("../../fixtures/8.10");
5
+ const UtilitiesPage_1 = require("../../pages/8.10/UtilitiesPage");
6
+ const _setup_1 = require("../../test-setup.js");
7
+ const apiHelpers_1 = require("../../utils/apiHelpers");
8
+ const sleep_1 = require("../../utils/sleep");
9
+ const users_1 = require("../../utils/users");
10
+ // fourteenthUser drives agentic AI (AWS Bedrock) tests on Test Cluster — reuse
11
+ const testUser = (0, users_1.getTestUser)('fourteenthUser');
12
+ let authToken;
13
+ _8_10_1.test.describe.configure({ mode: 'parallel' });
14
+ _8_10_1.test.describe('AWS Connectors User Flows', () => {
15
+ const clusterName = 'Test Cluster';
16
+ _8_10_1.test.beforeAll(async () => {
17
+ authToken = await (0, apiHelpers_1.authSaasAPI)();
18
+ });
19
+ _8_10_1.test.beforeEach(async ({ page, appsPage, loginPage }, testInfo) => {
20
+ await (0, UtilitiesPage_1.loginWithRetry)(page, loginPage, testUser, (testInfo.workerIndex + 1) * 1000);
21
+ await appsPage.clickCamundaApps();
22
+ await appsPage.clickOperate(clusterName);
23
+ });
24
+ _8_10_1.test.afterEach(async ({ page }, testInfo) => {
25
+ await (0, _setup_1.captureScreenshot)(page, testInfo);
26
+ await (0, _setup_1.captureFailureVideo)(page, testInfo);
27
+ });
28
+ (0, _8_10_1.test)('AWS Bedrock Knowledge Base - Retrieve relevant chunks from knowledge base', async ({ operateHomePage, operateProcessInstancePage, operateProcessesPage, }) => {
29
+ _8_10_1.test.slow();
30
+ const processKey = await (0, apiHelpers_1.deployProcess)('./resources/connectors/aws/bedrock-knowledge-base.bpmn', authToken);
31
+ if (processKey == null) {
32
+ throw new Error('Failed to deploy Bedrock KB process');
33
+ }
34
+ const instanceKey = await (0, apiHelpers_1.createProcessInstance)(String(processKey), authToken);
35
+ await _8_10_1.test.step('Process completes and retrievedChunks output variable is present', async () => {
36
+ await (0, sleep_1.sleep)(15000);
37
+ await operateHomePage.clickProcessesTab();
38
+ await operateProcessesPage.clickProcessCompletedCheckbox();
39
+ await operateProcessesPage.applyMoreFilters('Process Instance Key(s)', String(instanceKey));
40
+ await operateProcessesPage.clickProcessInstanceLink('AWS Bedrock Knowledge Base');
41
+ await operateProcessInstancePage.assertProcessCompleteStatusWithRetry();
42
+ // Assert retrievedChunks variable is present and contains at least one
43
+ // entry with a sourceUri (list with at least one entry containing a source URI)
44
+ await (0, test_1.expect)(operateProcessInstancePage.connectorResultVariableName('retrievedChunks')).toBeVisible({ timeout: 30000 });
45
+ await operateProcessInstancePage.assertProcessVariableContainsText('retrievedChunks', 'sourceUri');
46
+ });
47
+ });
48
+ });
@@ -40,6 +40,7 @@ _8_10_1.test.describe('Cluster Setup Tests', () => {
40
40
  await clusterSecretsPage.createSetOfSecrets(clusterName, connectorSecrets_1.gcpSecretsValues);
41
41
  await clusterSecretsPage.createSetOfSecrets(clusterName, connectorSecrets_1.azureSecretsValues);
42
42
  await clusterSecretsPage.createSetOfSecrets(clusterName, connectorSecrets_1.connectorSecretsValues);
43
+ await clusterSecretsPage.createSetOfSecrets(clusterName, connectorSecrets_1.bedrockKbSecretsValues);
43
44
  }
44
45
  });
45
46
  (0, _8_10_1.test)('Create AWS Cluster', async ({ page, loginPage, homePage, clusterPage, clusterDetailsPage, clusterSecretsPage, }, testInfo) => {
@@ -10,14 +10,14 @@ const resetSession_1 = require("../../utils/resetSession");
10
10
  const KeycloakUtils_1 = require("../../pages/SM-8.9/KeycloakUtils");
11
11
  const sleep_1 = require("../../utils/sleep");
12
12
  SM_8_9_1.test.describe.parallel('Smoke Tests', () => {
13
- SM_8_9_1.test.beforeEach(async ({ navigationPage, managementIdentityPage, keycloakLoginPage, keycloakAdminPage, page, browser, loginPage, ocIdentityHomePage, ocIdentityRolesPage, }, testInfo) => {
13
+ SM_8_9_1.test.beforeEach(async ({ navigationPage, managementIdentityPage, managementIdentityTenantPage, keycloakLoginPage, keycloakAdminPage, page, browser, loginPage, ocIdentityHomePage, ocIdentityRolesPage, }, testInfo) => {
14
14
  if (process.env.IS_MIGRATION === 'true') {
15
15
  await navigationPage.goToOCIdentity((testInfo.workerIndex + 1) * 1000);
16
16
  }
17
17
  else {
18
18
  console.log(`BeforeEach start: timeout = ${testInfo.timeout}`);
19
19
  (0, loggingUtils_1.setupTestLogging)(testInfo);
20
- const { testUsername, testPassword } = await (0, KeycloakUtils_1.setupKeycloakUser)(navigationPage, managementIdentityPage, keycloakLoginPage, keycloakAdminPage, ocIdentityHomePage, ocIdentityRolesPage);
20
+ const { testUsername, testPassword } = await (0, KeycloakUtils_1.setupKeycloakUser)(navigationPage, managementIdentityPage, keycloakLoginPage, keycloakAdminPage, ocIdentityHomePage, ocIdentityRolesPage, process.env.IS_OPTIMIZE !== 'false', managementIdentityTenantPage);
21
21
  console.log(`BeforeEach end: timeout = ${testInfo.timeout}`);
22
22
  await (0, resetSession_1.resetSession)(browser, page);
23
23
  await loginPage.login(testUsername, testPassword);
@@ -14,6 +14,10 @@ export declare const azureSecretsValues: {
14
14
  name: string;
15
15
  value: string;
16
16
  }[];
17
+ export declare const bedrockKbSecretsValues: {
18
+ name: string;
19
+ value: string;
20
+ }[];
17
21
  export declare const connectorSecretsValues: {
18
22
  name: string;
19
23
  value: string;
@@ -23,6 +27,10 @@ export declare const allConnectorSecrets: {
23
27
  name: string;
24
28
  value: string;
25
29
  }[];
30
+ BedrockKB: {
31
+ name: string;
32
+ value: string;
33
+ }[];
26
34
  GCP: {
27
35
  name: string;
28
36
  value: string;
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.allConnectorSecrets = exports.connectorSecretsValues = exports.azureSecretsValues = exports.gcpSecretsValues = exports.openAiSecretsValues = exports.awsSecretsValues = void 0;
3
+ exports.allConnectorSecrets = exports.connectorSecretsValues = exports.bedrockKbSecretsValues = exports.azureSecretsValues = exports.gcpSecretsValues = exports.openAiSecretsValues = exports.awsSecretsValues = void 0;
4
4
  exports.awsSecretsValues = [
5
5
  { name: 'IDP_AWS_REGION', value: process.env.IDP_AWS_REGION },
6
6
  { name: 'IDP_AWS_BUCKET_NAME', value: process.env.IDP_AWS_BUCKET_NAME },
@@ -121,6 +121,24 @@ exports.azureSecretsValues = [
121
121
  value: process.env.DB_VECTOR_AZURE_COSMOS_DB_CONTAINER,
122
122
  },
123
123
  ];
124
+ exports.bedrockKbSecretsValues = [
125
+ {
126
+ name: 'BEDROCK_KB_AWS_ACCESS_KEY',
127
+ value: process.env.BEDROCK_KB_AWS_ACCESS_KEY,
128
+ },
129
+ {
130
+ name: 'BEDROCK_KB_AWS_SECRET_KEY',
131
+ value: process.env.BEDROCK_KB_AWS_SECRET_KEY,
132
+ },
133
+ {
134
+ name: 'BEDROCK_KB_AWS_REGION',
135
+ value: process.env.BEDROCK_KB_AWS_REGION,
136
+ },
137
+ {
138
+ name: 'BEDROCK_KB_KNOWLEDGE_BASE_ID',
139
+ value: process.env.BEDROCK_KB_KNOWLEDGE_BASE_ID,
140
+ },
141
+ ];
124
142
  exports.connectorSecretsValues = [
125
143
  {
126
144
  name: 'endpoint_url',
@@ -131,6 +149,7 @@ exports.connectorSecretsValues = [
131
149
  ];
132
150
  exports.allConnectorSecrets = {
133
151
  AWS: exports.awsSecretsValues,
152
+ BedrockKB: exports.bedrockKbSecretsValues,
134
153
  GCP: exports.gcpSecretsValues,
135
154
  Azure: [...exports.azureSecretsValues, ...exports.openAiSecretsValues],
136
155
  Connectors: exports.connectorSecretsValues,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@camunda/e2e-test-suite",
3
- "version": "0.0.427",
3
+ "version": "0.0.429",
4
4
  "description": "End-to-end test helpers for Camunda 8",
5
5
  "repository": {
6
6
  "type": "git",