Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Everest-1717 | RBAC UI tests #951

Open
wants to merge 38 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
38 commits
Select commit Hold shift + click to select a range
5637dab
chore: test upgrades RBAC
fabio-silva Dec 10, 2024
0cf1000
chore: test cluster creation RBAC
fabio-silva Dec 10, 2024
b1569a6
chore: test cluster creation RBAC
fabio-silva Dec 10, 2024
37a5f82
chore: update playwright
fabio-silva Dec 10, 2024
df47088
chore: refactor mock request
fabio-silva Dec 11, 2024
ea8702f
chore: test DB actions
fabio-silva Dec 11, 2024
1d3b0e1
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 11, 2024
8716923
feat: add code commands to add namespaces
fabio-silva Dec 11, 2024
4f816bf
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 11, 2024
d1b6765
fix: bad routing on cluster details
fabio-silva Dec 19, 2024
f88114e
chore: test overview actions
fabio-silva Dec 19, 2024
bdeae1d
chore: use kubectl to change permissions on tests
fabio-silva Dec 19, 2024
747db1c
chore: apply kubectl for all permissions on tests
fabio-silva Dec 20, 2024
5c7323a
chore: test invisible actions
fabio-silva Dec 20, 2024
8c2deae
chore: remove unused var
fabio-silva Dec 20, 2024
7d0d674
chore: test backups
fabio-silva Dec 20, 2024
7bdccac
chore: test storages RBAC
fabio-silva Dec 20, 2024
3aa35d8
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 20, 2024
7622fcb
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 20, 2024
88cee8f
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 20, 2024
317a9df
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
mayankshah1607 Dec 20, 2024
26bdde1
chore: test schedules
fabio-silva Dec 20, 2024
0119a6f
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 20, 2024
a7e979e
Merge branch 'EVEREST-1717-rbac-ui-tests' of https://github.com/perco…
fabio-silva Dec 20, 2024
a739841
chore: further schedules RBAC tests
fabio-silva Dec 21, 2024
b9f5dbb
chore: test restores RBAC
fabio-silva Dec 22, 2024
e8adcc1
chore: further test restores RBAC
fabio-silva Dec 22, 2024
0f3eba5
chore: refactor e2e RBAC utils
fabio-silva Dec 22, 2024
ad48ebf
chore: rename setRBACPermissions fn
fabio-silva Dec 22, 2024
a278ce5
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 22, 2024
832acb4
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 23, 2024
47768b0
chore: simplify RBAC changes logic
fabio-silva Dec 23, 2024
9511cbc
Merge branch 'EVEREST-1717-rbac-ui-tests' of https://github.com/perco…
fabio-silva Dec 23, 2024
a092a55
chore: test new tests flow for RBAC
fabio-silva Dec 23, 2024
1cca599
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 24, 2024
6136cf3
chore: improve RBAC test flow
fabio-silva Dec 26, 2024
c8c05f6
fix: bash error
fabio-silva Dec 26, 2024
a257d3f
Merge branch 'main' into EVEREST-1717-rbac-ui-tests
fabio-silva Dec 26, 2024
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 6 additions & 0 deletions .github/workflows/dev-fe-e2e.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,10 @@ on:
required: true
CI_PASSWORD:
required: true
RBAC_USER:
required: true
RBAC_PASSWORD:
required: true

jobs:
e2e:
Expand Down Expand Up @@ -148,6 +152,8 @@ jobs:
EVEREST_LOCATION_URL: "https://minio.minio.svc.cluster.local"
CI_USER: "admin"
CI_PASSWORD: "${{ env.EVEREST_ADMIN_PASSWORD }}"
RBAC_USER: "rbac_user"
RBAC_PASSWORD: "rbac-e2e-test"
MONITORING_USER: "admin"
MONITORING_PASSWORD: "admin"
run: |
Expand Down
2 changes: 2 additions & 0 deletions .github/workflows/dev-fe-gatekeeper.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -129,6 +129,8 @@ jobs:
secrets:
CI_USER: everestadmin
CI_PASSWORD: everestadmin
RBAC_USER: rbac_user
RBAC_PASSWORD: rbac-e2e-test

merge-gatekeeper:
needs: [CI_checks, permission_checks, E2E_tests_workflow]
Expand Down
2 changes: 2 additions & 0 deletions ui/apps/everest/.e2e/.env.test
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,5 @@ MONITORING_USER="<MONITORING_USER>"
MONITORING_PASSWORD="<MONITORING_PASSWORD>"
CI_USER="<CI_USER>"
CI_PASSWORD="<CI_PASSWORD>"
RBAC_USER="<RBAC_USER>"
RBAC_PASSWORD="<RBAC_PASSWORD>"
1 change: 1 addition & 0 deletions ui/apps/everest/.e2e/.gitignore
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
tests-out
.env
user.json
old_rbac_permissions
39 changes: 34 additions & 5 deletions ui/apps/everest/.e2e/playwright.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ import { defineConfig } from '@playwright/test';
import path from 'path';
import { dirname } from 'path';
import { fileURLToPath } from 'url';
import { STORAGE_STATE_FILE, TIMEOUTS } from './constants';
import { STORAGE_STATE_FILE } from './constants';
import 'dotenv/config';

// Convert 'import.meta.url' to the equivalent __filename and __dirname
Expand Down Expand Up @@ -67,13 +67,13 @@ export default defineConfig({
/* Configure projects for major browsers */
projects: [
{
testDir: '.',
name: 'auth',
testDir: './setup',
testMatch: /auth.setup\.ts/,
},
{
testDir: '.',
name: 'setup',
testDir: './setup',
testMatch: /global.setup\.ts/,
teardown: 'teardown',
use: {
Expand All @@ -82,13 +82,41 @@ export default defineConfig({
dependencies: ['auth'],
},
{
testDir: '.',
name: 'teardown',
testDir: './teardown',
use: {
storageState: STORAGE_STATE_FILE,
},
testMatch: /global\.teardown\.ts/,
},
{
name: 'rbac-setup',
testDir: './setup',
testMatch: /rbac.setup\.ts/,
use: {
storageState: STORAGE_STATE_FILE,
},
dependencies: ['setup'],
},
{
name: 'rbac',
use: {
browserName: 'chromium',
channel: 'chrome',
storageState: STORAGE_STATE_FILE,
},
testDir: './pr/rbac',
dependencies: ['setup', 'rbac-setup'],
},
{
name: 'rbac-teardown',
testDir: './teardown',
testMatch: /rbac\.teardown\.ts/,
use: {
storageState: STORAGE_STATE_FILE,
},
dependencies: ['rbac'],
},
{
name: 'pr',
use: {
Expand All @@ -97,7 +125,8 @@ export default defineConfig({
storageState: STORAGE_STATE_FILE,
},
testDir: 'pr',
dependencies: ['setup'],
testIgnore: ['pr/rbac/**/*'],
dependencies: ['setup', 'rbac', 'rbac-teardown'],
},
{
name: 'release',
Expand Down
123 changes: 123 additions & 0 deletions ui/apps/everest/.e2e/pr/rbac/backups.e2e.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,123 @@
import { getTokenFromLocalStorage } from '@e2e/utils/localStorage';
import { getNamespacesFn } from '@e2e/utils/namespaces';
import { setRBACPermissionsK8S } from '@e2e/utils/rbac-cmd-line';
import { expect, test } from '@playwright/test';
import {
MOCK_CLUSTER_NAME,
mockBackups,
mockClusters,
mockStorages,
} from './utils';

test.describe('Backups RBAC', () => {
let namespace = '';
test.beforeAll(async ({ request }) => {
const token = await getTokenFromLocalStorage();
const namespaces = await getNamespacesFn(token, request);
namespace = namespaces[0];
console.log('Namespace:', namespace);
});

test('Hide Backups', async ({ page }) => {
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['backup-storages', '*', `${namespace}/*`],
['database-clusters', '*', `${namespace}/*`],
]);
await mockClusters(page, namespace);
await mockBackups(page, namespace);
await mockStorages(page, namespace);
await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}/backups`);
await expect(page.getByRole('table')).toBeVisible();
const rows = page.locator('.MuiTableRow-root:not(.MuiTableRow-head)');
expect(await rows.count()).toBe(0);
});

test('Show Backups', async ({ page }) => {
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['backup-storages', '*', `${namespace}/*`],
['database-clusters', '*', `${namespace}/*`],
['database-cluster-backups', 'read', `${namespace}/${MOCK_CLUSTER_NAME}`],
]);
await mockClusters(page, namespace);
await mockBackups(page, namespace);
await mockStorages(page, namespace);
await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}/backups`);
await expect(page.getByRole('table')).toBeVisible();
await expect(page.getByTestId('row-actions-menu-button')).not.toBeVisible();
const rows = page.locator('.MuiTableRow-root:not(.MuiTableRow-head)');
expect(await rows.count()).toBe(1);
});

test('Delete backup', async ({ page }) => {
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['backup-storages', '*', `${namespace}/*`],
['database-clusters', '*', `${namespace}/*`],
['database-cluster-backups', 'read', `${namespace}/${MOCK_CLUSTER_NAME}`],
[
'database-cluster-backups',
'delete',
`${namespace}/${MOCK_CLUSTER_NAME}`,
],
]);
await mockClusters(page, namespace);
await mockBackups(page, namespace);
await mockStorages(page, namespace);
await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}/backups`);
await expect(page.getByTestId('row-actions-menu-button')).toBeVisible();
await page.getByTestId('row-actions-menu-button').click();
await expect(page.getByText('Delete')).toBeVisible();
await expect(page.getByText('Restore to this DB')).not.toBeVisible();
await expect(page.getByText('Create new DB')).not.toBeVisible();
});

test('Create on-demand backup', async ({ page }) => {
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['backup-storages', '*', `${namespace}/*`],
['database-clusters', 'read', `${namespace}/*`],
[
'database-cluster-backups',
'create',
`${namespace}/${MOCK_CLUSTER_NAME}`,
],
]);
await mockClusters(page, namespace);
await mockBackups(page, namespace);
await mockStorages(page, namespace);
await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}/backups`);
await expect(page.getByTestId('menu-button')).toBeVisible();
await page.getByText('Create backup').click();
await expect(page.getByText('Now', { exact: true })).toBeVisible();
await expect(page.getByText('Schedule', { exact: true })).not.toBeVisible();
});

test('Create scheduled backup', async ({ page }) => {
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['backup-storages', '*', `${namespace}/*`],
['database-clusters', 'read', `${namespace}/*`],
['database-clusters', 'update', `${namespace}/*`],
[
'database-cluster-backups',
'create',
`${namespace}/${MOCK_CLUSTER_NAME}`,
],
]);
await mockClusters(page, namespace);
await mockBackups(page, namespace);
await mockStorages(page, namespace);
await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}/backups`);
await expect(page.getByTestId('menu-button')).toBeVisible();
await page.getByText('Create backup').click();
await expect(page.getByText('Schedule', { exact: true })).toBeVisible();
});
});
1;
113 changes: 113 additions & 0 deletions ui/apps/everest/.e2e/pr/rbac/clusters.e2e.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,113 @@
import { expect, test } from '@playwright/test';
import { mockEngines, MOCK_CLUSTER_NAME, mockClusters } from './utils';
import { getTokenFromLocalStorage } from '@e2e/utils/localStorage';
import { getNamespacesFn } from '@e2e/utils/namespaces';
import { setRBACPermissionsK8S } from '@e2e/utils/rbac-cmd-line';

const { CI_USER: user } = process.env;

test.describe('Clusters RBAC', () => {
let namespace = '';

test.beforeAll(async ({ request }) => {
const token = await getTokenFromLocalStorage();
const namespaces = await getNamespacesFn(token, request);
namespace = namespaces[0];
});

test('permitted cluster creation with present clusters', async ({ page }) => {
await mockEngines(page, namespace);
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['database-clusters', '*', `${namespace}/*`],
]);
await mockClusters(page, namespace);
await page.goto('/databases');
await expect(page.getByText('Create database')).toBeVisible();
await expect(page.getByText('Create database')).not.toBeDisabled();
});

test('permitted cluster creation without present clusters', async ({
page,
}) => {
await mockEngines(page, namespace);
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['database-clusters', '*', `${namespace}/*`],
]);
await page.goto('/databases');
await expect(page.getByText('Create database')).toBeVisible();
await expect(page.getByText('Create database')).not.toBeDisabled();
});

test('not permitted cluster creation with present clusters', async ({
page,
}) => {
await mockEngines(page, namespace);
await mockClusters(page, namespace);
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['database-clusters', 'read', `${namespace}/*`],
]);
await page.goto('/databases');
await expect(page.getByText('Create database')).not.toBeVisible();
});

test('not permitted cluster creation without present clusters', async ({
page,
}) => {
await mockEngines(page, namespace);
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['database-clusters', 'read', `${namespace}/*`],
]);
await page.goto('/databases');
await expect(page.getByText('Create database')).not.toBeVisible();
});

test('visible actions', async ({ page }) => {
await mockEngines(page, namespace);
await mockClusters(page, namespace);
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['database-clusters', '*', `${namespace}/${MOCK_CLUSTER_NAME}`],
]);
await page.goto('/databases');
await page.getByTestId('actions-menu-button').click();
await expect(page.getByText('Delete')).toBeVisible();
await expect(page.getByText('Suspend')).toBeVisible();
await expect(page.getByText('Restart')).toBeVisible();

await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}`);
await expect(
page.getByTestId('edit-advanced-configuration-db-btn')
).toBeVisible();
await expect(
page.getByTestId('edit-advanced-configuration-db-btn')
).not.toBeDisabled();
await expect(page.getByTestId('edit-resources-button')).toBeVisible();
await expect(page.getByTestId('edit-resources-button')).not.toBeDisabled();
});

test('not visible actions', async ({ page }) => {
await mockEngines(page, namespace);
await mockClusters(page, namespace);
await setRBACPermissionsK8S([
['namespaces', 'read', namespace],
['database-engines', '*', `${namespace}/*`],
['database-clusters', 'read', `${namespace}/${MOCK_CLUSTER_NAME}`],
]);
await page.goto('/databases');
await expect(page.getByTestId('actions-menu-button')).not.toBeVisible();
await page.goto(`/databases/${namespace}/${MOCK_CLUSTER_NAME}`);
await expect(
page.getByTestId('edit-advanced-configuration-db-btn')
).not.toBeVisible();
await expect(page.getByTestId('edit-resources-button')).toBeDisabled();
});
});
Loading
Loading