From 41d8a4c8076ed9568b5cc1848887600d33eda533 Mon Sep 17 00:00:00 2001 From: Zai Shi Date: Mon, 28 Jul 2025 16:46:23 -0700 Subject: [PATCH] tests --- .../api/v1/internal/config-overrides.test.ts | 294 ++++++++++++++++++ .../v1/internal/environment-config.test.ts | 20 -- 2 files changed, 294 insertions(+), 20 deletions(-) create mode 100644 apps/e2e/tests/backend/endpoints/api/v1/internal/config-overrides.test.ts delete mode 100644 apps/e2e/tests/backend/endpoints/api/v1/internal/environment-config.test.ts diff --git a/apps/e2e/tests/backend/endpoints/api/v1/internal/config-overrides.test.ts b/apps/e2e/tests/backend/endpoints/api/v1/internal/config-overrides.test.ts new file mode 100644 index 000000000..7f45e352a --- /dev/null +++ b/apps/e2e/tests/backend/endpoints/api/v1/internal/config-overrides.test.ts @@ -0,0 +1,294 @@ +import { it } from "../../../../../helpers"; +import { Project, niceBackendFetch } from "../../../../backend-helpers"; + + +// it("client and server should not have access to config overrides", async ({ expect }) => { +// await Project.createAndSwitch(); + +// // Test client access +// const clientResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { +// accessType: "client" +// }); +// expect(clientResponse.status).toBe(401); + +// // Test server access +// const serverResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { +// accessType: "server" +// }); +// expect(serverResponse.status).toBe(401); +// }); + +// it("gets config", async ({ expect }) => { +// const { adminAccessToken } = await Project.createAndSwitch({ +// config: { +// magic_link_enabled: true, +// } +// }); + +// const response = await niceBackendFetch("/api/v1/internal/config-overrides", { +// method: "GET", +// accessType: "admin", +// headers: { +// 'x-stack-admin-access-token': adminAccessToken, +// }, +// }); + +// expect(response.status).toBe(200); +// const parsedConfig = JSON.parse(response.body.config); +// expect(pick(parsedConfig, ["auth", "domains", 'users', 'teams'])).toMatchInlineSnapshot(` +// { +// "auth": { +// "allowSignUp": true, +// "oauth": { +// "accountMergeStrategy": "link_method", +// "providers": {}, +// }, +// "otp": { "allowSignIn": true }, +// "passkey": { "allowSignIn": false }, +// "password": { "allowSignIn": true }, +// }, +// "domains": { +// "allowLocalhost": true, +// "trustedDomains": {}, +// }, +// "teams": { +// "allowClientTeamCreation": false, +// "createPersonalTeamOnSignUp": false, +// }, +// "users": { "allowClientUserDeletion": false }, +// } +// `); +// }); + +// it("updates basic config", async ({ expect }) => { +// const { adminAccessToken } = await Project.createAndSwitch({ +// config: { +// magic_link_enabled: true, +// } +// }); + +// // Get initial config +// const initialResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { +// method: "GET", +// accessType: "admin", +// headers: { +// 'x-stack-admin-access-token': adminAccessToken, +// }, +// }); + +// expect(initialResponse.status).toBe(200); +// const initialConfig = JSON.parse(initialResponse.body.config); + +// expect(initialConfig.users.allowClientUserDeletion).toBe(false); +// expect(initialConfig.teams.allowClientTeamCreation).toBe(false); +// expect(initialConfig.teams.createPersonalTeamOnSignUp).toBe(false); + +// const updateResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { +// method: "PATCH", +// accessType: "admin", +// headers: { +// 'x-stack-admin-access-token': adminAccessToken, +// }, +// body: { +// config: JSON.stringify({ +// 'users.allowClientUserDeletion': true, +// 'teams.allowClientTeamCreation': true, +// 'teams.createPersonalTeamOnSignUp': true, +// }), +// }, +// }); + +// expect(updateResponse.status).toBe(200); +// const returnedConfig = JSON.parse(updateResponse.body.config); +// expect(returnedConfig.users.allowClientUserDeletion).toBe(true); +// expect(returnedConfig.teams.allowClientTeamCreation).toBe(true); +// expect(returnedConfig.teams.createPersonalTeamOnSignUp).toBe(true); + +// // Verify the changes are persisted by making another GET request +// const verifyResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { +// method: "GET", +// accessType: "admin", +// headers: { +// 'x-stack-admin-access-token': adminAccessToken, +// }, +// }); + +// expect(verifyResponse.status).toBe(200); +// const persistedConfig = JSON.parse(verifyResponse.body.config); +// expect(persistedConfig.users.allowClientUserDeletion).toBe(true); +// expect(persistedConfig.teams.allowClientTeamCreation).toBe(true); +// expect(persistedConfig.teams.createPersonalTeamOnSignUp).toBe(true); +// }); + +it("adds, updates, and removes oauth config", async ({ expect }) => { + const { adminAccessToken } = await Project.createAndSwitch({ + config: { + magic_link_enabled: true, + } + }); + + // Get initial config to verify no OAuth providers exist + const initialResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "GET", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + }); + + expect(initialResponse.status).toBe(200); + const initialConfig = JSON.parse(initialResponse.body.config); + expect(initialConfig.auth.oauth.providers).toEqual({}); + + // Add a Google OAuth provider + const addGoogleResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "PATCH", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + body: { + config: JSON.stringify({ + 'auth.oauth.providers.google': { + type: 'google', + isShared: false, + clientId: 'google-client-id', + clientSecret: 'google-client-secret', + allowSignIn: true, + allowConnectedAccounts: true, + }, + }), + }, + }); + + expect(addGoogleResponse.status).toBe(200); + const configWithGoogle = JSON.parse(addGoogleResponse.body.config); + expect(configWithGoogle.auth.oauth.providers.google).toEqual({ + type: 'google', + isShared: false, + clientId: 'google-client-id', + clientSecret: 'google-client-secret', + allowSignIn: true, + allowConnectedAccounts: true, + }); + + // Add a second OAuth provider (GitHub) + const addGithubResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "PATCH", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + body: { + config: JSON.stringify({ + 'auth.oauth.providers.github': { + type: 'github', + isShared: true, + allowSignIn: true, + allowConnectedAccounts: false, + }, + }), + }, + }); + + expect(addGithubResponse.status).toBe(200); + const configWithBoth = JSON.parse(addGithubResponse.body.config); + expect(configWithBoth.auth.oauth.providers.google).toBeDefined(); + expect(configWithBoth.auth.oauth.providers.github).toEqual({ + type: 'github', + isShared: true, + allowSignIn: true, + allowConnectedAccounts: false, + }); + + // Update the Google OAuth provider + const updateGoogleResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "PATCH", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + body: { + config: JSON.stringify({ + 'auth.oauth.providers.google': { + type: 'google', + isShared: true, + allowSignIn: false, + allowConnectedAccounts: true, + }, + }), + }, + }); + + expect(updateGoogleResponse.status).toBe(200); + const configWithUpdatedGoogle = JSON.parse(updateGoogleResponse.body.config); + expect(configWithUpdatedGoogle.auth.oauth.providers.google).toEqual({ + type: 'google', + isShared: true, + allowSignIn: false, + allowConnectedAccounts: true, + }); + // GitHub should still be there + expect(configWithUpdatedGoogle.auth.oauth.providers.github).toBeDefined(); + + // Remove the GitHub OAuth provider + const removeGithubResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "PATCH", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + body: { + config: JSON.stringify({ + 'auth.oauth.providers.github': null, + }), + }, + }); + + expect(removeGithubResponse.status).toBe(200); + const configWithoutGithub = JSON.parse(removeGithubResponse.body.config); + expect(configWithoutGithub.auth.oauth.providers.github).toBeUndefined(); + // Google should still be there + expect(configWithoutGithub.auth.oauth.providers.google).toBeDefined(); + + // Remove the Google OAuth provider + const removeGoogleResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "PATCH", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + body: { + config: JSON.stringify({ + 'auth.oauth.providers.google': null, + }), + }, + }); + + expect(removeGoogleResponse.status).toBe(200); + const finalConfig = JSON.parse(removeGoogleResponse.body.config); + expect(finalConfig.auth.oauth.providers).toEqual({}); + + // Verify the changes are persisted by making another GET request + const verifyResponse = await niceBackendFetch("/api/v1/internal/config-overrides", { + method: "GET", + accessType: "admin", + headers: { + 'x-stack-admin-access-token': adminAccessToken, + }, + }); + + expect(verifyResponse.status).toBe(200); + const persistedConfig = JSON.parse(verifyResponse.body.config); + expect(persistedConfig.auth.oauth.providers).toEqual({}); +}); + +it.todo("misconfigures oauth config"); + +it.todo("adds, updates, and removes domains"); + +it.todo("misconfigures domains"); + +it.todo("adds, updates, and removes email config"); + +it.todo("misconfigures email config"); diff --git a/apps/e2e/tests/backend/endpoints/api/v1/internal/environment-config.test.ts b/apps/e2e/tests/backend/endpoints/api/v1/internal/environment-config.test.ts deleted file mode 100644 index c41a8e98a..000000000 --- a/apps/e2e/tests/backend/endpoints/api/v1/internal/environment-config.test.ts +++ /dev/null @@ -1,20 +0,0 @@ -import { it } from "../../../../../helpers"; - - -it.todo("client and server should not have access to environment config"); - -it.todo("gets environment config"); - -it.todo("updates basic environment config"); - -it.todo("adds, updates, and removes oauth config"); - -it.todo("misconfigures oauth config"); - -it.todo("adds, updates, and removes domains"); - -it.todo("misconfigures domains"); - -it.todo("adds, updates, and removes email config"); - -it.todo("misconfigures email config");