Skip to content

Commit

Permalink
Remove user from team (#5797)
Browse files Browse the repository at this point in the history
* AB#30150 add e2e test and new seed script

---------

Co-authored-by: Domenico Gemoli <dgemoli@redcross.nl>
  • Loading branch information
Piotrk39 and aberonni authored Sep 10, 2024
1 parent 29be836 commit 20a87ea
Show file tree
Hide file tree
Showing 11 changed files with 543 additions and 0 deletions.
64 changes: 64 additions & 0 deletions e2e/portalicious/pages/ProjectTeam.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,29 @@ import BasePage from './BasePage';
class ProjectTeam extends BasePage {
readonly page: Page;
readonly tableRows: Locator;
readonly addUserFormUsersDropdown: Locator;
readonly addUserFormChooseUserDropdown: Locator;
readonly addUserFormChooseRoleDropdown: Locator;
readonly addUserFormSubmitButton: Locator;
readonly removeUserButton: Locator;

constructor(page: Page) {
super(page);
this.page = page;
this.tableRows = this.page.locator('table tbody tr');
this.addUserFormUsersDropdown = this.page.getByRole('option');
this.addUserFormChooseUserDropdown = this.page.locator(
`[formControlName="userValue"]`,
);
this.addUserFormChooseRoleDropdown = this.page.locator(
`[formControlName="rolesValue"]`,
);
this.addUserFormSubmitButton = this.page.getByRole('button', {
name: 'Submit',
});
this.removeUserButton = this.page.getByRole('button', {
name: 'Remove user',
});
}

async validateAssignedTeamMembers(expectedAssignedUsers: string[]) {
Expand All @@ -28,6 +46,52 @@ class ProjectTeam extends BasePage {

expect(sortedActualUsers).toEqual(sortedExpectedUsers);
}

async openAddUserForm() {
await this.page.getByRole('button', { name: 'Add team member' }).click();
}

async addUserToTeam({
userSearchPhrase,
userEmail,
role,
}: {
userSearchPhrase: string;
userEmail: string;
role: string;
}) {
await this.addUserFormChooseUserDropdown.click();
await this.addUserFormChooseUserDropdown.fill(userSearchPhrase);
await this.page.getByText(userEmail).click();
await this.addUserFormChooseRoleDropdown.click();
await this.page.getByText(role).click();
await this.addUserFormSubmitButton.click();
}

async validateAvailableSystemUsers(expectedAssignedUsers: string[]) {
await this.addUserFormChooseUserDropdown.click();
const actualAssignedUsers = await this.addUserFormUsersDropdown.evaluateAll(
(options) => options.map((option) => option.textContent.trim()),
);

const sortedActualUsers = [...actualAssignedUsers].sort((a, b) =>
a.localeCompare(b),
);
const sortedExpectedUsers = [...expectedAssignedUsers].sort((a, b) =>
a.localeCompare(b),
);

expect(sortedActualUsers).toEqual(sortedExpectedUsers);
}

async removeUserFromTeam({ userEmail }: { userEmail: string }) {
await this.page
.getByRole('row', { name: userEmail })
.getByRole('button')
.click();
await this.page.getByLabel('Remove user').click();
await this.removeUserButton.click();
}
}

export default ProjectTeam;
Original file line number Diff line number Diff line change
@@ -0,0 +1,52 @@
import BasePage from '@121-e2e/portalicious/pages/BasePage';
import LoginPage from '@121-e2e/portalicious/pages/LoginPage';
import ProjectTeam from '@121-e2e/portalicious/pages/ProjectTeam';
import { SeedScript } from '@121-service/src/scripts/seed-script.enum';
import { resetDB } from '@121-service/test/helpers/utility.helper';
import { test } from '@playwright/test';

const expectedAssignedUsers = ['admin@example.org'];
const expectedAvailablesystemUsers = [
'program-admin@example.org',
'view-user@example.org',
'kobo-user@example.org',
'cva-manager@example.org',
'cva-officer@example.org',
'finance-manager@example.org',
'finance-officer@example.org',
'view-no-pii@example.org',
];

test.beforeEach(async ({ page }) => {
await resetDB(SeedScript.oneAdmin);

// Login
const loginPage = new LoginPage(page);
await page.goto('/');
await loginPage.login(
process.env.USERCONFIG_121_SERVICE_EMAIL_ADMIN,
process.env.USERCONFIG_121_SERVICE_PASSWORD_ADMIN,
);
});

test('[29758] All system-users are available to be added to a "project team"', async ({
page,
}) => {
const basePage = new BasePage(page);
const manageTeam = new ProjectTeam(page);
const projectTitle = 'Cash program Warsaw';

await test.step('Select program and navigate to Manage team', async () => {
await basePage.selectProgram(projectTitle);
await basePage.navigateToProgramPage('Team');
});

await test.step('Validate assigned users are visible', async () => {
await manageTeam.validateAssignedTeamMembers(expectedAssignedUsers);
});

await test.step('Validate available system users are visible', async () => {
await manageTeam.openAddUserForm();
await manageTeam.validateAvailableSystemUsers(expectedAvailablesystemUsers);
});
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import BasePage from '@121-e2e/portalicious/pages/BasePage';
import LoginPage from '@121-e2e/portalicious/pages/LoginPage';
import ProjectTeam from '@121-e2e/portalicious/pages/ProjectTeam';
import { SeedScript } from '@121-service/src/scripts/seed-script.enum';
import { resetDB } from '@121-service/test/helpers/utility.helper';
import { test } from '@playwright/test';

const expectedAssignedUsers = ['admin@example.org', 'cva-officer@example.org'];
const userSearchPhrase = 'cva-officer';
const userFullEmail = 'cva-officer@example.org';
const userRole = 'Only CREATE registrations';

test.beforeEach(async ({ page }) => {
await resetDB(SeedScript.oneAdmin);

// Login
const loginPage = new LoginPage(page);
await page.goto('/');
await loginPage.login(
process.env.USERCONFIG_121_SERVICE_EMAIL_ADMIN,
process.env.USERCONFIG_121_SERVICE_PASSWORD_ADMIN,
);
});

test('[29759] Assign successfully roles to a user ', async ({ page }) => {
const basePage = new BasePage(page);
const manageTeam = new ProjectTeam(page);
const projectTitle = 'Cash program Warsaw';

await test.step('Select program and navigate to Manage team', async () => {
await basePage.selectProgram(projectTitle);
await basePage.navigateToProgramPage('Team');
});

await test.step('Validate available system users are visible', async () => {
await manageTeam.openAddUserForm();
await manageTeam.addUserToTeam({
userSearchPhrase: userSearchPhrase,
userEmail: userFullEmail,
role: userRole,
});
await manageTeam.validateToastMessage('User added');
await manageTeam.validateAssignedTeamMembers(expectedAssignedUsers);
});
});
59 changes: 59 additions & 0 deletions e2e/portalicious/tests/ManageTeam/RemoveUserFromTeam.spec.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
import BasePage from '@121-e2e/portalicious/pages/BasePage';
import LoginPage from '@121-e2e/portalicious/pages/LoginPage';
import ProjectTeam from '@121-e2e/portalicious/pages/ProjectTeam';
import { SeedScript } from '@121-service/src/scripts/seed-script.enum';
import { resetDB } from '@121-service/test/helpers/utility.helper';
import { test } from '@playwright/test';

const expectedInitialAssignedUsers = [
'admin@example.org',
'program-admin@example.org',
'view-user@example.org',
'kobo-user@example.org',
'cva-manager@example.org',
'cva-officer@example.org',
'finance-manager@example.org',
'finance-officer@example.org',
'view-no-pii@example.org',
];
const userToRemove = 'view-no-pii@example.org';
const expectedFinalAssignedUsers = expectedInitialAssignedUsers.filter(
(email) => email !== userToRemove,
);

test.beforeEach(async ({ page }) => {
await resetDB(SeedScript.test);

// Login
const loginPage = new LoginPage(page);
await page.goto('/');
await loginPage.login(
process.env.USERCONFIG_121_SERVICE_EMAIL_ADMIN,
process.env.USERCONFIG_121_SERVICE_PASSWORD_ADMIN,
);
});

test('[29760] Users should be removable from "project team"', async ({
page,
}) => {
const basePage = new BasePage(page);
const manageTeam = new ProjectTeam(page);
const projectTitle = 'Cash program Westeros';

await test.step('Select program and navigate to Manage team', async () => {
await basePage.selectProgram(projectTitle);
await basePage.navigateToProgramPage('Team');
});

await test.step('Validate assigned users are visible', async () => {
await manageTeam.validateAssignedTeamMembers(expectedInitialAssignedUsers);
});

await test.step('Validate available system users are visible', async () => {
await manageTeam.removeUserFromTeam({
userEmail: userToRemove,
});
await manageTeam.validateToastMessage('User removed');
await manageTeam.validateAssignedTeamMembers(expectedFinalAssignedUsers);
});
});
4 changes: 4 additions & 0 deletions services/121-service/src/scripts/scripts.controller.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,6 +9,7 @@ import { SeedProgramDrc } from '@121-service/src/scripts/seed-program-drc';
import { SeedNLProgramPV } from '@121-service/src/scripts/seed-program-nlrc-pv';
import { SeedTestProgram } from '@121-service/src/scripts/seed-program-test';
import { SeedTestMultipleProgram } from '@121-service/src/scripts/seed-program-test-multiple';
import { SeedTestOneAdmin } from '@121-service/src/scripts/seed-program-test-one-admin';
import { SeedProgramValidation } from '@121-service/src/scripts/seed-program-validation';
import { SeedScript } from '@121-service/src/scripts/seed-script.enum';
import { WrapperType } from '@121-service/src/wrapper.type';
Expand Down Expand Up @@ -36,6 +37,7 @@ export class ScriptsController {
private readonly seedProgramNlrcPv: SeedNLProgramPV,
private readonly seedProgramTestMultiple: SeedTestMultipleProgram,
private readonly seedProgramTest: SeedTestProgram,
private readonly seedProgramOneAdmin: SeedTestOneAdmin,
private readonly seedProgramValidation: SeedProgramValidation,
private readonly seedInit: SeedInit,
private readonly scriptsService: ScriptsService,
Expand Down Expand Up @@ -110,6 +112,8 @@ export class ScriptsController {
await this.seedDemoProgram.run(isApiTests);
} else if (script == SeedScript.test) {
await this.seedProgramTest.run(isApiTests);
} else if (script == SeedScript.oneAdmin) {
await this.seedProgramOneAdmin.run(isApiTests);
} else if (script == SeedScript.testMultiple) {
await this.seedProgramTestMultiple.run(isApiTests);
} else if (script == SeedScript.nlrcMultiple) {
Expand Down
2 changes: 2 additions & 0 deletions services/121-service/src/scripts/scripts.module.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,6 +16,7 @@ import { SeedProgramDrc } from '@121-service/src/scripts/seed-program-drc';
import { SeedNLProgramPV } from '@121-service/src/scripts/seed-program-nlrc-pv';
import { SeedTestProgram } from '@121-service/src/scripts/seed-program-test';
import { SeedTestMultipleProgram } from '@121-service/src/scripts/seed-program-test-multiple';
import { SeedTestOneAdmin } from '@121-service/src/scripts/seed-program-test-one-admin';
import { SeedProgramValidation } from '@121-service/src/scripts/seed-program-validation';
import { CustomHttpService } from '@121-service/src/shared/services/custom-http.service';
import { AxiosCallsService } from '@121-service/src/utils/axios/axios-calls.service';
Expand Down Expand Up @@ -44,6 +45,7 @@ import { TypeOrmModule, TypeOrmModuleOptions } from '@nestjs/typeorm';
SeedMultipleNLRCMockData,
SeedProgramDrc,
SeedTestProgram,
SeedTestOneAdmin,
SeedTestMultipleProgram,
SeedMockHelper,
AxiosCallsService,
Expand Down
80 changes: 80 additions & 0 deletions services/121-service/src/scripts/seed-helper.ts
Original file line number Diff line number Diff line change
Expand Up @@ -109,6 +109,86 @@ export class SeedHelper {
await this.assignAdminUserToProgram(program.id);
}

public async addOneDefaultAdminUser(
program: ProgramEntity,
debugScopeUsers: string[] = [],
): Promise<void> {
const users = [
{
type: 'programAdminUser',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_PROGRAM_ADMIN,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_PROGRAM_ADMIN,
roles: [DefaultUserRole.ProgramAdmin],
},
{
type: 'viewOnlyUser',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_USER_VIEW,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_USER_VIEW,
roles: [DefaultUserRole.View],
},
{
type: 'koboUser',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_USER_KOBO,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_USER_KOBO,
roles: [DefaultUserRole.KoboUser],
},
{
type: 'cvaManager',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_CVA_MANAGER,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_CVA_MANAGER,
roles: [DefaultUserRole.CvaManager],
},
{
type: 'cvaOfficer',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_CVA_OFFICER,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_CVA_OFFICER,
roles: [DefaultUserRole.CvaOfficer],
},
{
type: 'financeManager',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_FINANCE_MANAGER,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_FINANCE_MANAGER,
roles: [DefaultUserRole.FinanceManager],
},
{
type: 'financeOfficer',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_FINANCE_OFFICER,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_FINANCE_OFFICER,
roles: [DefaultUserRole.FinanceOfficer],
},
{
type: 'ViewWithoutPII',
username: process.env.USERCONFIG_121_SERVICE_EMAIL_VIEW_WITHOUT_PII,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_VIEW_WITHOUT_PII,
roles: [DefaultUserRole.ViewWithoutPII],
},
];

for (const user of users) {
await this.getOrSaveUser(user);
}

if (debugScopeUsers && DEBUG) {
for (const debugScopeUser of debugScopeUsers) {
const scopedUser = await this.getOrSaveUser({
type: 'debugScopedUser',
username: `${debugScopeUser}@example.org`,
password: process.env.USERCONFIG_121_SERVICE_PASSWORD_PROGRAM_ADMIN,
});
if (scopedUser) {
await this.assignAidworker(
scopedUser.id,
program.id,
[DefaultUserRole.Admin],
debugScopeUser,
);
}
}
}

await this.assignAdminUserToProgram(program.id);
}

public async getOrSaveUser(userInput: {
type: string;
username?: string;
Expand Down
24 changes: 24 additions & 0 deletions services/121-service/src/scripts/seed-program-test-one-admin.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
import { InterfaceScript } from '@121-service/src/scripts/scripts.module';
import { SeedHelper } from '@121-service/src/scripts/seed-helper';
import messageTemplateTest from '@121-service/src/seed-data/message-template/message-template-test.json';
import organizationAdmin from '@121-service/src/seed-data/organization/organization-one-admin.json';
import programTest from '@121-service/src/seed-data/program/program-test-one-admin.json';
import { Injectable } from '@nestjs/common';

@Injectable()
export class SeedTestOneAdmin implements InterfaceScript {
public constructor(private readonly seedHelper: SeedHelper) {}

public async run(isApiTests = false): Promise<void> {
// ***** CREATE PROGRAM *****
const program = await this.seedHelper.addProgram(programTest, isApiTests);

// ***** CREATE MESSAGE TEMPLATES *****
await this.seedHelper.addMessageTemplates(messageTemplateTest, program);

await this.seedHelper.addOneDefaultAdminUser(program);

// ***** CREATE ORGANIZATION *****
await this.seedHelper.addOrganization(organizationAdmin);
}
}
Loading

0 comments on commit 20a87ea

Please sign in to comment.