Skip to content

Commit

Permalink
ui/e2e: add e2e testing for statement bundles
Browse files Browse the repository at this point in the history
This commit adds some e2e cypress tests for statement
bundle features in DB Console:
* add tests for requesting, cancelling and viewing bundles
for privileged (VIEWACTIVITY, ADMIN) and non-privileged
users
* reformat cypress login command to use a new `users`
fixture that defines users by sql privilege
* add cypress command getUserWithExactPrivileges which
retrieves users from the fixture with the provided
privileges

Release note: None

Part of: cockroachdb#121301
  • Loading branch information
xinhaoz committed Aug 28, 2024
1 parent 3cb54eb commit b84b74c
Show file tree
Hide file tree
Showing 6 changed files with 166 additions and 6 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -8,9 +8,14 @@
// by the Apache License, Version 2.0, included in the file
// licenses/APL.txt.

import { SQLPrivilege } from "../../support/types";

describe("health check: authenticated user", () => {
it("serves a DB Console overview page", () => {
cy.login();
cy.getUserWithExactPrivileges([SQLPrivilege.ADMIN]);
cy.fixture("users").then((users) => {
cy.login(users[0].username, users[0].password);
});

// Ensure that something reasonable renders at / when authenticated, making
// just enough assertions to ensure the right page loaded. If this test
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
// Copyright 2024 The Cockroach Authors.
//
// Use of this software is governed by the Business Source License
// included in the file licenses/BSL.txt.
//
// As of the Change Date specified in that file, in accordance with
// the Business Source License, use of this software will be governed
// by the Apache License, Version 2.0, included in the file
// licenses/APL.txt.

import { SQLPrivilege } from "../../support/types";

// TODO (xinhaoz): This test currently only works when running pnpm run cy:run
// directly against a local cluster set up with sql activity in the last hour
// and the expected cypress users in fixtures. We need to automate this server
// setup for e2e testing.
describe("statement bundles", () => {
const runTestsForPrivilegedUser = (privilege: SQLPrivilege) => {
describe(`${privilege} user`, () => {
beforeEach(() => {
cy.getUserWithExactPrivileges([privilege]).then((user) => {
cy.login(user.username, user.password);
});
});

it("can request statement bundles", () => {
cy.visit("#/sql-activity");
cy.contains("button", "Apply").click();
// Open modal.
cy.contains("button", "Activate").click();
// Wait for modal.
cy.findByText(/activate statement diagnostics/i).should("be.visible");
// Click the Activate button within the modal
cy.get(`[role="dialog"]`) // Adjust this selector to match your modal's structure
.contains("button", "Activate")
.click();
cy.findByText(/statement diagnostics were successfully activated/i);
});

it("can view statement bundles", () => {
cy.visit("#/reports/statements/diagnosticshistory");
cy.get("table tbody tr").should("have.length.at.least", 1);
});

it("can cancel statement bundles", () => {
cy.visit("#/reports/statements/diagnosticshistory");
cy.get("table tbody tr").should("have.length.at.least", 1);
cy.contains("button", "Cancel").click();
cy.findByText(/statement diagnostics were successfully cancelled/i);
});
});
};

const runTestsForNonPrivilegedUser = (privilege?: SQLPrivilege) => {
beforeEach(() => {
cy.getUserWithExactPrivileges(privilege ? [privilege] : []).then(
(user) => {
cy.login(user.username, user.password);
},
);
});

it("cannot request statement bundles", () => {
cy.visit("#/sql-activity");
cy.contains("button", "Apply").click();
// Should not see an Activate button.
cy.contains("button", "Activate").should("not.exist");
});

it("cannot view statement bundles", () => {
cy.visit("#/reports/statements/diagnosticshistory");
cy.findByText(/no statement diagnostics to show/i);
});
};

describe("view activity user", () => {
runTestsForPrivilegedUser(SQLPrivilege.VIEWACTIVITY);
});

describe("admin user", () => {
runTestsForPrivilegedUser(SQLPrivilege.ADMIN);
});

describe("non-privileged VIEWACTIVITYREDACTED user", () => {
runTestsForNonPrivilegedUser(SQLPrivilege.VIEWACTIVITYREDACTED);
});

describe("non-privileged user", () => {
runTestsForNonPrivilegedUser();
});
});
28 changes: 28 additions & 0 deletions pkg/ui/workspaces/e2e-tests/cypress/fixtures/users.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
[
{
"username": "cypress",
"password": "tests",
"sqlPrivileges": [
"ADMIN"
]
},
{
"username": "va_user",
"password": "cypress",
"sqlPrivileges": [
"VIEWACTIVITY"
]
},
{
"username": "va_redacted_user",
"password": "cypress",
"sqlPrivileges": [
"VIEWACTIVITYREDACTED"
]
},
{
"username": "no_privs_user",
"password": "cypress",
"sqlPrivileges": []
}
]
18 changes: 15 additions & 3 deletions pkg/ui/workspaces/e2e-tests/cypress/support/commands.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,15 +9,16 @@
// licenses/APL.txt.

import "@testing-library/cypress/add-commands";
import { SQLPrivilege, User } from "./types";

Cypress.Commands.add("login", () => {
Cypress.Commands.add("login", (username: string, password: string) => {
cy.request({
method: "POST",
url: "/api/v2/login/",
form: true,
body: {
username: Cypress.env("username"),
password: Cypress.env("password"),
username: username,
password: password,
},
failOnStatusCode: true,
}).then(({ body }) => {
Expand All @@ -33,3 +34,14 @@ Cypress.Commands.add("login", () => {
}
});
});

// Gets a user from the users.json fixture with the given privileges.
Cypress.Commands.add("getUserWithExactPrivileges", (privs: SQLPrivilege[]) => {
return cy.fixture("users").then((users) => {
return users.find(
(user: User) =>
privs.every((priv) => user.sqlPrivileges.includes(priv)) ||
(privs.length === 0 && user.sqlPrivileges.length === 0),
);
});
});
6 changes: 4 additions & 2 deletions pkg/ui/workspaces/e2e-tests/cypress/support/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -24,6 +24,7 @@
// ***********************************************************

import "./commands";
import { SQLPrivilege, User } from "./types";

declare global {
// eslint-disable-next-line @typescript-eslint/no-namespace -- required for declaration merging
Expand All @@ -33,10 +34,11 @@ declare global {
* Sets a session cookie for the demo user on the current
* database.
* @example
* cy.login();
* cy.login("cypress", "tests");
* cy.visit("#/some/authenticated/route");
*/
login(): void;
login(username: string, password: string): Chainable<void>;
getUserWithExactPrivileges(privs: SQLPrivilege[]): Chainable<User>;
}
}
}
22 changes: 22 additions & 0 deletions pkg/ui/workspaces/e2e-tests/cypress/support/types.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,22 @@
// Copyright 2024 The Cockroach Authors.
//
// Use of this software is governed by the Business Source License
// included in the file licenses/BSL.txt.
//
// As of the Change Date specified in that file, in accordance with
// the Business Source License, use of this software will be governed
// by the Apache License, Version 2.0, included in the file
// licenses/APL.txt.

export enum SQLPrivilege {
ADMIN = "ADMIN",
VIEWACTIVITY = "VIEWACTIVITY",
VIEWACTIVITYREDACTED = "VIEWACTIVITYREDACTED",
NONE = "NONE",
}

export type User = {
username: string;
password: string;
sqlPrivileges: SQLPrivilege[];
};

0 comments on commit b84b74c

Please sign in to comment.