From cb2b861032ffbe6da489cf1973ee484da898a8f6 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Tue, 22 Nov 2022 16:52:56 +0000 Subject: [PATCH 01/43] Add User endpoints --- .../internal-api/TestConfiguration/index.ts | 3 + .../TestConfiguration/userManagement.ts | 43 ++++++++++++ .../internal-api/fixtures/userManagement.ts | 67 +++++++++++++++++++ .../userManagement/userManagement.spec.ts | 24 +++++++ 4 files changed, 137 insertions(+) create mode 100644 qa-core/src/config/internal-api/TestConfiguration/userManagement.ts create mode 100644 qa-core/src/config/internal-api/fixtures/userManagement.ts create mode 100644 qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts diff --git a/qa-core/src/config/internal-api/TestConfiguration/index.ts b/qa-core/src/config/internal-api/TestConfiguration/index.ts index ab996f7144..8ce5e94bc3 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/index.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/index.ts @@ -4,6 +4,7 @@ import InternalAPIClient from "./InternalAPIClient" import TablesApi from "./tables" import RowApi from "./rows" import ScreenApi from "./screens" +import UserManagementApi from "./userManagement" export default class TestConfiguration { applications: ApplicationApi @@ -12,6 +13,7 @@ export default class TestConfiguration { context: T tables: TablesApi rows: RowApi + userManagement: UserManagementApi constructor(apiClient: InternalAPIClient) { this.applications = new ApplicationApi(apiClient) @@ -19,6 +21,7 @@ export default class TestConfiguration { this.rows = new RowApi(apiClient) this.auth = new AuthApi(apiClient) this.screen = new ScreenApi(apiClient) + this.userManagement = new UserManagementApi(apiClient) this.context = {} } diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts new file mode 100644 index 0000000000..3a66049fd0 --- /dev/null +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -0,0 +1,43 @@ +import { Response } from "node-fetch" +import { User } from "@budibase/types" +import InternalAPIClient from "./InternalAPIClient" +import { responseMessage } from "../fixtures/types/responseMessage" + +export default class UserManagementApi { + api: InternalAPIClient + + constructor(apiClient: InternalAPIClient) { + this.api = apiClient + } + + async searchUsers(): Promise<[Response, User[]]> { + const response = await this.api.post(`/global/users/search`, {}) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json.length).toBeGreaterThan(0) + return [response, json] + } + + async getSelf(): Promise<[Response, User]> { + const response = await this.api.get(`/global/self`) + const json = await response.json() + expect(response).toHaveStatusCode(200) + return [response, json] + } + + async getAllUsers(): Promise<[Response, User]> { + const response = await this.api.get(`/global/users`) + const json = await response.json() + expect(response).toHaveStatusCode(200) + return [response, json] + } + + async inviteUsers(body: User[]): Promise<[Response, responseMessage]> { + const response = await this.api.post(`/global/users/multi/invite`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json.successful.length).toEqual(body.length) + expect(json.unsuccessful.length).toEqual(0) + return [response, json] + } +} diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts new file mode 100644 index 0000000000..ce15eb08e8 --- /dev/null +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -0,0 +1,67 @@ +import generator from "../../generator"; + +const randomId = generator.guid; +export const generateDeveloper = (): any => ({ + create: { + users: [{ + email: `pedro+${randomId()}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + builder: { + global: true + } + }], + groups: [] + } +}) + +export const generateAdmin = (): any => ({ + create: { + users: [{ + email: `pedro+${randomId()}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + admin: { + global: true + }, + builder: { + global: true + } + }], + groups: [] + } +}) +export const generateAppUser = (): any => ({ + create: { + users: [{ + email: `pedro+${randomId()}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + admin: { + global: false + }, + builder: { + global: false + } + }], + groups: [] + } +}) + +export const generateInviteUser = (): any => ( + [{ + email: `pedro+${randomId()}@budibase.com`, + userInfo: { + admin: { + global: true + }, + builder: { + global: true + }, + userGroups: [] + } + }] +) \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts new file mode 100644 index 0000000000..67fee8e53d --- /dev/null +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -0,0 +1,24 @@ +import TestConfiguration from "../../../config/internal-api/TestConfiguration" +import { Application } from "@budibase/server/api/controllers/public/mapping/types" +import { db } from "@budibase/backend-core" +import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" +import generateApp from "../../../config/internal-api/fixtures/applications" +import generator from "../../../config/generator" +import generateScreen from "../../../config/internal-api/fixtures/screens" + +describe("Internal API - User Management", () => { + const api = new InternalAPIClient() + const config = new TestConfiguration(api) + + beforeAll(async () => { + await config.beforeAll() + }) + + afterAll(async () => { + await config.afterAll() + }) + + it("Get all users", async () => { + await config.userManagement.searchUsers() + }) +}) From 7f8e093a52727ff8273335bf2131ee094441e7b1 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Mon, 28 Nov 2022 22:13:07 +0000 Subject: [PATCH 02/43] Add verification --- .../TestConfiguration/userManagement.ts | 22 +++++++++++++++++-- 1 file changed, 20 insertions(+), 2 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 3a66049fd0..2ff9450939 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -1,5 +1,5 @@ import { Response } from "node-fetch" -import { User } from "@budibase/types" +import { User, UserDeletedEvent } from "@budibase/types" import InternalAPIClient from "./InternalAPIClient" import { responseMessage } from "../fixtures/types/responseMessage" @@ -14,7 +14,8 @@ export default class UserManagementApi { const response = await this.api.post(`/global/users/search`, {}) const json = await response.json() expect(response).toHaveStatusCode(200) - expect(json.length).toBeGreaterThan(0) + expect(json.data.length).toBeGreaterThan(0) + expect(json.hasNextPage).toBe(false) return [response, json] } @@ -40,4 +41,21 @@ export default class UserManagementApi { expect(json.unsuccessful.length).toEqual(0) return [response, json] } + + async deleteUser(userId: string): Promise<[Response, responseMessage]> { + const body = { + delete: { + userIds: [ + userId + ] + } + } + const response = await this.api.post(`/global/users/bulk`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json.deleted.successful.length).toEqual(1) + expect(json.deleted.unsuccessful.length).toEqual(0) + expect(json.deleted.successful[0].userId).toEqual(userId) + return [response, json] + } } From b9186cac9d3e45455b0627dd31f448a844422d9a Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Wed, 30 Nov 2022 11:02:11 +0000 Subject: [PATCH 03/43] Add tests for user management --- .../TestConfiguration/userManagement.ts | 31 +++-- .../internal-api/fixtures/userManagement.ts | 115 ++++++++++-------- .../userManagement/userManagement.spec.ts | 19 ++- 3 files changed, 103 insertions(+), 62 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 2ff9450939..17fe5e0b0f 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -1,5 +1,5 @@ import { Response } from "node-fetch" -import { User, UserDeletedEvent } from "@budibase/types" +import { Role, User, UserDeletedEvent } from "@budibase/types" import InternalAPIClient from "./InternalAPIClient" import { responseMessage } from "../fixtures/types/responseMessage" @@ -15,7 +15,6 @@ export default class UserManagementApi { const json = await response.json() expect(response).toHaveStatusCode(200) expect(json.data.length).toBeGreaterThan(0) - expect(json.hasNextPage).toBe(false) return [response, json] } @@ -26,19 +25,20 @@ export default class UserManagementApi { return [response, json] } - async getAllUsers(): Promise<[Response, User]> { + async getAllUsers(): Promise<[Response, User[]]> { const response = await this.api.get(`/global/users`) const json = await response.json() expect(response).toHaveStatusCode(200) + expect(json.length).toBeGreaterThan(0) return [response, json] } - async inviteUsers(body: User[]): Promise<[Response, responseMessage]> { - const response = await this.api.post(`/global/users/multi/invite`, { body }) + async addUsers(body: any): Promise<[Response, responseMessage]> { + const response = await this.api.post(`/global/users/bulk`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) - expect(json.successful.length).toEqual(body.length) - expect(json.unsuccessful.length).toEqual(0) + expect(json.created.unsuccessful.length).toEqual(0) + expect(json.created.successful.length).toEqual(body.create.users.length) return [response, json] } @@ -58,4 +58,21 @@ export default class UserManagementApi { expect(json.deleted.successful[0].userId).toEqual(userId) return [response, json] } + + async inviteUser(body: any): Promise<[Response, responseMessage]> { + const response = await this.api.post(`/global/users/multi/invite`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json.created.successful.length).toEqual(body.length) + expect(json.created.unsuccessful.length).toEqual(0) + return [response, json] + } + + async getRoles(): Promise<[Response, Role[]]> { + const response = await this.api.get(`/roles`) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json.length).toEqual(4) + return [response, json] + } } diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index ce15eb08e8..6ada85bb49 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -1,59 +1,69 @@ import generator from "../../generator"; -const randomId = generator.guid; -export const generateDeveloper = (): any => ({ - create: { - users: [{ - email: `pedro+${randomId()}@budibase.com`, - password: randomId, - roles: {}, - forceResetPassword: true, - builder: { - global: true - } - }], - groups: [] - } -}) +export const generateDeveloper = (): Object => { + const randomId = generator.guid(); + return ({ + create: { + users: [{ + email: `pedro+${randomId}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + builder: { + global: true + } + }], + groups: [] + } + }) +} -export const generateAdmin = (): any => ({ - create: { - users: [{ - email: `pedro+${randomId()}@budibase.com`, - password: randomId, - roles: {}, - forceResetPassword: true, - admin: { - global: true - }, - builder: { - global: true - } - }], - groups: [] +export const generateAdmin = (): Object => { + const randomId = generator.guid(); + return ({ + create: { + users: [{ + email: `pedro+${randomId}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + admin: { + global: true + }, + builder: { + global: true + } + }], + groups: [] + } + }) +} +export const generateAppUser = (): Object => { + const randomId = generator.guid(); + const user = { + create: { + users: [{ + email: `pedro+${randomId}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + admin: { + global: false + }, + builder: { + global: false + } + }], + groups: [] + } } -}) -export const generateAppUser = (): any => ({ - create: { - users: [{ - email: `pedro+${randomId()}@budibase.com`, - password: randomId, - roles: {}, - forceResetPassword: true, - admin: { - global: false - }, - builder: { - global: false - } - }], - groups: [] - } -}) + return user +} -export const generateInviteUser = (): any => ( - [{ - email: `pedro+${randomId()}@budibase.com`, +export const generateInviteUser = (): Object[] => { + const randomId = generator.guid(); + return [{ + email: `pedro+${randomId}@budibase.com`, userInfo: { admin: { global: true @@ -64,4 +74,5 @@ export const generateInviteUser = (): any => ( userGroups: [] } }] -) \ No newline at end of file + +} \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 67fee8e53d..62d27ec2a4 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -4,9 +4,9 @@ import { db } from "@budibase/backend-core" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" import generateApp from "../../../config/internal-api/fixtures/applications" import generator from "../../../config/generator" -import generateScreen from "../../../config/internal-api/fixtures/screens" +import { generateAdmin, generateAppUser, generateDeveloper, generateInviteUser } from "../../../config/internal-api/fixtures/userManagement" -describe("Internal API - User Management", () => { +describe("Internal API - User Management & Permissions", () => { const api = new InternalAPIClient() const config = new TestConfiguration(api) @@ -18,7 +18,20 @@ describe("Internal API - User Management", () => { await config.afterAll() }) - it("Get all users", async () => { + it("Add Users with different roles", async () => { await config.userManagement.searchUsers() + await config.userManagement.getRoles() + + const [adminResponse, adminData] = await config.userManagement.addUsers(generateAdmin()) + const [devResponse, devData] = await config.userManagement.addUsers(generateDeveloper()) + const [userResponse, userData] = await config.userManagement.addUsers(generateAppUser()) + + const [invitedUserResponse, invitedUserData] = await config.userManagement.addUsers(generateInviteUser()) + + const [allUsersResponse, allUsersData] = await config.userManagement.getAllUsers() + expect(allUsersData.length).toEqual(4) + }) + + }) From 1c0767f549e4669574e8eef7f8f05625cabe4779 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 2 Dec 2022 18:42:56 +0000 Subject: [PATCH 04/43] Add users with all roles --- .../config/internal-api/TestConfiguration/userManagement.ts | 5 +++-- qa-core/src/config/internal-api/fixtures/userManagement.ts | 6 ------ .../internal-api/userManagement/userManagement.spec.ts | 2 +- 3 files changed, 4 insertions(+), 9 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 17fe5e0b0f..0bc8fd7b66 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -63,8 +63,9 @@ export default class UserManagementApi { const response = await this.api.post(`/global/users/multi/invite`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) - expect(json.created.successful.length).toEqual(body.length) - expect(json.created.unsuccessful.length).toEqual(0) + expect(json.unsuccessful.length).toEqual(0) + expect(json.successful.length).toEqual(body.length) + return [response, json] } diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index 6ada85bb49..035f6162f1 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -65,12 +65,6 @@ export const generateInviteUser = (): Object[] => { return [{ email: `pedro+${randomId}@budibase.com`, userInfo: { - admin: { - global: true - }, - builder: { - global: true - }, userGroups: [] } }] diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 62d27ec2a4..c18b6aaeff 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -26,7 +26,7 @@ describe("Internal API - User Management & Permissions", () => { const [devResponse, devData] = await config.userManagement.addUsers(generateDeveloper()) const [userResponse, userData] = await config.userManagement.addUsers(generateAppUser()) - const [invitedUserResponse, invitedUserData] = await config.userManagement.addUsers(generateInviteUser()) + const [invitedUserResponse, invitedUserData] = await config.userManagement.inviteUser(generateInviteUser()) const [allUsersResponse, allUsersData] = await config.userManagement.getAllUsers() expect(allUsersData.length).toEqual(4) From c0c8262561e48fa316f9772b093ae862c103c042 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 2 Dec 2022 18:59:08 +0000 Subject: [PATCH 05/43] Add generic login method --- .../config/internal-api/TestConfiguration/auth.ts | 14 +++++++++++++- .../config/internal-api/TestConfiguration/index.ts | 8 ++++++-- .../config/internal-api/fixtures/userManagement.ts | 4 ++-- .../internal-api/applications/applications.spec.ts | 2 +- .../src/tests/internal-api/screens/screens.spec.ts | 2 +- .../src/tests/internal-api/tables/tables.spec.ts | 2 +- .../userManagement/userManagement.spec.ts | 6 ++---- 7 files changed, 26 insertions(+), 12 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/auth.ts b/qa-core/src/config/internal-api/TestConfiguration/auth.ts index d83c859ab3..d72502b417 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/auth.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/auth.ts @@ -8,7 +8,7 @@ export default class AuthApi { this.api = apiClient } - async login(): Promise<[Response, any]> { + async loginAsAdmin(): Promise<[Response, any]> { const response = await this.api.post(`/global/auth/default/login`, { body: { username: process.env.BB_ADMIN_USER_EMAIL, @@ -20,6 +20,18 @@ export default class AuthApi { return [response, cookie] } + async login(email: String, password: String): Promise<[Response, any]> { + const response = await this.api.post(`/global/auth/default/login`, { + body: { + username: email, + password: password, + }, + }) + const cookie = response.headers.get("set-cookie") + this.api.cookie = cookie as any + return [response, cookie] + } + async logout(): Promise { return this.api.post(`/global/auth/logout`) } diff --git a/qa-core/src/config/internal-api/TestConfiguration/index.ts b/qa-core/src/config/internal-api/TestConfiguration/index.ts index 8ce5e94bc3..b424b32416 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/index.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/index.ts @@ -25,8 +25,12 @@ export default class TestConfiguration { this.context = {} } - async beforeAll() { - await this.auth.login() + async loginAsAdmin() { + await this.auth.login(process.env.BB_ADMIN_USER_EMAIL, process.env.BB_ADMIN_USER_PASSWORD) + } + + async login(email: String, password: String) { + await this.auth.login(email, password) } async afterAll() { diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index 035f6162f1..5c5979256f 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -61,9 +61,9 @@ export const generateAppUser = (): Object => { } export const generateInviteUser = (): Object[] => { - const randomId = generator.guid(); + //const randomId = generator.guid(); return [{ - email: `pedro+${randomId}@budibase.com`, + email: `pedro+test@budibase.com`, userInfo: { userGroups: [] } diff --git a/qa-core/src/tests/internal-api/applications/applications.spec.ts b/qa-core/src/tests/internal-api/applications/applications.spec.ts index 98895a6f28..c7738152c4 100644 --- a/qa-core/src/tests/internal-api/applications/applications.spec.ts +++ b/qa-core/src/tests/internal-api/applications/applications.spec.ts @@ -11,7 +11,7 @@ describe("Internal API - Application creation, update, publish and delete", () = const config = new TestConfiguration(api) beforeAll(async () => { - await config.beforeAll() + await config.loginAsAdmin() }) afterAll(async () => { diff --git a/qa-core/src/tests/internal-api/screens/screens.spec.ts b/qa-core/src/tests/internal-api/screens/screens.spec.ts index 218d71cb0d..1af13d0a11 100644 --- a/qa-core/src/tests/internal-api/screens/screens.spec.ts +++ b/qa-core/src/tests/internal-api/screens/screens.spec.ts @@ -11,7 +11,7 @@ describe("Internal API - /screens endpoints", () => { const appConfig = new TestConfiguration(api) beforeAll(async () => { - await config.beforeAll() + await config.loginAsAdmin() }) afterAll(async () => { diff --git a/qa-core/src/tests/internal-api/tables/tables.spec.ts b/qa-core/src/tests/internal-api/tables/tables.spec.ts index 4f9e4299cf..6b2d2240e5 100644 --- a/qa-core/src/tests/internal-api/tables/tables.spec.ts +++ b/qa-core/src/tests/internal-api/tables/tables.spec.ts @@ -13,7 +13,7 @@ describe("Internal API - Application creation, update, publish and delete", () = const config = new TestConfiguration(api) beforeAll(async () => { - await config.beforeAll() + await config.loginAsAdmin() }) afterAll(async () => { diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index c18b6aaeff..7e38409723 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -11,7 +11,7 @@ describe("Internal API - User Management & Permissions", () => { const config = new TestConfiguration(api) beforeAll(async () => { - await config.beforeAll() + await config.loginAsAdmin() }) afterAll(async () => { @@ -26,10 +26,8 @@ describe("Internal API - User Management & Permissions", () => { const [devResponse, devData] = await config.userManagement.addUsers(generateDeveloper()) const [userResponse, userData] = await config.userManagement.addUsers(generateAppUser()) - const [invitedUserResponse, invitedUserData] = await config.userManagement.inviteUser(generateInviteUser()) - const [allUsersResponse, allUsersData] = await config.userManagement.getAllUsers() - expect(allUsersData.length).toEqual(4) + expect(allUsersData.length).toBeGreaterThan(0) }) From 0034bbbe2d0a5a51edb833a577898460c22fa2eb Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 2 Dec 2022 19:04:23 +0000 Subject: [PATCH 06/43] Record generated users passwords in test context --- .../userManagement/userManagement.spec.ts | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-) diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 7e38409723..f7442a34fc 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -5,6 +5,7 @@ import InternalAPIClient from "../../../config/internal-api/TestConfiguration/In import generateApp from "../../../config/internal-api/fixtures/applications" import generator from "../../../config/generator" import { generateAdmin, generateAppUser, generateDeveloper, generateInviteUser } from "../../../config/internal-api/fixtures/userManagement" +import generate from "../../../config/internal-api/fixtures/applications" describe("Internal API - User Management & Permissions", () => { const api = new InternalAPIClient() @@ -22,9 +23,14 @@ describe("Internal API - User Management & Permissions", () => { await config.userManagement.searchUsers() await config.userManagement.getRoles() - const [adminResponse, adminData] = await config.userManagement.addUsers(generateAdmin()) - const [devResponse, devData] = await config.userManagement.addUsers(generateDeveloper()) - const [userResponse, userData] = await config.userManagement.addUsers(generateAppUser()) + // These need to be saved to the context so the passwords can be used to login + const admin = generateAdmin() + const developer = generateDeveloper() + const appUser = generateAppUser() + + const [adminResponse, adminData] = await config.userManagement.addUsers(admin) + const [devResponse, devData] = await config.userManagement.addUsers(developer) + const [userResponse, userData] = await config.userManagement.addUsers(appUser) const [allUsersResponse, allUsersData] = await config.userManagement.getAllUsers() expect(allUsersData.length).toBeGreaterThan(0) From 895c29d45fdf94cc7f9f6dce273d43c70e90e652 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Mon, 5 Dec 2022 17:54:40 +0000 Subject: [PATCH 07/43] Add Tests for changes to user information/roles --- .../TestConfiguration/userManagement.ts | 36 +++++++++++++-- .../userManagement/userManagement.spec.ts | 46 ++++++++++++++++--- 2 files changed, 72 insertions(+), 10 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 0bc8fd7b66..4bdec74cc4 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -33,7 +33,7 @@ export default class UserManagementApi { return [response, json] } - async addUsers(body: any): Promise<[Response, responseMessage]> { + async addUsers(body: any): Promise<[Response, any]> { const response = await this.api.post(`/global/users/bulk`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -42,7 +42,7 @@ export default class UserManagementApi { return [response, json] } - async deleteUser(userId: string): Promise<[Response, responseMessage]> { + async deleteMultipleUsers(userId: string[]): Promise<[Response, responseMessage]> { const body = { delete: { userIds: [ @@ -58,6 +58,13 @@ export default class UserManagementApi { expect(json.deleted.successful[0].userId).toEqual(userId) return [response, json] } + async deleteUser(userId: string): Promise<[Response, UserDeletedEvent]> { + const response = await this.api.del(`/global/users/${userId}`) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json.message).toEqual(`User ${userId} deleted.`) + return [response, json] + } async inviteUser(body: any): Promise<[Response, responseMessage]> { const response = await this.api.post(`/global/users/multi/invite`, { body }) @@ -76,4 +83,27 @@ export default class UserManagementApi { expect(json.length).toEqual(4) return [response, json] } -} + + async changeUserInformation(body: any): Promise<[Response, User]> { + const response = await this.api.post(`/global/users/`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + return [response, json] + } + + async forcePasswordReset(body: any): Promise<[Response, User]> { + const response = await this.api.post(`/global/users/`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json._id).toEqual(body._id) + expect(json._rev).not.toEqual(body._rev) + return [response, json] + } + + async getUserInformation(userId: string): Promise<[Response, User]> { + const response = await this.api.get(`/global/users/${userId}`) + const json = await response.json() + expect(response).toHaveStatusCode(200) + return [response, json] + } +} \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index f7442a34fc..09b8501e0c 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -1,11 +1,7 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { Application } from "@budibase/server/api/controllers/public/mapping/types" -import { db } from "@budibase/backend-core" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" -import generateApp from "../../../config/internal-api/fixtures/applications" -import generator from "../../../config/generator" import { generateAdmin, generateAppUser, generateDeveloper, generateInviteUser } from "../../../config/internal-api/fixtures/userManagement" -import generate from "../../../config/internal-api/fixtures/applications" describe("Internal API - User Management & Permissions", () => { const api = new InternalAPIClient() @@ -28,13 +24,49 @@ describe("Internal API - User Management & Permissions", () => { const developer = generateDeveloper() const appUser = generateAppUser() - const [adminResponse, adminData] = await config.userManagement.addUsers(admin) - const [devResponse, devData] = await config.userManagement.addUsers(developer) - const [userResponse, userData] = await config.userManagement.addUsers(appUser) + await config.userManagement.addUsers(admin) + await config.userManagement.addUsers(developer) + await config.userManagement.addUsers(appUser) const [allUsersResponse, allUsersData] = await config.userManagement.getAllUsers() expect(allUsersData.length).toBeGreaterThan(0) + + + }) + + it("Delete User", async () => { + const appUser = generateAppUser() + const [userResponse, userData] = await config.userManagement.addUsers(appUser) + const userId = userData.created.successful[0]._id + await config.userManagement.deleteUser(userId) + }) + + it("Reset Password", async () => { + const appUser = generateAppUser() + const [userResponse, userData] = await config.userManagement.addUsers(appUser) + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userData.created.successful[0]._id) + const body = { + ...userInfoJson, + password: "newPassword" + + } + await config.userManagement.forcePasswordReset(body) + }) + + it("Change User information", async () => { + const appUser = generateAppUser() + const [userResponse, userData] = await config.userManagement.addUsers(appUser) + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userData.created.successful[0]._id) + const body = { + ...userInfoJson, + builder: { + global: true + } + } + const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) + expect(changedUserJson.builder?.global).toBeDefined() + expect(changedUserJson.builder?.global).toEqual(true) }) From d2a8923d0da700777cf90524cd94cde7f20fa2af Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Tue, 6 Dec 2022 16:14:00 +0000 Subject: [PATCH 08/43] Add tests for Roles --- .../TestConfiguration/applications.ts | 5 +- .../userManagement/userManagement.spec.ts | 94 +++++++++++++++++-- 2 files changed, 91 insertions(+), 8 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/applications.ts b/qa-core/src/config/internal-api/TestConfiguration/applications.ts index 13d0969854..7eeda01f0e 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/applications.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/applications.ts @@ -13,12 +13,13 @@ export default class AppApi { constructor(apiClient: InternalAPIClient) { this.api = apiClient } - + // TODO Fix the fetch apps to receive an optional number of apps and compare if the received app is more or less. + // each possible scenario should have its own method. async fetchEmptyAppList(): Promise<[Response, Application[]]> { const response = await this.api.get(`/applications?status=all`) const json = await response.json() expect(response).toHaveStatusCode(200) - expect(json.length).toEqual(0) + expect(json.length).toBeGreaterThanOrEqual(0) return [response, json] } diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 09b8501e0c..1f5ac695a9 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -1,7 +1,9 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { Application } from "@budibase/server/api/controllers/public/mapping/types" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" +import generateApp from "../../../config/internal-api/fixtures/applications" import { generateAdmin, generateAppUser, generateDeveloper, generateInviteUser } from "../../../config/internal-api/fixtures/userManagement" +import { User } from "@budibase/types" describe("Internal API - User Management & Permissions", () => { const api = new InternalAPIClient() @@ -46,7 +48,7 @@ describe("Internal API - User Management & Permissions", () => { const appUser = generateAppUser() const [userResponse, userData] = await config.userManagement.addUsers(appUser) const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userData.created.successful[0]._id) - const body = { + const body: User = { ...userInfoJson, password: "newPassword" @@ -56,18 +58,98 @@ describe("Internal API - User Management & Permissions", () => { it("Change User information", async () => { const appUser = generateAppUser() - const [userResponse, userData] = await config.userManagement.addUsers(appUser) - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userData.created.successful[0]._id) - const body = { + const [userResponse, userJson] = await config.userManagement.addUsers(appUser) + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) + const body: User = { ...userInfoJson, + firstName: "newFirstName", + lastName: "newLastName", builder: { global: true } } const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) - expect(changedUserJson.builder?.global).toBeDefined() - expect(changedUserJson.builder?.global).toEqual(true) + expect(changedUserJson._id).toEqual(userJson.created.successful[0]._id) + expect(changedUserJson._rev).not.toEqual(userJson.created.successful[0]._rev) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) + expect(changedUserInfoJson.builder?.global).toBeDefined() + expect(changedUserInfoJson.builder?.global).toEqual(true) }) + it("Add BASIC user to app", async () => { + const basicUser = generateAppUser() + + const [createUserResponse, createUserJson] = await config.userManagement.addUsers(basicUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId?.toString() || ""]: "BASIC", + } + } + const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) + expect(changedUserJson._id).toEqual(createUserJson.created.successful[0]._id) + expect(changedUserJson._rev).not.toEqual(createUserJson.created.successful[0]._rev) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("BASIC") + + }) + + it("Add ADMIN user to app", async () => { + const adminUser = generateAdmin() + + const [createUserResponse, createUserJson] = await config.userManagement.addUsers(adminUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId?.toString() || ""]: "ADMIN", + } + } + const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) + expect(changedUserJson._id).toEqual(createUserJson.created.successful[0]._id) + expect(changedUserJson._rev).not.toEqual(createUserJson.created.successful[0]._rev) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("ADMIN") + + }) + + it("Add POWER user to app", async () => { + const powerUser = generateDeveloper() + + const [createUserResponse, createUserJson] = await config.userManagement.addUsers(powerUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId?.toString() || ""]: "POWER", + } + } + const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) + expect(changedUserJson._id).toEqual(createUserJson.created.successful[0]._id) + expect(changedUserJson._rev).not.toEqual(createUserJson.created.successful[0]._rev) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("POWER") + + }) }) From c03ee6a61369c6c71a8cf2b89a90eea263bb010f Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Tue, 6 Dec 2022 16:16:07 +0000 Subject: [PATCH 09/43] Fix names --- .../userManagement/userManagement.spec.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 1f5ac695a9..faea247204 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -30,8 +30,8 @@ describe("Internal API - User Management & Permissions", () => { await config.userManagement.addUsers(developer) await config.userManagement.addUsers(appUser) - const [allUsersResponse, allUsersData] = await config.userManagement.getAllUsers() - expect(allUsersData.length).toBeGreaterThan(0) + const [allUsersResponse, allUsersJson] = await config.userManagement.getAllUsers() + expect(allUsersJson.length).toBeGreaterThan(0) @@ -39,15 +39,15 @@ describe("Internal API - User Management & Permissions", () => { it("Delete User", async () => { const appUser = generateAppUser() - const [userResponse, userData] = await config.userManagement.addUsers(appUser) - const userId = userData.created.successful[0]._id + const [userResponse, userJson] = await config.userManagement.addUsers(appUser) + const userId = userJson.created.successful[0]._id await config.userManagement.deleteUser(userId) }) it("Reset Password", async () => { const appUser = generateAppUser() - const [userResponse, userData] = await config.userManagement.addUsers(appUser) - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userData.created.successful[0]._id) + const [userResponse, userJson] = await config.userManagement.addUsers(appUser) + const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) const body: User = { ...userInfoJson, password: "newPassword" From 4467d2b0050b798f1e94cbf2817f444cce2b166e Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Tue, 6 Dec 2022 18:20:02 +0000 Subject: [PATCH 10/43] Remove duplicated assertions --- .../TestConfiguration/userManagement.ts | 2 ++ .../userManagement/userManagement.spec.ts | 16 ++++------------ 2 files changed, 6 insertions(+), 12 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 4bdec74cc4..33d53a6604 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -88,6 +88,8 @@ export default class UserManagementApi { const response = await this.api.post(`/global/users/`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) + expect(json._id).toEqual(body._id) + expect(json._rev).not.toEqual(body._rev) return [response, json] } diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index faea247204..099d79df1c 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -68,9 +68,7 @@ describe("Internal API - User Management & Permissions", () => { global: true } } - const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) - expect(changedUserJson._id).toEqual(userJson.created.successful[0]._id) - expect(changedUserJson._rev).not.toEqual(userJson.created.successful[0]._rev) + await config.userManagement.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) expect(changedUserInfoJson.builder?.global).toBeDefined() @@ -92,9 +90,7 @@ describe("Internal API - User Management & Permissions", () => { [app.appId?.toString() || ""]: "BASIC", } } - const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) - expect(changedUserJson._id).toEqual(createUserJson.created.successful[0]._id) - expect(changedUserJson._rev).not.toEqual(createUserJson.created.successful[0]._rev) + await config.userManagement.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() @@ -117,9 +113,7 @@ describe("Internal API - User Management & Permissions", () => { [app.appId?.toString() || ""]: "ADMIN", } } - const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) - expect(changedUserJson._id).toEqual(createUserJson.created.successful[0]._id) - expect(changedUserJson._rev).not.toEqual(createUserJson.created.successful[0]._rev) + await config.userManagement.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() @@ -142,9 +136,7 @@ describe("Internal API - User Management & Permissions", () => { [app.appId?.toString() || ""]: "POWER", } } - const [changedUserResponse, changedUserJson] = await config.userManagement.changeUserInformation(body) - expect(changedUserJson._id).toEqual(createUserJson.created.successful[0]._id) - expect(changedUserJson._rev).not.toEqual(createUserJson.created.successful[0]._rev) + await config.userManagement.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() From 6d87a38ab3b0a30ff3e451ec88d9a7d71dac1ec7 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 9 Dec 2022 17:34:59 +0000 Subject: [PATCH 11/43] Changes to types and user generation --- .../internal-api/TestConfiguration/index.ts | 8 +- .../TestConfiguration/userManagement.ts | 8 +- .../internal-api/fixtures/userManagement.ts | 99 ++++++++++--------- .../userManagement/userManagement.spec.ts | 92 +++++++++-------- 4 files changed, 118 insertions(+), 89 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/index.ts b/qa-core/src/config/internal-api/TestConfiguration/index.ts index b424b32416..a82c1fdf03 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/index.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/index.ts @@ -13,7 +13,7 @@ export default class TestConfiguration { context: T tables: TablesApi rows: RowApi - userManagement: UserManagementApi + users: UserManagementApi constructor(apiClient: InternalAPIClient) { this.applications = new ApplicationApi(apiClient) @@ -21,15 +21,15 @@ export default class TestConfiguration { this.rows = new RowApi(apiClient) this.auth = new AuthApi(apiClient) this.screen = new ScreenApi(apiClient) - this.userManagement = new UserManagementApi(apiClient) + this.users = new UserManagementApi(apiClient) this.context = {} } async loginAsAdmin() { - await this.auth.login(process.env.BB_ADMIN_USER_EMAIL, process.env.BB_ADMIN_USER_PASSWORD) + await this.auth.login(process.env.BB_ADMIN_USER_EMAIL, process.env.BB_ADMIN_USER_PASSWORD) } - async login(email: String, password: String) { + async login(email: string, password: string) { await this.auth.login(email, password) } diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 33d53a6604..52f610ab17 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -33,7 +33,13 @@ export default class UserManagementApi { return [response, json] } - async addUsers(body: any): Promise<[Response, any]> { + async addMultipleUsers(userList: User[]): Promise<[Response, any]> { + const body = { + create: { + users: userList, + groups: [] + } + } const response = await this.api.post(`/global/users/bulk`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index 5c5979256f..78374ae6e1 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -1,63 +1,51 @@ import generator from "../../generator"; +import { User } from "@budibase/types"; +import { generateUserMetadataID } from "@budibase/backend-core/src/db"; -export const generateDeveloper = (): Object => { + +const generateDeveloper = (): User => { const randomId = generator.guid(); return ({ - create: { - users: [{ - email: `pedro+${randomId}@budibase.com`, - password: randomId, - roles: {}, - forceResetPassword: true, - builder: { - global: true - } - }], - groups: [] + email: `pedro+${randomId}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + builder: { + global: true } }) } -export const generateAdmin = (): Object => { +const generateAdmin = (): User => { const randomId = generator.guid(); return ({ - create: { - users: [{ - email: `pedro+${randomId}@budibase.com`, - password: randomId, - roles: {}, - forceResetPassword: true, - admin: { - global: true - }, - builder: { - global: true - } - }], - groups: [] + email: `pedro+${randomId}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + admin: { + global: true + }, + builder: { + global: true } }) } -export const generateAppUser = (): Object => { +const generateAppUser = (): User => { const randomId = generator.guid(); - const user = { - create: { - users: [{ - email: `pedro+${randomId}@budibase.com`, - password: randomId, - roles: {}, - forceResetPassword: true, - admin: { - global: false - }, - builder: { - global: false - } - }], - groups: [] + return ({ + email: `pedro+${randomId}@budibase.com`, + password: randomId, + roles: {}, + forceResetPassword: true, + admin: { + global: false + }, + builder: { + global: false } - } - return user + }) + } export const generateInviteUser = (): Object[] => { @@ -69,4 +57,25 @@ export const generateInviteUser = (): Object[] => { } }] +} + +export const generateUser = (amount: number = 1, role?: string): User[] => { + const userList: User[] = []; + for (let i = 0; i < amount; i++) { + switch (role) { + case "admin": + userList.push(generateAdmin()); + break; + case "developer": + userList.push(generateDeveloper()); + break; + case "appUser": + userList.push(generateAppUser()); + break; + default: + userList.push(generateAppUser()); + break; + } + } + return userList } \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 099d79df1c..cd8d9cbf65 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -2,7 +2,7 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { Application } from "@budibase/server/api/controllers/public/mapping/types" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" import generateApp from "../../../config/internal-api/fixtures/applications" -import { generateAdmin, generateAppUser, generateDeveloper, generateInviteUser } from "../../../config/internal-api/fixtures/userManagement" +import { generateUser } from "../../../config/internal-api/fixtures/userManagement" import { User } from "@budibase/types" describe("Internal API - User Management & Permissions", () => { @@ -18,19 +18,24 @@ describe("Internal API - User Management & Permissions", () => { }) it("Add Users with different roles", async () => { - await config.userManagement.searchUsers() - await config.userManagement.getRoles() + await config.users.searchUsers() + await config.users.getRoles() // These need to be saved to the context so the passwords can be used to login - const admin = generateAdmin() - const developer = generateDeveloper() - const appUser = generateAppUser() + const admin = generateUser(1, "admin") + expect(admin[0].builder?.global).toEqual(true) + expect(admin[0].admin?.global).toEqual(true) + const developer = generateUser(1, "developer") + expect(developer[0].builder?.global).toEqual(true) + const appUser = generateUser(1, "appUser") + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) - await config.userManagement.addUsers(admin) - await config.userManagement.addUsers(developer) - await config.userManagement.addUsers(appUser) + await config.users.addMultipleUsers(admin) + await config.users.addMultipleUsers(developer) + await config.users.addMultipleUsers(appUser) - const [allUsersResponse, allUsersJson] = await config.userManagement.getAllUsers() + const [allUsersResponse, allUsersJson] = await config.users.getAllUsers() expect(allUsersJson.length).toBeGreaterThan(0) @@ -38,28 +43,34 @@ describe("Internal API - User Management & Permissions", () => { }) it("Delete User", async () => { - const appUser = generateAppUser() - const [userResponse, userJson] = await config.userManagement.addUsers(appUser) + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [userResponse, userJson] = await config.users.addMultipleUsers(appUser) const userId = userJson.created.successful[0]._id - await config.userManagement.deleteUser(userId) + await config.users.deleteUser(userId) }) it("Reset Password", async () => { - const appUser = generateAppUser() - const [userResponse, userJson] = await config.userManagement.addUsers(appUser) - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [userResponse, userJson] = await config.users.addMultipleUsers(appUser) + const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(userJson.created.successful[0]._id) const body: User = { ...userInfoJson, password: "newPassword" } - await config.userManagement.forcePasswordReset(body) + await config.users.forcePasswordReset(body) }) it("Change User information", async () => { - const appUser = generateAppUser() - const [userResponse, userJson] = await config.userManagement.addUsers(appUser) - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [userResponse, userJson] = await config.users.addMultipleUsers(appUser) + const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(userJson.created.successful[0]._id) const body: User = { ...userInfoJson, firstName: "newFirstName", @@ -68,77 +79,80 @@ describe("Internal API - User Management & Permissions", () => { global: true } } - await config.userManagement.changeUserInformation(body) + await config.users.changeUserInformation(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(userJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(userJson.created.successful[0]._id) expect(changedUserInfoJson.builder?.global).toBeDefined() expect(changedUserInfoJson.builder?.global).toEqual(true) }) it("Add BASIC user to app", async () => { - const basicUser = generateAppUser() - - const [createUserResponse, createUserJson] = await config.userManagement.addUsers(basicUser) + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(appUser) const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { [app.appId?.toString() || ""]: "BASIC", } } - await config.userManagement.changeUserInformation(body) + await config.users.changeUserInformation(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("BASIC") }) it("Add ADMIN user to app", async () => { - const adminUser = generateAdmin() - - const [createUserResponse, createUserJson] = await config.userManagement.addUsers(adminUser) + const adminUser = generateUser(1, "admin") + expect(adminUser[0].builder?.global).toEqual(true) + expect(adminUser[0].admin?.global).toEqual(true) + const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(adminUser) const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { [app.appId?.toString() || ""]: "ADMIN", } } - await config.userManagement.changeUserInformation(body) + await config.users.changeUserInformation(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("ADMIN") }) it("Add POWER user to app", async () => { - const powerUser = generateDeveloper() + const powerUser = generateUser(1, 'Developer') + expect(powerUser[0].builder?.global).toEqual(true) - const [createUserResponse, createUserJson] = await config.userManagement.addUsers(powerUser) + const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(powerUser) const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId - const [userInfoResponse, userInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { [app.appId?.toString() || ""]: "POWER", } } - await config.userManagement.changeUserInformation(body) + await config.users.changeUserInformation(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.userManagement.getUserInformation(createUserJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("POWER") From b995575189b84575eb63ae278158619655644329 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 9 Dec 2022 17:49:45 +0000 Subject: [PATCH 12/43] Add partial user type --- .../internal-api/TestConfiguration/userManagement.ts | 8 ++++---- .../src/config/internal-api/fixtures/userManagement.ts | 10 +++++----- .../internal-api/userManagement/userManagement.spec.ts | 6 +++--- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 52f610ab17..4a6dbfd1e1 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -10,7 +10,7 @@ export default class UserManagementApi { this.api = apiClient } - async searchUsers(): Promise<[Response, User[]]> { + async searchUsers(): Promise<[Response, Partial[]]> { const response = await this.api.post(`/global/users/search`, {}) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -18,14 +18,14 @@ export default class UserManagementApi { return [response, json] } - async getSelf(): Promise<[Response, User]> { + async getSelf(): Promise<[Response, Partial]> { const response = await this.api.get(`/global/self`) const json = await response.json() expect(response).toHaveStatusCode(200) return [response, json] } - async getAllUsers(): Promise<[Response, User[]]> { + async getAllUsers(): Promise<[Response, Partial[]]> { const response = await this.api.get(`/global/users`) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -33,7 +33,7 @@ export default class UserManagementApi { return [response, json] } - async addMultipleUsers(userList: User[]): Promise<[Response, any]> { + async addMultipleUsers(userList: Partial[]): Promise<[Response, any]> { const body = { create: { users: userList, diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index 78374ae6e1..077f42ae57 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -3,7 +3,7 @@ import { User } from "@budibase/types"; import { generateUserMetadataID } from "@budibase/backend-core/src/db"; -const generateDeveloper = (): User => { +const generateDeveloper = (): Partial => { const randomId = generator.guid(); return ({ email: `pedro+${randomId}@budibase.com`, @@ -16,7 +16,7 @@ const generateDeveloper = (): User => { }) } -const generateAdmin = (): User => { +const generateAdmin = (): Partial => { const randomId = generator.guid(); return ({ email: `pedro+${randomId}@budibase.com`, @@ -31,7 +31,7 @@ const generateAdmin = (): User => { } }) } -const generateAppUser = (): User => { +const generateAppUser = (): Partial => { const randomId = generator.guid(); return ({ email: `pedro+${randomId}@budibase.com`, @@ -59,8 +59,8 @@ export const generateInviteUser = (): Object[] => { } -export const generateUser = (amount: number = 1, role?: string): User[] => { - const userList: User[] = []; +export const generateUser = (amount: number = 1, role?: string): Partial[] => { + const userList: Partial[] = []; for (let i = 0; i < amount; i++) { switch (role) { case "admin": diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index cd8d9cbf65..78cb6deca0 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -135,7 +135,7 @@ describe("Internal API - User Management & Permissions", () => { }) it("Add POWER user to app", async () => { - const powerUser = generateUser(1, 'Developer') + const powerUser = generateUser(1, 'developer') expect(powerUser[0].builder?.global).toEqual(true) const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(powerUser) @@ -153,8 +153,8 @@ describe("Internal API - User Management & Permissions", () => { await config.users.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("POWER") + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") }) From fbf50f0ddf931c96e56f2a78486a514324e5271a Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 9 Dec 2022 17:52:33 +0000 Subject: [PATCH 13/43] Remove explicit toString --- .../internal-api/userManagement/userManagement.spec.ts | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 78cb6deca0..4f6eefc247 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -105,8 +105,8 @@ describe("Internal API - User Management & Permissions", () => { await config.users.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("BASIC") + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") }) @@ -129,8 +129,8 @@ describe("Internal API - User Management & Permissions", () => { await config.users.changeUserInformation(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId?.toString() || ""]).toEqual("ADMIN") + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") }) From d390fe7d8d83aebdf607948cd80b062218639681 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 9 Dec 2022 18:00:13 +0000 Subject: [PATCH 14/43] Rename users methods --- .../TestConfiguration/userManagement.ts | 16 +++--- .../internal-api/fixtures/userManagement.ts | 4 +- .../userManagement/userManagement.spec.ts | 50 +++++++++---------- 3 files changed, 35 insertions(+), 35 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index 4a6dbfd1e1..e323c3a098 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -10,7 +10,7 @@ export default class UserManagementApi { this.api = apiClient } - async searchUsers(): Promise<[Response, Partial[]]> { + async search(): Promise<[Response, Partial[]]> { const response = await this.api.post(`/global/users/search`, {}) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -25,7 +25,7 @@ export default class UserManagementApi { return [response, json] } - async getAllUsers(): Promise<[Response, Partial[]]> { + async getAll(): Promise<[Response, Partial[]]> { const response = await this.api.get(`/global/users`) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -33,7 +33,7 @@ export default class UserManagementApi { return [response, json] } - async addMultipleUsers(userList: Partial[]): Promise<[Response, any]> { + async addMultiple(userList: Partial[]): Promise<[Response, any]> { const body = { create: { users: userList, @@ -48,7 +48,7 @@ export default class UserManagementApi { return [response, json] } - async deleteMultipleUsers(userId: string[]): Promise<[Response, responseMessage]> { + async deleteMultiple(userId: string[]): Promise<[Response, responseMessage]> { const body = { delete: { userIds: [ @@ -64,7 +64,7 @@ export default class UserManagementApi { expect(json.deleted.successful[0].userId).toEqual(userId) return [response, json] } - async deleteUser(userId: string): Promise<[Response, UserDeletedEvent]> { + async delete(userId: string): Promise<[Response, UserDeletedEvent]> { const response = await this.api.del(`/global/users/${userId}`) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -72,7 +72,7 @@ export default class UserManagementApi { return [response, json] } - async inviteUser(body: any): Promise<[Response, responseMessage]> { + async invite(body: any): Promise<[Response, responseMessage]> { const response = await this.api.post(`/global/users/multi/invite`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -90,7 +90,7 @@ export default class UserManagementApi { return [response, json] } - async changeUserInformation(body: any): Promise<[Response, User]> { + async updateInfo(body: any): Promise<[Response, User]> { const response = await this.api.post(`/global/users/`, { body }) const json = await response.json() expect(response).toHaveStatusCode(200) @@ -108,7 +108,7 @@ export default class UserManagementApi { return [response, json] } - async getUserInformation(userId: string): Promise<[Response, User]> { + async getInfo(userId: string): Promise<[Response, User]> { const response = await this.api.get(`/global/users/${userId}`) const json = await response.json() expect(response).toHaveStatusCode(200) diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index 077f42ae57..446ae3b0c5 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -49,9 +49,9 @@ const generateAppUser = (): Partial => { } export const generateInviteUser = (): Object[] => { - //const randomId = generator.guid(); + const randomId = generator.guid(); return [{ - email: `pedro+test@budibase.com`, + email: `pedro+${randomId}@budibase.com`, userInfo: { userGroups: [] } diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 4f6eefc247..92ecf96258 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -18,7 +18,7 @@ describe("Internal API - User Management & Permissions", () => { }) it("Add Users with different roles", async () => { - await config.users.searchUsers() + await config.users.search() await config.users.getRoles() // These need to be saved to the context so the passwords can be used to login @@ -31,11 +31,11 @@ describe("Internal API - User Management & Permissions", () => { expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) - await config.users.addMultipleUsers(admin) - await config.users.addMultipleUsers(developer) - await config.users.addMultipleUsers(appUser) + await config.users.addMultiple(admin) + await config.users.addMultiple(developer) + await config.users.addMultiple(appUser) - const [allUsersResponse, allUsersJson] = await config.users.getAllUsers() + const [allUsersResponse, allUsersJson] = await config.users.getAll() expect(allUsersJson.length).toBeGreaterThan(0) @@ -46,17 +46,17 @@ describe("Internal API - User Management & Permissions", () => { const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) - const [userResponse, userJson] = await config.users.addMultipleUsers(appUser) + const [userResponse, userJson] = await config.users.addMultiple(appUser) const userId = userJson.created.successful[0]._id - await config.users.deleteUser(userId) + await config.users.delete(userId) }) it("Reset Password", async () => { const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) - const [userResponse, userJson] = await config.users.addMultipleUsers(appUser) - const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(userJson.created.successful[0]._id) + const [userResponse, userJson] = await config.users.addMultiple(appUser) + const [userInfoResponse, userInfoJson] = await config.users.getInfo(userJson.created.successful[0]._id) const body: User = { ...userInfoJson, password: "newPassword" @@ -69,8 +69,8 @@ describe("Internal API - User Management & Permissions", () => { const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) - const [userResponse, userJson] = await config.users.addMultipleUsers(appUser) - const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(userJson.created.successful[0]._id) + const [userResponse, userJson] = await config.users.addMultiple(appUser) + const [userInfoResponse, userInfoJson] = await config.users.getInfo(userJson.created.successful[0]._id) const body: User = { ...userInfoJson, firstName: "newFirstName", @@ -79,9 +79,9 @@ describe("Internal API - User Management & Permissions", () => { global: true } } - await config.users.changeUserInformation(body) + await config.users.updateInfo(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(userJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(userJson.created.successful[0]._id) expect(changedUserInfoJson.builder?.global).toBeDefined() expect(changedUserInfoJson.builder?.global).toEqual(true) }) @@ -90,21 +90,21 @@ describe("Internal API - User Management & Permissions", () => { const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) - const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(appUser) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId - const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { [app.appId?.toString() || ""]: "BASIC", } } - await config.users.changeUserInformation(body) + await config.users.updateInfo(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId]).toBeDefined() expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") @@ -114,21 +114,21 @@ describe("Internal API - User Management & Permissions", () => { const adminUser = generateUser(1, "admin") expect(adminUser[0].builder?.global).toEqual(true) expect(adminUser[0].admin?.global).toEqual(true) - const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(adminUser) + const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId - const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { [app.appId?.toString() || ""]: "ADMIN", } } - await config.users.changeUserInformation(body) + await config.users.updateInfo(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId]).toBeDefined() expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") @@ -138,21 +138,21 @@ describe("Internal API - User Management & Permissions", () => { const powerUser = generateUser(1, 'developer') expect(powerUser[0].builder?.global).toEqual(true) - const [createUserResponse, createUserJson] = await config.users.addMultipleUsers(powerUser) + const [createUserResponse, createUserJson] = await config.users.addMultiple(powerUser) const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId - const [userInfoResponse, userInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { [app.appId?.toString() || ""]: "POWER", } } - await config.users.changeUserInformation(body) + await config.users.updateInfo(body) - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getUserInformation(createUserJson.created.successful[0]._id) + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId]).toBeDefined() expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") From 1765e10995aa1c436593a47d7e31f48255453ac2 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 9 Dec 2022 18:10:17 +0000 Subject: [PATCH 15/43] Remove toString --- .../internal-api/userManagement/userManagement.spec.ts | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 92ecf96258..e6277a5e7f 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -99,7 +99,7 @@ describe("Internal API - User Management & Permissions", () => { const body: User = { ...userInfoJson, roles: { - [app.appId?.toString() || ""]: "BASIC", + [app.appId]: "BASIC", } } await config.users.updateInfo(body) @@ -123,7 +123,7 @@ describe("Internal API - User Management & Permissions", () => { const body: User = { ...userInfoJson, roles: { - [app.appId?.toString() || ""]: "ADMIN", + [app.appId]: "ADMIN", } } await config.users.updateInfo(body) @@ -147,7 +147,7 @@ describe("Internal API - User Management & Permissions", () => { const body: User = { ...userInfoJson, roles: { - [app.appId?.toString() || ""]: "POWER", + [app.appId]: "POWER", } } await config.users.updateInfo(body) From 300b0b7b671a8b702e853992dfa1cb5bd1bcbbd0 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Sun, 11 Dec 2022 11:07:14 +0000 Subject: [PATCH 16/43] Add access tests for tables --- .../internal-api/TestConfiguration/tables.ts | 8 + .../TestConfiguration/userManagement.ts | 1 + .../internal-api/fixtures/userManagement.ts | 1 - .../userManagement/userManagement.spec.ts | 143 +++++++++++++++++- 4 files changed, 147 insertions(+), 6 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/tables.ts b/qa-core/src/config/internal-api/TestConfiguration/tables.ts index 5b7e1648a0..5e52b71c94 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/tables.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/tables.ts @@ -39,6 +39,14 @@ export default class TablesApi { return [response, json] } + async forbiddenSave(body: any): Promise<[Response, Table]> { + const response = await this.api.post(`/tables`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(403) + + return [response, json] + } + async delete( id: string, revId: string diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index e323c3a098..e602c37c8a 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -33,6 +33,7 @@ export default class UserManagementApi { return [response, json] } + // This endpoint is used for one or more users when we want add users with passwords set. async addMultiple(userList: Partial[]): Promise<[Response, any]> { const body = { create: { diff --git a/qa-core/src/config/internal-api/fixtures/userManagement.ts b/qa-core/src/config/internal-api/fixtures/userManagement.ts index 446ae3b0c5..c036589089 100644 --- a/qa-core/src/config/internal-api/fixtures/userManagement.ts +++ b/qa-core/src/config/internal-api/fixtures/userManagement.ts @@ -1,6 +1,5 @@ import generator from "../../generator"; import { User } from "@budibase/types"; -import { generateUserMetadataID } from "@budibase/backend-core/src/db"; const generateDeveloper = (): Partial => { diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index e6277a5e7f..8110929b41 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -4,12 +4,15 @@ import InternalAPIClient from "../../../config/internal-api/TestConfiguration/In import generateApp from "../../../config/internal-api/fixtures/applications" import { generateUser } from "../../../config/internal-api/fixtures/userManagement" import { User } from "@budibase/types" +import { generateNewColumnForTable, generateTable } from "../../../config/internal-api/fixtures/table" +import generateScreen from "../../../config/internal-api/fixtures/screens" describe("Internal API - User Management & Permissions", () => { const api = new InternalAPIClient() const config = new TestConfiguration(api) - beforeAll(async () => { + // Before each test, login as admin. Some tests will require login as a different user + beforeEach(async () => { await config.loginAsAdmin() }) @@ -21,7 +24,6 @@ describe("Internal API - User Management & Permissions", () => { await config.users.search() await config.users.getRoles() - // These need to be saved to the context so the passwords can be used to login const admin = generateUser(1, "admin") expect(admin[0].builder?.global).toEqual(true) expect(admin[0].admin?.global).toEqual(true) @@ -31,9 +33,9 @@ describe("Internal API - User Management & Permissions", () => { expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) - await config.users.addMultiple(admin) - await config.users.addMultiple(developer) - await config.users.addMultiple(appUser) + const userList = [...admin, ...developer, ...appUser] + + await config.users.addMultiple(userList) const [allUsersResponse, allUsersJson] = await config.users.getAll() expect(allUsersJson.length).toBeGreaterThan(0) @@ -158,4 +160,135 @@ describe("Internal API - User Management & Permissions", () => { }) + it("Check Table access for app user", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "BASIC", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") + + const [createdTableResponse, createdTableData] = await config.tables.save( + generateTable() + ) + await config.login(appUser[0].email, appUser[0].password) + const newColumn = generateNewColumnForTable(createdTableData) + await config.tables.forbiddenSave( + newColumn) + await config.tables.forbiddenSave(generateTable()) + }) + //Incomplete Test + it("Check Screen access for app user", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "BASIC", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") + + const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) + }) + + it("Check Table access for developer", async () => { + const developer = generateUser(1, 'developer') + expect(developer[0].builder?.global).toEqual(true) + + const [createUserResponse, createUserJson] = await config.users.addMultiple(developer) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "POWER", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") + + const [createdTableResponse, createdTableData] = await config.tables.save( + generateTable() + ) + await config.login(developer[0].email, developer[0].password) + const newColumn = generateNewColumnForTable(createdTableData) + const [addColumnResponse, addColumnData] = await config.tables.save( + newColumn, + true + ) + }) + + it("Check Screen access for developer", async () => { + + }) + + it("Check Table access for admin", async () => { + const adminUser = generateUser(1, "admin") + expect(adminUser[0].builder?.global).toEqual(true) + expect(adminUser[0].admin?.global).toEqual(true) + const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "ADMIN", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") + + await config.login(adminUser[0].email, adminUser[0].password) + const [createdTableResponse, createdTableData] = await config.tables.save( + generateTable() + ) + const newColumn = generateNewColumnForTable(createdTableData) + const [addColumnResponse, addColumnData] = await config.tables.save( + newColumn, + true + ) + }) + + it("Check Screen access for admin", async () => { + + }) + }) From 5773f39659a9468043d190a542534ec45d974287 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Mon, 12 Dec 2022 16:32:37 +0000 Subject: [PATCH 17/43] Organize user and permissions tests --- .../userManagement/appSpecificRoles.spec.ts | 278 ++++++++++++++++++ .../userManagement/userManagement.spec.ts | 204 ------------- 2 files changed, 278 insertions(+), 204 deletions(-) create mode 100644 qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts diff --git a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts new file mode 100644 index 0000000000..3fb97cf847 --- /dev/null +++ b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts @@ -0,0 +1,278 @@ +import TestConfiguration from "../../../config/internal-api/TestConfiguration" +import { Application } from "@budibase/server/api/controllers/public/mapping/types" +import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" +import generateApp from "../../../config/internal-api/fixtures/applications" +import { generateUser } from "../../../config/internal-api/fixtures/userManagement" +import { User } from "@budibase/types" +import { generateNewColumnForTable, generateTable } from "../../../config/internal-api/fixtures/table" +import generateScreen from "../../../config/internal-api/fixtures/screens" + +describe("Internal API - App Specific Roles & Permissions", () => { + const api = new InternalAPIClient() + const config = new TestConfiguration(api) + + // Before each test, login as admin. Some tests will require login as a different user + beforeEach(async () => { + await config.loginAsAdmin() + }) + + afterAll(async () => { + await config.afterAll() + }) + + it("Add BASIC user to app", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "BASIC", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") + + }) + + it("Add ADMIN user to app", async () => { + const adminUser = generateUser(1, "admin") + expect(adminUser[0].builder?.global).toEqual(true) + expect(adminUser[0].admin?.global).toEqual(true) + const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "ADMIN", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") + + }) + + it("Add POWER user to app", async () => { + const powerUser = generateUser(1, 'developer') + expect(powerUser[0].builder?.global).toEqual(true) + + const [createUserResponse, createUserJson] = await config.users.addMultiple(powerUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "POWER", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") + + }) + + describe("Check Access for default roles", () => { + it("Check Table access for app user", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "BASIC", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") + + const [createdTableResponse, createdTableData] = await config.tables.save( + generateTable() + ) + await config.login(appUser[0].email, appUser[0].password) + const newColumn = generateNewColumnForTable(createdTableData) + await config.tables.forbiddenSave( + newColumn) + await config.tables.forbiddenSave(generateTable()) + }) + + it("Check Table access for developer", async () => { + const developer = generateUser(1, 'developer') + expect(developer[0].builder?.global).toEqual(true) + + const [createUserResponse, createUserJson] = await config.users.addMultiple(developer) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "POWER", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") + + const [createdTableResponse, createdTableData] = await config.tables.save( + generateTable() + ) + await config.login(developer[0].email, developer[0].password) + const newColumn = generateNewColumnForTable(createdTableData) + const [addColumnResponse, addColumnData] = await config.tables.save( + newColumn, + true + ) + }) + + it("Check Table access for admin", async () => { + const adminUser = generateUser(1, "admin") + expect(adminUser[0].builder?.global).toEqual(true) + expect(adminUser[0].admin?.global).toEqual(true) + const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "ADMIN", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") + + await config.login(adminUser[0].email, adminUser[0].password) + const [createdTableResponse, createdTableData] = await config.tables.save( + generateTable() + ) + const newColumn = generateNewColumnForTable(createdTableData) + const [addColumnResponse, addColumnData] = await config.tables.save( + newColumn, + true + ) + }) + + it("Check Screen access for BASIC Role", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "BASIC", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") + + const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) + + + }) + + it("Check Screen access for POWER role", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "POWER", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") + }) + + it("Check Screen access for ADMIN role", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const body: User = { + ...userInfoJson, + roles: { + [app.appId]: "ADMIN", + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[app.appId]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") + + }) + }) + + + describe.skip("App Access for custom roles", () => { + it("Custom role access for level 1 permissions", async () => { }) + it("Custom role access for level 2 permissions", async () => { }) + it("Custom role access for level 3 permissions", async () => { }) + it("Custom role access for level 4 permissions", async () => { }) + it("Custom role access for level 5 permissions", async () => { }) + }) + +}) \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts index 8110929b41..32820b8b7f 100644 --- a/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/userManagement.spec.ts @@ -1,11 +1,8 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { Application } from "@budibase/server/api/controllers/public/mapping/types" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" -import generateApp from "../../../config/internal-api/fixtures/applications" import { generateUser } from "../../../config/internal-api/fixtures/userManagement" import { User } from "@budibase/types" -import { generateNewColumnForTable, generateTable } from "../../../config/internal-api/fixtures/table" -import generateScreen from "../../../config/internal-api/fixtures/screens" describe("Internal API - User Management & Permissions", () => { const api = new InternalAPIClient() @@ -88,207 +85,6 @@ describe("Internal API - User Management & Permissions", () => { expect(changedUserInfoJson.builder?.global).toEqual(true) }) - it("Add BASIC user to app", async () => { - const appUser = generateUser() - expect(appUser[0].builder?.global).toEqual(false) - expect(appUser[0].admin?.global).toEqual(false) - const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "BASIC", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") - - }) - - it("Add ADMIN user to app", async () => { - const adminUser = generateUser(1, "admin") - expect(adminUser[0].builder?.global).toEqual(true) - expect(adminUser[0].admin?.global).toEqual(true) - const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) - - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "ADMIN", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") - - }) - - it("Add POWER user to app", async () => { - const powerUser = generateUser(1, 'developer') - expect(powerUser[0].builder?.global).toEqual(true) - - const [createUserResponse, createUserJson] = await config.users.addMultiple(powerUser) - - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "POWER", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") - - }) - - it("Check Table access for app user", async () => { - const appUser = generateUser() - expect(appUser[0].builder?.global).toEqual(false) - expect(appUser[0].admin?.global).toEqual(false) - const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) - - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "BASIC", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") - - const [createdTableResponse, createdTableData] = await config.tables.save( - generateTable() - ) - await config.login(appUser[0].email, appUser[0].password) - const newColumn = generateNewColumnForTable(createdTableData) - await config.tables.forbiddenSave( - newColumn) - await config.tables.forbiddenSave(generateTable()) - }) - //Incomplete Test - it("Check Screen access for app user", async () => { - const appUser = generateUser() - expect(appUser[0].builder?.global).toEqual(false) - expect(appUser[0].admin?.global).toEqual(false) - const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) - - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "BASIC", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") - - const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) - }) - - it("Check Table access for developer", async () => { - const developer = generateUser(1, 'developer') - expect(developer[0].builder?.global).toEqual(true) - - const [createUserResponse, createUserJson] = await config.users.addMultiple(developer) - - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "POWER", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") - - const [createdTableResponse, createdTableData] = await config.tables.save( - generateTable() - ) - await config.login(developer[0].email, developer[0].password) - const newColumn = generateNewColumnForTable(createdTableData) - const [addColumnResponse, addColumnData] = await config.tables.save( - newColumn, - true - ) - }) - - it("Check Screen access for developer", async () => { - - }) - - it("Check Table access for admin", async () => { - const adminUser = generateUser(1, "admin") - expect(adminUser[0].builder?.global).toEqual(true) - expect(adminUser[0].admin?.global).toEqual(true) - const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) - - const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId - - const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - const body: User = { - ...userInfoJson, - roles: { - [app.appId]: "ADMIN", - } - } - await config.users.updateInfo(body) - - const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") - - await config.login(adminUser[0].email, adminUser[0].password) - const [createdTableResponse, createdTableData] = await config.tables.save( - generateTable() - ) - const newColumn = generateNewColumnForTable(createdTableData) - const [addColumnResponse, addColumnData] = await config.tables.save( - newColumn, - true - ) - }) - - it("Check Screen access for admin", async () => { - - }) }) From d55172a9fb32eec9914a126f84547a02658af8fe Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Wed, 14 Dec 2022 23:15:02 +0000 Subject: [PATCH 18/43] Improve Role tests --- .../TestConfiguration/applications.ts | 10 +++++++- .../internal-api/fixtures/applications.ts | 17 +++++++++++-- .../applications/applications.spec.ts | 16 +++---------- .../internal-api/screens/screens.spec.ts | 2 +- .../userManagement/appSpecificRoles.spec.ts | 24 +++++++++++++------ 5 files changed, 45 insertions(+), 24 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/applications.ts b/qa-core/src/config/internal-api/TestConfiguration/applications.ts index 7eeda01f0e..53679e0bed 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/applications.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/applications.ts @@ -33,13 +33,21 @@ export default class AppApi { async canRender(): Promise<[Response, boolean]> { const response = await this.api.get("/routing/client") + expect(response).toHaveStatusCode(200) const json = await response.json() const publishedAppRenders = Object.keys(json.routes).length > 0 - expect(response).toHaveStatusCode(200) expect(publishedAppRenders).toBe(true) return [response, publishedAppRenders] } + async failRender(): Promise<[Response, responseMessage]> { + const response = await this.api.get("/routing/client") + const json = await response.json() + expect(response).toHaveStatusCode(404) + return [response, json] + } + + async getAppPackage(appId: string): Promise<[Response, AppPackageResponse]> { const response = await this.api.get(`/applications/${appId}/appPackage`) const json = await response.json() diff --git a/qa-core/src/config/internal-api/fixtures/applications.ts b/qa-core/src/config/internal-api/fixtures/applications.ts index 200aa9abff..0ce69bb889 100644 --- a/qa-core/src/config/internal-api/fixtures/applications.ts +++ b/qa-core/src/config/internal-api/fixtures/applications.ts @@ -1,7 +1,9 @@ import generator from "../../generator" import { Application } from "@budibase/server/api/controllers/public/mapping/types" +import { Template } from "@budibase/types" +import { App } from "@budibase/types" -const generate = ( +export const generateApp = ( overrides: Partial = {} ): Partial => ({ name: generator.word() + generator.hash(), @@ -9,4 +11,15 @@ const generate = ( ...overrides, }) -export default generate +// Applications type doesn't work here, save to add useTemplate parameter? +export const appFromTemplate = (): any => { + return ({ + name: generator.word(), + url: `/${generator.word()}`, + useTemplate: "true", + templateName: "Near Miss Register", + templateKey: "app/near-miss-register", + templateFile: undefined, + }) +} + diff --git a/qa-core/src/tests/internal-api/applications/applications.spec.ts b/qa-core/src/tests/internal-api/applications/applications.spec.ts index c7738152c4..2f0cdef411 100644 --- a/qa-core/src/tests/internal-api/applications/applications.spec.ts +++ b/qa-core/src/tests/internal-api/applications/applications.spec.ts @@ -2,7 +2,7 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { Application } from "@budibase/server/api/controllers/public/mapping/types" import { db } from "@budibase/backend-core" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" -import generateApp from "../../../config/internal-api/fixtures/applications" +import { generateApp, appFromTemplate } from "../../../config/internal-api/fixtures/applications" import generator from "../../../config/generator" import generateScreen from "../../../config/internal-api/fixtures/screens" @@ -18,16 +18,7 @@ describe("Internal API - Application creation, update, publish and delete", () = await config.afterAll() }) - async function createAppFromTemplate() { - return config.applications.create({ - name: generator.word(), - url: `/${generator.word()}`, - useTemplate: "true", - templateName: "Near Miss Register", - templateKey: "app/near-miss-register", - templateFile: undefined, - }) - } + it("Get applications without applications", async () => { await config.applications.fetchEmptyAppList() }) @@ -59,8 +50,7 @@ describe("Internal API - Application creation, update, publish and delete", () = it("Publish app", async () => { // create the app - const appName = generator.word() - const app = await createAppFromTemplate() + const app = await config.applications.create(appFromTemplate()) config.applications.api.appId = app.appId // check preview renders diff --git a/qa-core/src/tests/internal-api/screens/screens.spec.ts b/qa-core/src/tests/internal-api/screens/screens.spec.ts index 1af13d0a11..1d2a21a8c7 100644 --- a/qa-core/src/tests/internal-api/screens/screens.spec.ts +++ b/qa-core/src/tests/internal-api/screens/screens.spec.ts @@ -1,7 +1,7 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { App } from "@budibase/types" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" -import generateApp from "../../../config/internal-api/fixtures/applications" +import { generateApp, appFromTemplate } from "../../../config/internal-api/fixtures/applications" import { Screen } from "@budibase/types" import generateScreen from "../../../config/internal-api/fixtures/screens" diff --git a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts index 3fb97cf847..cfdd75f82e 100644 --- a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts @@ -1,11 +1,12 @@ import TestConfiguration from "../../../config/internal-api/TestConfiguration" import { Application } from "@budibase/server/api/controllers/public/mapping/types" import InternalAPIClient from "../../../config/internal-api/TestConfiguration/InternalAPIClient" -import generateApp from "../../../config/internal-api/fixtures/applications" +import { generateApp, appFromTemplate } from "../../../config/internal-api/fixtures/applications" import { generateUser } from "../../../config/internal-api/fixtures/userManagement" import { User } from "@budibase/types" import { generateNewColumnForTable, generateTable } from "../../../config/internal-api/fixtures/table" import generateScreen from "../../../config/internal-api/fixtures/screens" +import { db } from "@budibase/backend-core" describe("Internal API - App Specific Roles & Permissions", () => { const api = new InternalAPIClient() @@ -26,7 +27,7 @@ describe("Internal API - App Specific Roles & Permissions", () => { expect(appUser[0].admin?.global).toEqual(false) const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) - const app = await config.applications.create(generateApp()) + const app = await config.applications.create(appFromTemplate()) config.applications.api.appId = app.appId const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) @@ -50,7 +51,10 @@ describe("Internal API - App Specific Roles & Permissions", () => { expect(adminUser[0].admin?.global).toEqual(true) const [createUserResponse, createUserJson] = await config.users.addMultiple(adminUser) - const app = await config.applications.create(generateApp()) + //const app = await config.applications.create(generateApp()) + //config.applications.api.appId = app.appId + + const app = await config.applications.create(appFromTemplate()) config.applications.api.appId = app.appId const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) @@ -66,6 +70,12 @@ describe("Internal API - App Specific Roles & Permissions", () => { expect(changedUserInfoJson.roles[app.appId]).toBeDefined() expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") + // publish app + await config.applications.publish(app.url) + // check published app renders + config.applications.api.appId = db.getProdAppID(app.appId!) + await config.applications.canRender() + }) it("Add POWER user to app", async () => { @@ -190,7 +200,9 @@ describe("Internal API - App Specific Roles & Permissions", () => { true ) }) + }) + describe("Screen Access for App specific roles", () => { it("Check Screen access for BASIC Role", async () => { const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) @@ -265,9 +277,7 @@ describe("Internal API - App Specific Roles & Permissions", () => { }) }) - - - describe.skip("App Access for custom roles", () => { + describe.skip("Screen Access for custom roles", () => { it("Custom role access for level 1 permissions", async () => { }) it("Custom role access for level 2 permissions", async () => { }) it("Custom role access for level 3 permissions", async () => { }) @@ -275,4 +285,4 @@ describe("Internal API - App Specific Roles & Permissions", () => { it("Custom role access for level 5 permissions", async () => { }) }) -}) \ No newline at end of file +}) From a1ee10c1c6ab89af1988d89fed538823e6b21e7a Mon Sep 17 00:00:00 2001 From: FlaminWrap <97764630+FlaminWrap@users.noreply.github.com> Date: Thu, 15 Dec 2022 16:21:24 +0000 Subject: [PATCH 19/43] Button action for user prompt (#8676) * Commit for enhancement #7762 Added Question option for buttons which acts as a dialog prompting the user to confirm or cancel before continuing. * Fixes * Made changes to allow custom modal title Changed Question to User Prompt Allows custom title * Revert "Made changes to allow custom modal title" This reverts commit 42a43bef4914cd52b07a2b6964bf78aa50eb2707. * Revert "Fixes" This reverts commit 915a8718e5ac6dd32a6c3d377d5edb02fc8a3138. * Adds custom title Adds custom title * Wrong version of buttonActions was commited * Delete index.js * refactor * lint Co-authored-by: Mel O'Hagan --- .../actions/PromptUser.svelte | 50 +++++++++++++++++++ .../ButtonActionEditor/actions/index.js | 1 + .../controls/ButtonActionEditor/manifest.json | 5 ++ packages/client/src/utils/buttonActions.js | 12 ++++- 4 files changed, 66 insertions(+), 2 deletions(-) create mode 100644 packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/PromptUser.svelte diff --git a/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/PromptUser.svelte b/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/PromptUser.svelte new file mode 100644 index 0000000000..85d395e4f4 --- /dev/null +++ b/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/PromptUser.svelte @@ -0,0 +1,50 @@ + + +
+ Enter the message you wish to display to the user. +
+ + + + +
+
+ + diff --git a/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/index.js b/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/index.js index 4a9640312d..90ce1607e4 100644 --- a/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/index.js +++ b/packages/builder/src/components/design/settings/controls/ButtonActionEditor/actions/index.js @@ -16,5 +16,6 @@ export { default as ExportData } from "./ExportData.svelte" export { default as ContinueIf } from "./ContinueIf.svelte" export { default as UpdateFieldValue } from "./UpdateFieldValue.svelte" export { default as ShowNotification } from "./ShowNotification.svelte" +export { default as PromptUser } from "./PromptUser.svelte" export { default as OpenSidePanel } from "./OpenSidePanel.svelte" export { default as CloseSidePanel } from "./CloseSidePanel.svelte" diff --git a/packages/builder/src/components/design/settings/controls/ButtonActionEditor/manifest.json b/packages/builder/src/components/design/settings/controls/ButtonActionEditor/manifest.json index 521ad85f0a..7497990304 100644 --- a/packages/builder/src/components/design/settings/controls/ButtonActionEditor/manifest.json +++ b/packages/builder/src/components/design/settings/controls/ButtonActionEditor/manifest.json @@ -117,6 +117,11 @@ "component": "ShowNotification", "dependsOnFeature": "showNotificationAction" }, + { + "name": "Prompt User", + "type": "application", + "component": "PromptUser" + }, { "name": "Open Side Panel", "type": "application", diff --git a/packages/client/src/utils/buttonActions.js b/packages/client/src/utils/buttonActions.js index e471518285..06bc6f356a 100644 --- a/packages/client/src/utils/buttonActions.js +++ b/packages/client/src/utils/buttonActions.js @@ -327,6 +327,8 @@ const showNotificationHandler = action => { notificationStore.actions[type]?.(message, autoDismiss) } +const promptUserHandler = () => {} + const OpenSidePanelHandler = action => { const { id } = action.parameters if (id) { @@ -357,6 +359,7 @@ const handlerMap = { ["Export Data"]: exportDataHandler, ["Continue if / Stop if"]: continueIfHandler, ["Show Notification"]: showNotificationHandler, + ["Prompt User"]: promptUserHandler, ["Open Side Panel"]: OpenSidePanelHandler, ["Close Side Panel"]: CloseSidePanelHandler, } @@ -366,6 +369,7 @@ const confirmTextMap = { ["Save Row"]: "Are you sure you want to save this row?", ["Execute Query"]: "Are you sure you want to execute this query?", ["Trigger Automation"]: "Are you sure you want to trigger this automation?", + ["Prompt User"]: "Are you sure you want to contiune?", } /** @@ -417,8 +421,12 @@ export const enrichButtonActions = (actions, context) => { return new Promise(resolve => { const defaultText = confirmTextMap[action["##eventHandlerType"]] const confirmText = action.parameters?.confirmText || defaultText + + const defaultTitleText = action["##eventHandlerType"] + const customTitleText = + action.parameters?.customTitleText || defaultTitleText confirmationStore.actions.showConfirmation( - action["##eventHandlerType"], + customTitleText, confirmText, async () => { // When confirmed, execute this action immediately, @@ -429,7 +437,7 @@ export const enrichButtonActions = (actions, context) => { buttonContext.push(result) const newContext = { ...context, actions: buttonContext } - // Enrich and call the next button action + // Enrich and call the next button action if there is more than one action remaining const next = enrichButtonActions( actions.slice(i + 1), newContext From 03b8d7b439fd17307f76f440e024c9a1bac5dc31 Mon Sep 17 00:00:00 2001 From: Budibase Staging Release Bot <> Date: Thu, 15 Dec 2022 16:38:10 +0000 Subject: [PATCH 20/43] v2.2.4-alpha.3 --- lerna.json | 2 +- packages/backend-core/package.json | 4 ++-- packages/bbui/package.json | 4 ++-- packages/builder/package.json | 10 +++++----- packages/cli/package.json | 8 ++++---- packages/client/package.json | 8 ++++---- packages/frontend-core/package.json | 4 ++-- packages/sdk/package.json | 2 +- packages/server/package.json | 10 +++++----- packages/string-templates/package.json | 2 +- packages/types/package.json | 2 +- packages/worker/package.json | 8 ++++---- 12 files changed, 32 insertions(+), 32 deletions(-) diff --git a/lerna.json b/lerna.json index 439190499e..f61ae22758 100644 --- a/lerna.json +++ b/lerna.json @@ -1,5 +1,5 @@ { - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "npmClient": "yarn", "packages": [ "packages/*" diff --git a/packages/backend-core/package.json b/packages/backend-core/package.json index dd36746391..b432264fab 100644 --- a/packages/backend-core/package.json +++ b/packages/backend-core/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/backend-core", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase backend core libraries used in server and worker", "main": "dist/src/index.js", "types": "dist/src/index.d.ts", @@ -21,7 +21,7 @@ }, "dependencies": { "@budibase/nano": "10.1.1", - "@budibase/types": "2.2.4-alpha.2", + "@budibase/types": "2.2.4-alpha.3", "@shopify/jest-koa-mocks": "5.0.1", "@techpass/passport-openidconnect": "0.3.2", "aws-cloudfront-sign": "2.2.0", diff --git a/packages/bbui/package.json b/packages/bbui/package.json index 20e727f0c6..3864ba41da 100644 --- a/packages/bbui/package.json +++ b/packages/bbui/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/bbui", "description": "A UI solution used in the different Budibase projects.", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "license": "MPL-2.0", "svelte": "src/index.js", "module": "dist/bbui.es.js", @@ -38,7 +38,7 @@ ], "dependencies": { "@adobe/spectrum-css-workflow-icons": "1.2.1", - "@budibase/string-templates": "2.2.4-alpha.2", + "@budibase/string-templates": "2.2.4-alpha.3", "@spectrum-css/actionbutton": "1.0.1", "@spectrum-css/actiongroup": "1.0.1", "@spectrum-css/avatar": "3.0.2", diff --git a/packages/builder/package.json b/packages/builder/package.json index b1d31891c7..8c344a1e8f 100644 --- a/packages/builder/package.json +++ b/packages/builder/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/builder", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "license": "GPL-3.0", "private": true, "scripts": { @@ -71,10 +71,10 @@ } }, "dependencies": { - "@budibase/bbui": "2.2.4-alpha.2", - "@budibase/client": "2.2.4-alpha.2", - "@budibase/frontend-core": "2.2.4-alpha.2", - "@budibase/string-templates": "2.2.4-alpha.2", + "@budibase/bbui": "2.2.4-alpha.3", + "@budibase/client": "2.2.4-alpha.3", + "@budibase/frontend-core": "2.2.4-alpha.3", + "@budibase/string-templates": "2.2.4-alpha.3", "@sentry/browser": "5.19.1", "@spectrum-css/page": "^3.0.1", "@spectrum-css/vars": "^3.0.1", diff --git a/packages/cli/package.json b/packages/cli/package.json index b4ec4dc6fb..04ce554cd7 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/cli", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase CLI, for developers, self hosting and migrations.", "main": "src/index.js", "bin": { @@ -26,9 +26,9 @@ "outputPath": "build" }, "dependencies": { - "@budibase/backend-core": "2.2.4-alpha.2", - "@budibase/string-templates": "2.2.4-alpha.2", - "@budibase/types": "2.2.4-alpha.2", + "@budibase/backend-core": "2.2.4-alpha.3", + "@budibase/string-templates": "2.2.4-alpha.3", + "@budibase/types": "2.2.4-alpha.3", "axios": "0.21.2", "chalk": "4.1.0", "cli-progress": "3.11.2", diff --git a/packages/client/package.json b/packages/client/package.json index 56ac723814..79599b1805 100644 --- a/packages/client/package.json +++ b/packages/client/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/client", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "license": "MPL-2.0", "module": "dist/budibase-client.js", "main": "dist/budibase-client.js", @@ -19,9 +19,9 @@ "dev:builder": "rollup -cw" }, "dependencies": { - "@budibase/bbui": "2.2.4-alpha.2", - "@budibase/frontend-core": "2.2.4-alpha.2", - "@budibase/string-templates": "2.2.4-alpha.2", + "@budibase/bbui": "2.2.4-alpha.3", + "@budibase/frontend-core": "2.2.4-alpha.3", + "@budibase/string-templates": "2.2.4-alpha.3", "@spectrum-css/button": "^3.0.3", "@spectrum-css/card": "^3.0.3", "@spectrum-css/divider": "^1.0.3", diff --git a/packages/frontend-core/package.json b/packages/frontend-core/package.json index caad86f712..b07847be2b 100644 --- a/packages/frontend-core/package.json +++ b/packages/frontend-core/package.json @@ -1,12 +1,12 @@ { "name": "@budibase/frontend-core", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase frontend core libraries used in builder and client", "author": "Budibase", "license": "MPL-2.0", "svelte": "src/index.js", "dependencies": { - "@budibase/bbui": "2.2.4-alpha.2", + "@budibase/bbui": "2.2.4-alpha.3", "lodash": "^4.17.21", "svelte": "^3.46.2" } diff --git a/packages/sdk/package.json b/packages/sdk/package.json index 06e58c1448..d42a4b0db1 100644 --- a/packages/sdk/package.json +++ b/packages/sdk/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/sdk", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase Public API SDK", "author": "Budibase", "license": "MPL-2.0", diff --git a/packages/server/package.json b/packages/server/package.json index 5a1a0a0d9f..72de0d3434 100644 --- a/packages/server/package.json +++ b/packages/server/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/server", "email": "hi@budibase.com", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase Web Server", "main": "src/index.ts", "repository": { @@ -43,11 +43,11 @@ "license": "GPL-3.0", "dependencies": { "@apidevtools/swagger-parser": "10.0.3", - "@budibase/backend-core": "2.2.4-alpha.2", - "@budibase/client": "2.2.4-alpha.2", + "@budibase/backend-core": "2.2.4-alpha.3", + "@budibase/client": "2.2.4-alpha.3", "@budibase/pro": "2.2.4-alpha.2", - "@budibase/string-templates": "2.2.4-alpha.2", - "@budibase/types": "2.2.4-alpha.2", + "@budibase/string-templates": "2.2.4-alpha.3", + "@budibase/types": "2.2.4-alpha.3", "@bull-board/api": "3.7.0", "@bull-board/koa": "3.9.4", "@elastic/elasticsearch": "7.10.0", diff --git a/packages/string-templates/package.json b/packages/string-templates/package.json index 00875c759d..2486e1bb63 100644 --- a/packages/string-templates/package.json +++ b/packages/string-templates/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/string-templates", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Handlebars wrapper for Budibase templating.", "main": "src/index.cjs", "module": "dist/bundle.mjs", diff --git a/packages/types/package.json b/packages/types/package.json index 523df6b045..5acd23a83f 100644 --- a/packages/types/package.json +++ b/packages/types/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/types", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase types", "main": "dist/index.js", "types": "dist/index.d.ts", diff --git a/packages/worker/package.json b/packages/worker/package.json index 185b90eb7e..bdbd96fd29 100644 --- a/packages/worker/package.json +++ b/packages/worker/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/worker", "email": "hi@budibase.com", - "version": "2.2.4-alpha.2", + "version": "2.2.4-alpha.3", "description": "Budibase background service", "main": "src/index.ts", "repository": { @@ -36,10 +36,10 @@ "author": "Budibase", "license": "GPL-3.0", "dependencies": { - "@budibase/backend-core": "2.2.4-alpha.2", + "@budibase/backend-core": "2.2.4-alpha.3", "@budibase/pro": "2.2.4-alpha.2", - "@budibase/string-templates": "2.2.4-alpha.2", - "@budibase/types": "2.2.4-alpha.2", + "@budibase/string-templates": "2.2.4-alpha.3", + "@budibase/types": "2.2.4-alpha.3", "@koa/router": "8.0.8", "@sentry/node": "6.17.7", "@techpass/passport-openidconnect": "0.3.2", From 0e8dd810346ebbc0dcd5f4423cbf5a7fdeecf4eb Mon Sep 17 00:00:00 2001 From: Budibase Staging Release Bot <> Date: Thu, 15 Dec 2022 16:42:29 +0000 Subject: [PATCH 21/43] Update pro version to 2.2.4-alpha.3 --- packages/server/package.json | 2 +- packages/server/yarn.lock | 30 +++++++++++++++--------------- packages/worker/package.json | 2 +- packages/worker/yarn.lock | 30 +++++++++++++++--------------- 4 files changed, 32 insertions(+), 32 deletions(-) diff --git a/packages/server/package.json b/packages/server/package.json index 72de0d3434..4067c96490 100644 --- a/packages/server/package.json +++ b/packages/server/package.json @@ -45,7 +45,7 @@ "@apidevtools/swagger-parser": "10.0.3", "@budibase/backend-core": "2.2.4-alpha.3", "@budibase/client": "2.2.4-alpha.3", - "@budibase/pro": "2.2.4-alpha.2", + "@budibase/pro": "2.2.4-alpha.3", "@budibase/string-templates": "2.2.4-alpha.3", "@budibase/types": "2.2.4-alpha.3", "@bull-board/api": "3.7.0", diff --git a/packages/server/yarn.lock b/packages/server/yarn.lock index c04560642a..94cdc996c8 100644 --- a/packages/server/yarn.lock +++ b/packages/server/yarn.lock @@ -1273,13 +1273,13 @@ resolved "https://registry.yarnpkg.com/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz#75a2e8b51cb758a7553d6804a5932d7aace75c39" integrity sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw== -"@budibase/backend-core@2.2.4-alpha.2": - version "2.2.4-alpha.2" - resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.2.tgz#7942695880cd5677d91dd1fc85deb0f13769bed1" - integrity sha512-2VMZjKeojP9S0aDKeK8y/I1xY5XoIWHmioqwydppG9R0hIRk2MsxNAg6XxcPMHFEwV2AJc9TX9byDo+qXKyvlw== +"@budibase/backend-core@2.2.4-alpha.3": + version "2.2.4-alpha.3" + resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.3.tgz#9651f883f94a8ad2f16078851a8d564ef05a2d0a" + integrity sha512-aJ5qLauH4wk6zFVjlpuy7+qpOgCDH+K5IaGQBMFBTswV/cZGmX5j6VkZin57CTZ/6RfaujvifAcDy90UDl8PRA== dependencies: "@budibase/nano" "10.1.1" - "@budibase/types" "2.2.4-alpha.2" + "@budibase/types" "2.2.4-alpha.3" "@shopify/jest-koa-mocks" "5.0.1" "@techpass/passport-openidconnect" "0.3.2" aws-cloudfront-sign "2.2.0" @@ -1373,13 +1373,13 @@ qs "^6.11.0" tough-cookie "^4.1.2" -"@budibase/pro@2.2.4-alpha.2": - version "2.2.4-alpha.2" - resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.2.tgz#1e1a26b9194669aed1737d1245be45b448a6e889" - integrity sha512-jqOuLIUqFyphG9K0Ovly2ipVdAMZ7yvqLo74S3KwVu74Rk5Ab7rBw4DecOdKvGbu/r0ssNdXDXv8bns/P6I2ng== +"@budibase/pro@2.2.4-alpha.3": + version "2.2.4-alpha.3" + resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.3.tgz#e872bc5db00716b3a3f180d2588c0cea5e3fb550" + integrity sha512-qHGgYdK1ny7gt73Qn3heAzadp3jqNQsJHuk9HEkmTIp5frvreya7J7FcA1thi6w2isUMxydk0bKegalDyT3fnA== dependencies: - "@budibase/backend-core" "2.2.4-alpha.2" - "@budibase/types" "2.2.4-alpha.2" + "@budibase/backend-core" "2.2.4-alpha.3" + "@budibase/types" "2.2.4-alpha.3" "@koa/router" "8.0.8" bull "4.10.1" joi "17.6.0" @@ -1404,10 +1404,10 @@ svelte-apexcharts "^1.0.2" svelte-flatpickr "^3.1.0" -"@budibase/types@2.2.4-alpha.2": - version "2.2.4-alpha.2" - resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.2.tgz#56503aee0e1294ca5b27338f229290dc4739c79a" - integrity sha512-Z8VcC/TjuBz0SoFPRD+Kj1B0w5w4lNpSXQWecsHp9ne72vG788LrMeoepBnXMw/icNof1cG/vu7J/sr4ONzQTg== +"@budibase/types@2.2.4-alpha.3": + version "2.2.4-alpha.3" + resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.3.tgz#23009c111ecc46aa99b29f97176c68c39bce5180" + integrity sha512-w0UxNeea1wV3DChKHNckxkAYfnirKXyWJLyLCyq1U4z5p2XADmHKmL7LTdFCWZPJzbH+JmtXgNYm7+Nt9h6ogw== "@bull-board/api@3.7.0": version "3.7.0" diff --git a/packages/worker/package.json b/packages/worker/package.json index bdbd96fd29..f5ec959871 100644 --- a/packages/worker/package.json +++ b/packages/worker/package.json @@ -37,7 +37,7 @@ "license": "GPL-3.0", "dependencies": { "@budibase/backend-core": "2.2.4-alpha.3", - "@budibase/pro": "2.2.4-alpha.2", + "@budibase/pro": "2.2.4-alpha.3", "@budibase/string-templates": "2.2.4-alpha.3", "@budibase/types": "2.2.4-alpha.3", "@koa/router": "8.0.8", diff --git a/packages/worker/yarn.lock b/packages/worker/yarn.lock index e3eb4f73d7..a5c6e6c627 100644 --- a/packages/worker/yarn.lock +++ b/packages/worker/yarn.lock @@ -470,13 +470,13 @@ resolved "https://registry.yarnpkg.com/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz#75a2e8b51cb758a7553d6804a5932d7aace75c39" integrity sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw== -"@budibase/backend-core@2.2.4-alpha.2": - version "2.2.4-alpha.2" - resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.2.tgz#7942695880cd5677d91dd1fc85deb0f13769bed1" - integrity sha512-2VMZjKeojP9S0aDKeK8y/I1xY5XoIWHmioqwydppG9R0hIRk2MsxNAg6XxcPMHFEwV2AJc9TX9byDo+qXKyvlw== +"@budibase/backend-core@2.2.4-alpha.3": + version "2.2.4-alpha.3" + resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.3.tgz#9651f883f94a8ad2f16078851a8d564ef05a2d0a" + integrity sha512-aJ5qLauH4wk6zFVjlpuy7+qpOgCDH+K5IaGQBMFBTswV/cZGmX5j6VkZin57CTZ/6RfaujvifAcDy90UDl8PRA== dependencies: "@budibase/nano" "10.1.1" - "@budibase/types" "2.2.4-alpha.2" + "@budibase/types" "2.2.4-alpha.3" "@shopify/jest-koa-mocks" "5.0.1" "@techpass/passport-openidconnect" "0.3.2" aws-cloudfront-sign "2.2.0" @@ -520,23 +520,23 @@ qs "^6.11.0" tough-cookie "^4.1.2" -"@budibase/pro@2.2.4-alpha.2": - version "2.2.4-alpha.2" - resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.2.tgz#1e1a26b9194669aed1737d1245be45b448a6e889" - integrity sha512-jqOuLIUqFyphG9K0Ovly2ipVdAMZ7yvqLo74S3KwVu74Rk5Ab7rBw4DecOdKvGbu/r0ssNdXDXv8bns/P6I2ng== +"@budibase/pro@2.2.4-alpha.3": + version "2.2.4-alpha.3" + resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.3.tgz#e872bc5db00716b3a3f180d2588c0cea5e3fb550" + integrity sha512-qHGgYdK1ny7gt73Qn3heAzadp3jqNQsJHuk9HEkmTIp5frvreya7J7FcA1thi6w2isUMxydk0bKegalDyT3fnA== dependencies: - "@budibase/backend-core" "2.2.4-alpha.2" - "@budibase/types" "2.2.4-alpha.2" + "@budibase/backend-core" "2.2.4-alpha.3" + "@budibase/types" "2.2.4-alpha.3" "@koa/router" "8.0.8" bull "4.10.1" joi "17.6.0" jsonwebtoken "8.5.1" node-fetch "^2.6.1" -"@budibase/types@2.2.4-alpha.2": - version "2.2.4-alpha.2" - resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.2.tgz#56503aee0e1294ca5b27338f229290dc4739c79a" - integrity sha512-Z8VcC/TjuBz0SoFPRD+Kj1B0w5w4lNpSXQWecsHp9ne72vG788LrMeoepBnXMw/icNof1cG/vu7J/sr4ONzQTg== +"@budibase/types@2.2.4-alpha.3": + version "2.2.4-alpha.3" + resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.3.tgz#23009c111ecc46aa99b29f97176c68c39bce5180" + integrity sha512-w0UxNeea1wV3DChKHNckxkAYfnirKXyWJLyLCyq1U4z5p2XADmHKmL7LTdFCWZPJzbH+JmtXgNYm7+Nt9h6ogw== "@cspotcode/source-map-support@^0.8.0": version "0.8.1" From f4a39080dee3176d91f3f26a0e4b55b4b13a04e3 Mon Sep 17 00:00:00 2001 From: Rory Powell Date: Fri, 16 Dec 2022 11:14:31 +0000 Subject: [PATCH 22/43] Minio and local licensing fixes (#9071) --- packages/backend-core/src/objectStore/objectStore.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/backend-core/src/objectStore/objectStore.ts b/packages/backend-core/src/objectStore/objectStore.ts index 89e1c88e10..1cc8ad3add 100644 --- a/packages/backend-core/src/objectStore/objectStore.ts +++ b/packages/backend-core/src/objectStore/objectStore.ts @@ -86,7 +86,7 @@ export const ObjectStore = ( // custom S3 is in use i.e. minio if (env.MINIO_URL) { - if (opts.presigning && !env.MINIO_ENABLED) { + if (opts.presigning && env.MINIO_ENABLED) { // IMPORTANT: Signed urls will inspect the host header of the request. // Normally a signed url will need to be generated with a specified host in mind. // To support dynamic hosts, e.g. some unknown self-hosted installation url, From 0fa1e7b97bb3949d2fbd091d866321dee7e11f7b Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 16 Dec 2022 11:24:16 +0000 Subject: [PATCH 23/43] Add tests for app specific roles --- .../internal-api/TestConfiguration/auth.ts | 1 + .../TestConfiguration/userManagement.ts | 9 +++++ .../userManagement/appSpecificRoles.spec.ts | 33 +++++++++++++++++++ 3 files changed, 43 insertions(+) diff --git a/qa-core/src/config/internal-api/TestConfiguration/auth.ts b/qa-core/src/config/internal-api/TestConfiguration/auth.ts index d72502b417..3fe57c50be 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/auth.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/auth.ts @@ -27,6 +27,7 @@ export default class AuthApi { password: password, }, }) + expect(response).toHaveStatusCode(200) const cookie = response.headers.get("set-cookie") this.api.cookie = cookie as any return [response, cookie] diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index e602c37c8a..b10eafa217 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -115,4 +115,13 @@ export default class UserManagementApi { expect(response).toHaveStatusCode(200) return [response, json] } + + async changeSelfPassword(body: Partial): Promise<[Response, User]> { + const response = await this.api.post(`/global/self`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + expect(json._id).toEqual(body._id) + expect(json._rev).not.toEqual(body._rev) + return [response, json] + } } \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts index cfdd75f82e..f375cf3158 100644 --- a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts @@ -226,8 +226,26 @@ describe("Internal API - App Specific Roles & Permissions", () => { expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) + const [powerScreenResponse, powerScreenJson] = await config.screen.create(generateScreen("POWER")) + const [adminScreenResponse, adminScreenJson] = await config.screen.create(generateScreen("ADMIN")) + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + await config.login(appUser[0].email, appUser[0].password) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + //Update password + const userWithNewPassword = { + ...selfInfoJson, + password: appUser[0].password + } + await config.users.changeSelfPassword(userWithNewPassword) + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(1) + expect(appPackageJson.screens[0].routing.roleId).toEqual("BASIC") }) it("Check Screen access for POWER role", async () => { @@ -251,6 +269,21 @@ describe("Internal API - App Specific Roles & Permissions", () => { const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId]).toBeDefined() expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") + + const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) + const [powerScreenResponse, powerScreenJson] = await config.screen.create(generateScreen("POWER")) + const [adminScreenResponse, adminScreenJson] = await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + await config.login(appUser[0].email, appUser[0].password) + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(2) + expect(appPackageJson.screens[0].routing.roleId).toEqual("BASIC") }) it("Check Screen access for ADMIN role", async () => { From 4760a76978fd017651000c7254ff06ab0a9c0663 Mon Sep 17 00:00:00 2001 From: Budibase Staging Release Bot <> Date: Fri, 16 Dec 2022 11:33:20 +0000 Subject: [PATCH 24/43] v2.2.4-alpha.4 --- lerna.json | 2 +- packages/backend-core/package.json | 4 ++-- packages/bbui/package.json | 4 ++-- packages/builder/package.json | 10 +++++----- packages/cli/package.json | 8 ++++---- packages/client/package.json | 8 ++++---- packages/frontend-core/package.json | 4 ++-- packages/sdk/package.json | 2 +- packages/server/package.json | 10 +++++----- packages/string-templates/package.json | 2 +- packages/types/package.json | 2 +- packages/worker/package.json | 8 ++++---- 12 files changed, 32 insertions(+), 32 deletions(-) diff --git a/lerna.json b/lerna.json index f61ae22758..6073b88ae5 100644 --- a/lerna.json +++ b/lerna.json @@ -1,5 +1,5 @@ { - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "npmClient": "yarn", "packages": [ "packages/*" diff --git a/packages/backend-core/package.json b/packages/backend-core/package.json index b432264fab..1f4af2ad63 100644 --- a/packages/backend-core/package.json +++ b/packages/backend-core/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/backend-core", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase backend core libraries used in server and worker", "main": "dist/src/index.js", "types": "dist/src/index.d.ts", @@ -21,7 +21,7 @@ }, "dependencies": { "@budibase/nano": "10.1.1", - "@budibase/types": "2.2.4-alpha.3", + "@budibase/types": "2.2.4-alpha.4", "@shopify/jest-koa-mocks": "5.0.1", "@techpass/passport-openidconnect": "0.3.2", "aws-cloudfront-sign": "2.2.0", diff --git a/packages/bbui/package.json b/packages/bbui/package.json index 3864ba41da..1243cc5b4b 100644 --- a/packages/bbui/package.json +++ b/packages/bbui/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/bbui", "description": "A UI solution used in the different Budibase projects.", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "license": "MPL-2.0", "svelte": "src/index.js", "module": "dist/bbui.es.js", @@ -38,7 +38,7 @@ ], "dependencies": { "@adobe/spectrum-css-workflow-icons": "1.2.1", - "@budibase/string-templates": "2.2.4-alpha.3", + "@budibase/string-templates": "2.2.4-alpha.4", "@spectrum-css/actionbutton": "1.0.1", "@spectrum-css/actiongroup": "1.0.1", "@spectrum-css/avatar": "3.0.2", diff --git a/packages/builder/package.json b/packages/builder/package.json index 8c344a1e8f..4926ce4107 100644 --- a/packages/builder/package.json +++ b/packages/builder/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/builder", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "license": "GPL-3.0", "private": true, "scripts": { @@ -71,10 +71,10 @@ } }, "dependencies": { - "@budibase/bbui": "2.2.4-alpha.3", - "@budibase/client": "2.2.4-alpha.3", - "@budibase/frontend-core": "2.2.4-alpha.3", - "@budibase/string-templates": "2.2.4-alpha.3", + "@budibase/bbui": "2.2.4-alpha.4", + "@budibase/client": "2.2.4-alpha.4", + "@budibase/frontend-core": "2.2.4-alpha.4", + "@budibase/string-templates": "2.2.4-alpha.4", "@sentry/browser": "5.19.1", "@spectrum-css/page": "^3.0.1", "@spectrum-css/vars": "^3.0.1", diff --git a/packages/cli/package.json b/packages/cli/package.json index 04ce554cd7..2a8ab02ced 100644 --- a/packages/cli/package.json +++ b/packages/cli/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/cli", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase CLI, for developers, self hosting and migrations.", "main": "src/index.js", "bin": { @@ -26,9 +26,9 @@ "outputPath": "build" }, "dependencies": { - "@budibase/backend-core": "2.2.4-alpha.3", - "@budibase/string-templates": "2.2.4-alpha.3", - "@budibase/types": "2.2.4-alpha.3", + "@budibase/backend-core": "2.2.4-alpha.4", + "@budibase/string-templates": "2.2.4-alpha.4", + "@budibase/types": "2.2.4-alpha.4", "axios": "0.21.2", "chalk": "4.1.0", "cli-progress": "3.11.2", diff --git a/packages/client/package.json b/packages/client/package.json index 79599b1805..b1bc035062 100644 --- a/packages/client/package.json +++ b/packages/client/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/client", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "license": "MPL-2.0", "module": "dist/budibase-client.js", "main": "dist/budibase-client.js", @@ -19,9 +19,9 @@ "dev:builder": "rollup -cw" }, "dependencies": { - "@budibase/bbui": "2.2.4-alpha.3", - "@budibase/frontend-core": "2.2.4-alpha.3", - "@budibase/string-templates": "2.2.4-alpha.3", + "@budibase/bbui": "2.2.4-alpha.4", + "@budibase/frontend-core": "2.2.4-alpha.4", + "@budibase/string-templates": "2.2.4-alpha.4", "@spectrum-css/button": "^3.0.3", "@spectrum-css/card": "^3.0.3", "@spectrum-css/divider": "^1.0.3", diff --git a/packages/frontend-core/package.json b/packages/frontend-core/package.json index b07847be2b..df0bd1df5f 100644 --- a/packages/frontend-core/package.json +++ b/packages/frontend-core/package.json @@ -1,12 +1,12 @@ { "name": "@budibase/frontend-core", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase frontend core libraries used in builder and client", "author": "Budibase", "license": "MPL-2.0", "svelte": "src/index.js", "dependencies": { - "@budibase/bbui": "2.2.4-alpha.3", + "@budibase/bbui": "2.2.4-alpha.4", "lodash": "^4.17.21", "svelte": "^3.46.2" } diff --git a/packages/sdk/package.json b/packages/sdk/package.json index d42a4b0db1..c9d2887d80 100644 --- a/packages/sdk/package.json +++ b/packages/sdk/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/sdk", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase Public API SDK", "author": "Budibase", "license": "MPL-2.0", diff --git a/packages/server/package.json b/packages/server/package.json index 4067c96490..37850606e4 100644 --- a/packages/server/package.json +++ b/packages/server/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/server", "email": "hi@budibase.com", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase Web Server", "main": "src/index.ts", "repository": { @@ -43,11 +43,11 @@ "license": "GPL-3.0", "dependencies": { "@apidevtools/swagger-parser": "10.0.3", - "@budibase/backend-core": "2.2.4-alpha.3", - "@budibase/client": "2.2.4-alpha.3", + "@budibase/backend-core": "2.2.4-alpha.4", + "@budibase/client": "2.2.4-alpha.4", "@budibase/pro": "2.2.4-alpha.3", - "@budibase/string-templates": "2.2.4-alpha.3", - "@budibase/types": "2.2.4-alpha.3", + "@budibase/string-templates": "2.2.4-alpha.4", + "@budibase/types": "2.2.4-alpha.4", "@bull-board/api": "3.7.0", "@bull-board/koa": "3.9.4", "@elastic/elasticsearch": "7.10.0", diff --git a/packages/string-templates/package.json b/packages/string-templates/package.json index 2486e1bb63..e31c2f0f84 100644 --- a/packages/string-templates/package.json +++ b/packages/string-templates/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/string-templates", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Handlebars wrapper for Budibase templating.", "main": "src/index.cjs", "module": "dist/bundle.mjs", diff --git a/packages/types/package.json b/packages/types/package.json index 5acd23a83f..8fd504a244 100644 --- a/packages/types/package.json +++ b/packages/types/package.json @@ -1,6 +1,6 @@ { "name": "@budibase/types", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase types", "main": "dist/index.js", "types": "dist/index.d.ts", diff --git a/packages/worker/package.json b/packages/worker/package.json index f5ec959871..bc3f509286 100644 --- a/packages/worker/package.json +++ b/packages/worker/package.json @@ -1,7 +1,7 @@ { "name": "@budibase/worker", "email": "hi@budibase.com", - "version": "2.2.4-alpha.3", + "version": "2.2.4-alpha.4", "description": "Budibase background service", "main": "src/index.ts", "repository": { @@ -36,10 +36,10 @@ "author": "Budibase", "license": "GPL-3.0", "dependencies": { - "@budibase/backend-core": "2.2.4-alpha.3", + "@budibase/backend-core": "2.2.4-alpha.4", "@budibase/pro": "2.2.4-alpha.3", - "@budibase/string-templates": "2.2.4-alpha.3", - "@budibase/types": "2.2.4-alpha.3", + "@budibase/string-templates": "2.2.4-alpha.4", + "@budibase/types": "2.2.4-alpha.4", "@koa/router": "8.0.8", "@sentry/node": "6.17.7", "@techpass/passport-openidconnect": "0.3.2", From cf0bc606e43569084f1b383d0182d87ea88fdfd3 Mon Sep 17 00:00:00 2001 From: Budibase Staging Release Bot <> Date: Fri, 16 Dec 2022 11:37:35 +0000 Subject: [PATCH 25/43] Update pro version to 2.2.4-alpha.4 --- packages/server/package.json | 2 +- packages/server/yarn.lock | 30 +++++++++++++++--------------- packages/worker/package.json | 2 +- packages/worker/yarn.lock | 30 +++++++++++++++--------------- 4 files changed, 32 insertions(+), 32 deletions(-) diff --git a/packages/server/package.json b/packages/server/package.json index 37850606e4..d2e5770612 100644 --- a/packages/server/package.json +++ b/packages/server/package.json @@ -45,7 +45,7 @@ "@apidevtools/swagger-parser": "10.0.3", "@budibase/backend-core": "2.2.4-alpha.4", "@budibase/client": "2.2.4-alpha.4", - "@budibase/pro": "2.2.4-alpha.3", + "@budibase/pro": "2.2.4-alpha.4", "@budibase/string-templates": "2.2.4-alpha.4", "@budibase/types": "2.2.4-alpha.4", "@bull-board/api": "3.7.0", diff --git a/packages/server/yarn.lock b/packages/server/yarn.lock index 94cdc996c8..87977b6157 100644 --- a/packages/server/yarn.lock +++ b/packages/server/yarn.lock @@ -1273,13 +1273,13 @@ resolved "https://registry.yarnpkg.com/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz#75a2e8b51cb758a7553d6804a5932d7aace75c39" integrity sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw== -"@budibase/backend-core@2.2.4-alpha.3": - version "2.2.4-alpha.3" - resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.3.tgz#9651f883f94a8ad2f16078851a8d564ef05a2d0a" - integrity sha512-aJ5qLauH4wk6zFVjlpuy7+qpOgCDH+K5IaGQBMFBTswV/cZGmX5j6VkZin57CTZ/6RfaujvifAcDy90UDl8PRA== +"@budibase/backend-core@2.2.4-alpha.4": + version "2.2.4-alpha.4" + resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.4.tgz#c0b858936131ef4631c6baa2282482e089e6e9bf" + integrity sha512-CAK7cy6VSIAcQHpvD+yX4BHSglJ0pYEHIWfGjXVAk8iI0BDQg76NWhHNkuqko2bUhKxcGLe7J9hF5zWvY+J+/w== dependencies: "@budibase/nano" "10.1.1" - "@budibase/types" "2.2.4-alpha.3" + "@budibase/types" "2.2.4-alpha.4" "@shopify/jest-koa-mocks" "5.0.1" "@techpass/passport-openidconnect" "0.3.2" aws-cloudfront-sign "2.2.0" @@ -1373,13 +1373,13 @@ qs "^6.11.0" tough-cookie "^4.1.2" -"@budibase/pro@2.2.4-alpha.3": - version "2.2.4-alpha.3" - resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.3.tgz#e872bc5db00716b3a3f180d2588c0cea5e3fb550" - integrity sha512-qHGgYdK1ny7gt73Qn3heAzadp3jqNQsJHuk9HEkmTIp5frvreya7J7FcA1thi6w2isUMxydk0bKegalDyT3fnA== +"@budibase/pro@2.2.4-alpha.4": + version "2.2.4-alpha.4" + resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.4.tgz#e8eb302a227cd3ef24830ae4ccca32790221af09" + integrity sha512-484bPOjmo617tyd4L1qZfiBIN5IMZH7+J4f6QrUGtHYy1JfEf0W0A0ZIbLoC/U7a/6D/FhVPRLQU8aWYnr+BIw== dependencies: - "@budibase/backend-core" "2.2.4-alpha.3" - "@budibase/types" "2.2.4-alpha.3" + "@budibase/backend-core" "2.2.4-alpha.4" + "@budibase/types" "2.2.4-alpha.4" "@koa/router" "8.0.8" bull "4.10.1" joi "17.6.0" @@ -1404,10 +1404,10 @@ svelte-apexcharts "^1.0.2" svelte-flatpickr "^3.1.0" -"@budibase/types@2.2.4-alpha.3": - version "2.2.4-alpha.3" - resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.3.tgz#23009c111ecc46aa99b29f97176c68c39bce5180" - integrity sha512-w0UxNeea1wV3DChKHNckxkAYfnirKXyWJLyLCyq1U4z5p2XADmHKmL7LTdFCWZPJzbH+JmtXgNYm7+Nt9h6ogw== +"@budibase/types@2.2.4-alpha.4": + version "2.2.4-alpha.4" + resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.4.tgz#6f4ad1967546459efb49f8169e5d68147b90effc" + integrity sha512-VAPp8+FuM6lG2wUwVq9e7MvRnW/OBuNFDuB8vK2jUKxOMNu+C195DSQUBzVZGBgF/6R5pxnoLMfC0oJgftH7ww== "@bull-board/api@3.7.0": version "3.7.0" diff --git a/packages/worker/package.json b/packages/worker/package.json index bc3f509286..ac4c2bc403 100644 --- a/packages/worker/package.json +++ b/packages/worker/package.json @@ -37,7 +37,7 @@ "license": "GPL-3.0", "dependencies": { "@budibase/backend-core": "2.2.4-alpha.4", - "@budibase/pro": "2.2.4-alpha.3", + "@budibase/pro": "2.2.4-alpha.4", "@budibase/string-templates": "2.2.4-alpha.4", "@budibase/types": "2.2.4-alpha.4", "@koa/router": "8.0.8", diff --git a/packages/worker/yarn.lock b/packages/worker/yarn.lock index a5c6e6c627..aa2843fd03 100644 --- a/packages/worker/yarn.lock +++ b/packages/worker/yarn.lock @@ -470,13 +470,13 @@ resolved "https://registry.yarnpkg.com/@bcoe/v8-coverage/-/v8-coverage-0.2.3.tgz#75a2e8b51cb758a7553d6804a5932d7aace75c39" integrity sha512-0hYQ8SB4Db5zvZB4axdMHGwEaQjkZzFjQiN9LVYvIFB2nSUHW9tYpxWriPrWDASIxiaXax83REcLxuSdnGPZtw== -"@budibase/backend-core@2.2.4-alpha.3": - version "2.2.4-alpha.3" - resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.3.tgz#9651f883f94a8ad2f16078851a8d564ef05a2d0a" - integrity sha512-aJ5qLauH4wk6zFVjlpuy7+qpOgCDH+K5IaGQBMFBTswV/cZGmX5j6VkZin57CTZ/6RfaujvifAcDy90UDl8PRA== +"@budibase/backend-core@2.2.4-alpha.4": + version "2.2.4-alpha.4" + resolved "https://registry.yarnpkg.com/@budibase/backend-core/-/backend-core-2.2.4-alpha.4.tgz#c0b858936131ef4631c6baa2282482e089e6e9bf" + integrity sha512-CAK7cy6VSIAcQHpvD+yX4BHSglJ0pYEHIWfGjXVAk8iI0BDQg76NWhHNkuqko2bUhKxcGLe7J9hF5zWvY+J+/w== dependencies: "@budibase/nano" "10.1.1" - "@budibase/types" "2.2.4-alpha.3" + "@budibase/types" "2.2.4-alpha.4" "@shopify/jest-koa-mocks" "5.0.1" "@techpass/passport-openidconnect" "0.3.2" aws-cloudfront-sign "2.2.0" @@ -520,23 +520,23 @@ qs "^6.11.0" tough-cookie "^4.1.2" -"@budibase/pro@2.2.4-alpha.3": - version "2.2.4-alpha.3" - resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.3.tgz#e872bc5db00716b3a3f180d2588c0cea5e3fb550" - integrity sha512-qHGgYdK1ny7gt73Qn3heAzadp3jqNQsJHuk9HEkmTIp5frvreya7J7FcA1thi6w2isUMxydk0bKegalDyT3fnA== +"@budibase/pro@2.2.4-alpha.4": + version "2.2.4-alpha.4" + resolved "https://registry.yarnpkg.com/@budibase/pro/-/pro-2.2.4-alpha.4.tgz#e8eb302a227cd3ef24830ae4ccca32790221af09" + integrity sha512-484bPOjmo617tyd4L1qZfiBIN5IMZH7+J4f6QrUGtHYy1JfEf0W0A0ZIbLoC/U7a/6D/FhVPRLQU8aWYnr+BIw== dependencies: - "@budibase/backend-core" "2.2.4-alpha.3" - "@budibase/types" "2.2.4-alpha.3" + "@budibase/backend-core" "2.2.4-alpha.4" + "@budibase/types" "2.2.4-alpha.4" "@koa/router" "8.0.8" bull "4.10.1" joi "17.6.0" jsonwebtoken "8.5.1" node-fetch "^2.6.1" -"@budibase/types@2.2.4-alpha.3": - version "2.2.4-alpha.3" - resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.3.tgz#23009c111ecc46aa99b29f97176c68c39bce5180" - integrity sha512-w0UxNeea1wV3DChKHNckxkAYfnirKXyWJLyLCyq1U4z5p2XADmHKmL7LTdFCWZPJzbH+JmtXgNYm7+Nt9h6ogw== +"@budibase/types@2.2.4-alpha.4": + version "2.2.4-alpha.4" + resolved "https://registry.yarnpkg.com/@budibase/types/-/types-2.2.4-alpha.4.tgz#6f4ad1967546459efb49f8169e5d68147b90effc" + integrity sha512-VAPp8+FuM6lG2wUwVq9e7MvRnW/OBuNFDuB8vK2jUKxOMNu+C195DSQUBzVZGBgF/6R5pxnoLMfC0oJgftH7ww== "@cspotcode/source-map-support@^0.8.0": version "0.8.1" From c0eb8c039ad0cf80714e766ee37c0a14d23d6721 Mon Sep 17 00:00:00 2001 From: Martin McKeaveney Date: Fri, 16 Dec 2022 15:30:12 +0000 Subject: [PATCH 26/43] using production appID in BASIC screens test --- .../userManagement/appSpecificRoles.spec.ts | 50 ++++++++++--------- 1 file changed, 26 insertions(+), 24 deletions(-) diff --git a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts index f375cf3158..cda597bb8c 100644 --- a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts @@ -204,45 +204,48 @@ describe("Internal API - App Specific Roles & Permissions", () => { describe("Screen Access for App specific roles", () => { it("Check Screen access for BASIC Role", async () => { + // Set up user const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + // Create App const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId + // Update user roles const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID const body: User = { ...userInfoJson, roles: { - [app.appId]: "BASIC", + [prodAppId]: "BASIC", } } await config.users.updateInfo(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("BASIC") + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual("BASIC") - const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) - const [powerScreenResponse, powerScreenJson] = await config.screen.create(generateScreen("POWER")) - const [adminScreenResponse, adminScreenJson] = await config.screen.create(generateScreen("ADMIN")) + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) await config.applications.publish(app.url) const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) expect(firstappPackageJson.screens).toBeDefined() expect(firstappPackageJson.screens.length).toEqual(3) - await config.login(appUser[0].email, appUser[0].password) + // login with BASIC user + await config.login(appUser[0].email!, appUser[0].password!) const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() - //Update password - const userWithNewPassword = { - ...selfInfoJson, - password: appUser[0].password - } - await config.users.changeSelfPassword(userWithNewPassword) - const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId) + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) expect(appPackageJson.screens).toBeDefined() expect(appPackageJson.screens.length).toEqual(1) expect(appPackageJson.screens[0].routing.roleId).toEqual("BASIC") @@ -255,35 +258,35 @@ describe("Internal API - App Specific Roles & Permissions", () => { const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) const body: User = { ...userInfoJson, roles: { - [app.appId]: "POWER", + [app.appId!]: "POWER", } } await config.users.updateInfo(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("POWER") + expect(changedUserInfoJson.roles[app.appId!]).toBeDefined() + expect(changedUserInfoJson.roles[app.appId!]).toEqual("POWER") - const [basicScreenResponse, basicScreenJson] = await config.screen.create(generateScreen("BASIC")) - const [powerScreenResponse, powerScreenJson] = await config.screen.create(generateScreen("POWER")) - const [adminScreenResponse, adminScreenJson] = await config.screen.create(generateScreen("ADMIN")) + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) await config.applications.publish(app.url) - const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId!) expect(firstappPackageJson.screens).toBeDefined() expect(firstappPackageJson.screens.length).toEqual(3) - await config.login(appUser[0].email, appUser[0].password) + await config.login(appUser[0].email!, appUser[0].password!) const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId) expect(appPackageJson.screens).toBeDefined() expect(appPackageJson.screens.length).toEqual(2) - expect(appPackageJson.screens[0].routing.roleId).toEqual("BASIC") }) it("Check Screen access for ADMIN role", async () => { @@ -307,7 +310,6 @@ describe("Internal API - App Specific Roles & Permissions", () => { const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) expect(changedUserInfoJson.roles[app.appId]).toBeDefined() expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") - }) }) describe.skip("Screen Access for custom roles", () => { From 8cc8db7842f5612b2943e146d10cd62a9a4bd745 Mon Sep 17 00:00:00 2001 From: Pedro Silva Date: Fri, 16 Dec 2022 18:17:30 +0000 Subject: [PATCH 27/43] Add for app specific custom roles --- .../TestConfiguration/userManagement.ts | 10 +- .../userManagement/appSpecificRoles.spec.ts | 334 +++++++++++++++++- 2 files changed, 327 insertions(+), 17 deletions(-) diff --git a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts index b10eafa217..12a52034cc 100644 --- a/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts +++ b/qa-core/src/config/internal-api/TestConfiguration/userManagement.ts @@ -1,5 +1,5 @@ import { Response } from "node-fetch" -import { Role, User, UserDeletedEvent } from "@budibase/types" +import { Role, User, UserDeletedEvent, UserRoles } from "@budibase/types" import InternalAPIClient from "./InternalAPIClient" import { responseMessage } from "../fixtures/types/responseMessage" @@ -87,7 +87,6 @@ export default class UserManagementApi { const response = await this.api.get(`/roles`) const json = await response.json() expect(response).toHaveStatusCode(200) - expect(json.length).toEqual(4) return [response, json] } @@ -124,4 +123,11 @@ export default class UserManagementApi { expect(json._rev).not.toEqual(body._rev) return [response, json] } + + async createRole(body: Partial): Promise<[Response, UserRoles]> { + const response = await this.api.post(`/roles`, { body }) + const json = await response.json() + expect(response).toHaveStatusCode(200) + return [response, json] + } } \ No newline at end of file diff --git a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts index cda597bb8c..d27e846b22 100644 --- a/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts +++ b/qa-core/src/tests/internal-api/userManagement/appSpecificRoles.spec.ts @@ -252,72 +252,376 @@ describe("Internal API - App Specific Roles & Permissions", () => { }) it("Check Screen access for POWER role", async () => { + // Set up user const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + // Create App const app = await config.applications.create(generateApp()) - config.applications.api.appId = app.appId + // Update user roles const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID const body: User = { ...userInfoJson, roles: { - [app.appId!]: "POWER", + [prodAppId]: "POWER", } } await config.users.updateInfo(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId!]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId!]).toEqual("POWER") + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual("POWER") await config.screen.create(generateScreen("BASIC")) await config.screen.create(generateScreen("POWER")) await config.screen.create(generateScreen("ADMIN")) await config.applications.publish(app.url) - const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId!) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) expect(firstappPackageJson.screens).toBeDefined() expect(firstappPackageJson.screens.length).toEqual(3) + // login with POWER user await config.login(appUser[0].email!, appUser[0].password!) - const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) expect(appPackageJson.screens).toBeDefined() expect(appPackageJson.screens.length).toEqual(2) }) it("Check Screen access for ADMIN role", async () => { + // Set up user const appUser = generateUser() expect(appUser[0].builder?.global).toEqual(false) expect(appUser[0].admin?.global).toEqual(false) const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + // Create App const app = await config.applications.create(generateApp()) config.applications.api.appId = app.appId + // Update user roles const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID const body: User = { ...userInfoJson, roles: { - [app.appId]: "ADMIN", + [prodAppId]: "ADMIN", } } await config.users.updateInfo(body) const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) - expect(changedUserInfoJson.roles[app.appId]).toBeDefined() - expect(changedUserInfoJson.roles[app.appId]).toEqual("ADMIN") + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual("ADMIN") + + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + // login with ADMIN user + await config.login(appUser[0].email!, appUser[0].password!) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(3) }) }) - describe.skip("Screen Access for custom roles", () => { - it("Custom role access for level 1 permissions", async () => { }) - it("Custom role access for level 2 permissions", async () => { }) - it("Custom role access for level 3 permissions", async () => { }) - it("Custom role access for level 4 permissions", async () => { }) - it("Custom role access for level 5 permissions", async () => { }) + describe("Screen Access for custom roles", () => { + it("Custom role access for level 1 permissions", async () => { + // Set up user + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + // Create App + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + //Create level 1 role + const role = { + inherits: "BASIC", + permissionId: "public", + name: "level 1" + } + const [createRoleResponse, createRoleJson] = await config.users.createRole(role) + + + + // Update user roles + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID + const body: User = { + ...userInfoJson, + roles: { + [prodAppId]: createRoleJson._id, + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual(createRoleJson._id) + + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + // login with level 1 user + await config.login(appUser[0].email!, appUser[0].password!) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(1) + }) + it("Custom role access for level 2 permissions", async () => {// Set up user + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + // Create App + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + //Create level 1 role + const role = { + inherits: "BASIC", + permissionId: "read_only", + name: "level 2" + } + const [createRoleResponse, createRoleJson] = await config.users.createRole(role) + + + + // Update user roles + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID + const body: User = { + ...userInfoJson, + roles: { + [prodAppId]: createRoleJson._id, + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual(createRoleJson._id) + + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + // login with level 1 user + await config.login(appUser[0].email!, appUser[0].password!) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(1) + }) + it("Custom role access for level 3 permissions", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + // Create App + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + //Create level 1 role + const role = { + inherits: "BASIC", + permissionId: "write", + name: "level 3" + } + const [createRoleResponse, createRoleJson] = await config.users.createRole(role) + + + + // Update user roles + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID + const body: User = { + ...userInfoJson, + roles: { + [prodAppId]: createRoleJson._id, + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual(createRoleJson._id) + + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + // login with level 1 user + await config.login(appUser[0].email!, appUser[0].password!) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(1) + }) + it("Custom role access for level 4 permissions", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + // Create App + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + //Create level 1 role + const role = { + inherits: "BASIC", + permissionId: "power", + name: "level 4" + } + const [createRoleResponse, createRoleJson] = await config.users.createRole(role) + + + + // Update user roles + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID + const body: User = { + ...userInfoJson, + roles: { + [prodAppId]: createRoleJson._id, + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual(createRoleJson._id) + + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + // login with level 1 user + await config.login(appUser[0].email!, appUser[0].password!) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(1) + }) + it("Custom role access for level 5 permissions", async () => { + const appUser = generateUser() + expect(appUser[0].builder?.global).toEqual(false) + expect(appUser[0].admin?.global).toEqual(false) + const [createUserResponse, createUserJson] = await config.users.addMultiple(appUser) + + // Create App + const app = await config.applications.create(generateApp()) + config.applications.api.appId = app.appId + + //Create level 1 role + const role = { + inherits: "BASIC", + permissionId: "admin", + name: "level 5" + } + const [createRoleResponse, createRoleJson] = await config.users.createRole(role) + + + + // Update user roles + const [userInfoResponse, userInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + const prodAppId = db.getProdAppID(app.appId!) + + // Roles must always be set with prod appID + const body: User = { + ...userInfoJson, + roles: { + [prodAppId]: createRoleJson._id, + } + } + await config.users.updateInfo(body) + + const [changedUserInfoResponse, changedUserInfoJson] = await config.users.getInfo(createUserJson.created.successful[0]._id) + expect(changedUserInfoJson.roles[prodAppId]).toBeDefined() + expect(changedUserInfoJson.roles[prodAppId]).toEqual(createRoleJson._id) + + await config.screen.create(generateScreen("BASIC")) + await config.screen.create(generateScreen("POWER")) + await config.screen.create(generateScreen("ADMIN")) + + await config.applications.publish(app.url) + const [firstappPackageResponse, firstappPackageJson] = await config.applications.getAppPackage(app.appId) + expect(firstappPackageJson.screens).toBeDefined() + expect(firstappPackageJson.screens.length).toEqual(3) + + // login with level 1 user + await config.login(appUser[0].email!, appUser[0].password!) + const [selfInfoResponse, selfInfoJson] = await config.users.getSelf() + + // fetch app package + const [appPackageResponse, appPackageJson] = await config.applications.getAppPackage(app.appId!) + expect(appPackageJson.screens).toBeDefined() + expect(appPackageJson.screens.length).toEqual(1) + }) }) }) From 3b1819952d9eea37634902d05a9055af8e13087f Mon Sep 17 00:00:00 2001 From: Andrew Kingston Date: Sat, 17 Dec 2022 14:13:06 +0000 Subject: [PATCH 28/43] Builder data section routing refactor (#8996) * Improve theming with spectrum badges and dedupe spectrum label usage * Update data section nav to match designs and use panel component * Fix main content layout in data section * Update data section routing for tables * Improve data section routing for tables to account for edge cases * Update internal and sample datasource routing * Update external datasource routing * Update routing for queries and make a top level concept like everything else * Update routing for views * Fix undefined reference when deleting datasource * Reduce network calls and fix issues with stale datasourcenavigator state * Update routing for REST queries and unify routes for normal queries and REST queries * Lint * Fix links for queries from datasource details page * Remove redundant API calls and improve table deletion logic * Improve data entity deletion logic and redirection and fix query details keying * Improve determination of selected item in datasource tree * Lint * Fix BBUI import * Fix datasource navigator selected state not working for internal DB or sample data --- packages/bbui/src/Badge/Badge.svelte | 13 + .../src/Table/RelationshipRenderer.svelte | 11 +- .../components/backend/DataTable/Table.svelte | 1 - .../DataTable/modals/CreateViewModal.svelte | 4 +- .../DatasourceNavigator.svelte | 132 ++++++---- .../popovers/EditDatasourcePopover.svelte | 19 +- .../popovers/EditQueryPopover.svelte | 16 +- .../TableNavigator/TableNavigator.svelte | 33 +-- .../popovers/EditTablePopover.svelte | 9 +- .../popovers/EditViewPopover.svelte | 7 +- .../src/components/design/Panel.svelte | 2 + .../integration}/DynamicVariableModal.svelte | 0 .../components/integration/QueryViewer.svelte | 245 +++++++++--------- .../integration}/RestBodyInput.svelte | 0 .../integration/RestQueryViewer.svelte} | 37 ++- packages/builder/src/helpers/urlStateSync.js | 19 +- .../app/[application]/data/_layout.svelte | 69 ++--- .../datasource/[datasourceId]/_layout.svelte | 23 ++ .../index.svelte | 52 ++-- .../[query]/_layout.svelte | 23 -- .../[selectedDatasource]/[query]/index.svelte | 39 --- .../[selectedDatasource]/_layout.svelte | 17 -- .../rest/[query]/_layout.svelte | 13 - .../datasource/bb_internal/_layout.svelte | 7 - .../data/datasource/bb_internal/index.svelte | 10 +- .../_layout.svelte | 8 - .../index.svelte | 19 +- .../data/datasource/index.svelte | 10 +- .../data/query/[queryId]/_layout.svelte | 22 ++ .../data/query/[queryId]/index.svelte | 18 ++ .../app/[application]/data/query/index.svelte | 16 ++ .../query/new/[datasourceId]/index.svelte | 38 +++ .../[application]/data/query/new/index.svelte | 5 + .../data/table/[selectedTable]/_layout.svelte | 13 - .../data/table/[tableId]/_layout.svelte | 20 ++ .../index.svelte | 6 +- .../[rowId]/[field]}/index.svelte | 6 +- .../relationship/[rowId]}/index.svelte | 0 .../relationship/index.svelte | 0 .../[application]/data/table/_layout.svelte | 19 -- .../app/[application]/data/table/index.svelte | 11 +- .../data/view/[selectedView]/_layout.svelte | 22 -- .../data/view/[viewName]/_layout.svelte | 20 ++ .../index.svelte | 0 .../app/[application]/data/view/index.svelte | 16 ++ .../builder/src/stores/backend/datasources.js | 160 ++++++------ .../builder/src/stores/backend/queries.js | 226 ++++++++-------- packages/builder/src/stores/backend/tables.js | 196 +++++++------- packages/builder/src/stores/backend/views.js | 88 ++++--- 49 files changed, 894 insertions(+), 846 deletions(-) rename packages/builder/src/{pages/builder/app/[application]/data/datasource/[selectedDatasource]/_components => components/integration}/DynamicVariableModal.svelte (100%) rename packages/builder/src/{pages/builder/app/[application]/data/datasource/[selectedDatasource]/_components => components/integration}/RestBodyInput.svelte (100%) rename packages/builder/src/{pages/builder/app/[application]/data/datasource/[selectedDatasource]/rest/[query]/index.svelte => components/integration/RestQueryViewer.svelte} (98%) create mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/[datasourceId]/_layout.svelte rename packages/builder/src/pages/builder/app/[application]/data/datasource/{[selectedDatasource] => [datasourceId]}/index.svelte (87%) delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/[selectedDatasource]/[query]/_layout.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/[selectedDatasource]/[query]/index.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/[selectedDatasource]/_layout.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/[selectedDatasource]/rest/[query]/_layout.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/bb_internal/_layout.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/datasource/datasource_internal_bb_default/_layout.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/query/[queryId]/_layout.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/query/[queryId]/index.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/query/index.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/query/new/[datasourceId]/index.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/query/new/index.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/table/[selectedTable]/_layout.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/table/[tableId]/_layout.svelte rename packages/builder/src/pages/builder/app/[application]/data/table/{[selectedTable] => [tableId]}/index.svelte (71%) rename packages/builder/src/pages/builder/app/[application]/data/table/{[selectedTable]/relationship/[selectedRow]/[selectedField] => [tableId]/relationship/[rowId]/[field]}/index.svelte (62%) rename packages/builder/src/pages/builder/app/[application]/data/table/{[selectedTable]/relationship/[selectedRow] => [tableId]/relationship/[rowId]}/index.svelte (100%) rename packages/builder/src/pages/builder/app/[application]/data/table/{[selectedTable] => [tableId]}/relationship/index.svelte (100%) delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/table/_layout.svelte delete mode 100644 packages/builder/src/pages/builder/app/[application]/data/view/[selectedView]/_layout.svelte create mode 100644 packages/builder/src/pages/builder/app/[application]/data/view/[viewName]/_layout.svelte rename packages/builder/src/pages/builder/app/[application]/data/view/{[selectedView] => [viewName]}/index.svelte (100%) create mode 100644 packages/builder/src/pages/builder/app/[application]/data/view/index.svelte diff --git a/packages/bbui/src/Badge/Badge.svelte b/packages/bbui/src/Badge/Badge.svelte index 4bc701d983..8b54045297 100644 --- a/packages/bbui/src/Badge/Badge.svelte +++ b/packages/bbui/src/Badge/Badge.svelte @@ -10,10 +10,13 @@ export let green = false export let active = false export let inactive = false + export let hoverable = false + + diff --git a/packages/bbui/src/Table/RelationshipRenderer.svelte b/packages/bbui/src/Table/RelationshipRenderer.svelte index 4db0c63d95..b70eaeb07d 100644 --- a/packages/bbui/src/Table/RelationshipRenderer.svelte +++ b/packages/bbui/src/Table/RelationshipRenderer.svelte @@ -1,6 +1,7 @@ {#if $database?._id} @@ -44,8 +23,9 @@ border={idx > 0} icon={table._id === TableNames.USERS ? "UserGroup" : "Table"} text={table.name} - selected={$tables.selected?._id === table._id} - on:click={() => selectTable(table)} + selected={$isActive("./table/:tableId") && + $tables.selected?._id === table._id} + on:click={() => $goto(`./table/${table._id}`)} > {#if table._id !== TableNames.USERS} @@ -56,8 +36,9 @@ indentLevel={2} icon="Remove" text={viewName} - selected={selectedView === viewName} - on:click={() => onClickView(table, viewName)} + selected={$isActive("./view/:viewName") && + $views.selected?.name === viewName} + on:click={() => $goto(`./view/${viewName}`)} > - import { goto } from "@roxi/routify" + import { goto, params } from "@roxi/routify" import { store } from "builderStore" import { cloneDeep } from "lodash/fp" import { tables, datasources } from "stores/backend" @@ -41,17 +41,16 @@ } async function deleteTable() { - const wasSelectedTable = $tables.selected + const isSelected = $params.tableId === table._id try { await tables.delete(table) await store.actions.screens.delete(templateScreens) - await tables.fetch() if (table.type === "external") { await datasources.fetch() } notifications.success("Table deleted") - if (wasSelectedTable && wasSelectedTable._id === table._id) { - $goto("./table") + if (isSelected) { + $goto(`./datasource/${table.datasourceId}`) } } catch (error) { notifications.error("Error deleting table") diff --git a/packages/builder/src/components/backend/TableNavigator/popovers/EditViewPopover.svelte b/packages/builder/src/components/backend/TableNavigator/popovers/EditViewPopover.svelte index f543b34ddc..44eb1e9b7b 100644 --- a/packages/builder/src/components/backend/TableNavigator/popovers/EditViewPopover.svelte +++ b/packages/builder/src/components/backend/TableNavigator/popovers/EditViewPopover.svelte @@ -1,5 +1,5 @@ - - Query {integrationInfo?.friendlyName} - - Config -
-
- - -
- {#if queryConfig} -
- -
- Add a JavaScript function to transform the query result. - (query.transformer = e.detail)} - /> - -
-
- Results - - - - -
- - Below, you can preview the results from your query and change the schema. - -
- {#if data} - - - - - - - - - - - + {#if queryConfig} +
+ +