From 865192adf041aae68519893119bba1ff2de855b8 Mon Sep 17 00:00:00 2001 From: Val <68596159+valya@users.noreply.github.com> Date: Thu, 23 Nov 2023 13:38:11 +0000 Subject: [PATCH] feat: Add global admin role (no-changelog) (#7781) Github issue / Community forum post (link here to close automatically): --- packages/cli/src/databases/entities/User.ts | 3 +- .../1700571993961-AddGlobalAdminRole.ts | 58 +++++++++++++++++++ .../src/databases/migrations/mysqldb/index.ts | 2 + .../databases/migrations/postgresdb/index.ts | 2 + .../src/databases/migrations/sqlite/index.ts | 2 + 5 files changed, 66 insertions(+), 1 deletion(-) create mode 100644 packages/cli/src/databases/migrations/common/1700571993961-AddGlobalAdminRole.ts diff --git a/packages/cli/src/databases/entities/User.ts b/packages/cli/src/databases/entities/User.ts index eb69b2e37f..12ffcb31b4 100644 --- a/packages/cli/src/databases/entities/User.ts +++ b/packages/cli/src/databases/entities/User.ts @@ -20,7 +20,7 @@ import { objectRetriever, lowerCaser } from '../utils/transformers'; import { WithTimestamps, jsonColumnType } from './AbstractEntity'; import type { IPersonalizationSurveyAnswers } from '@/Interfaces'; import type { AuthIdentity } from './AuthIdentity'; -import { ownerPermissions, memberPermissions } from '@/permissions/roles'; +import { ownerPermissions, memberPermissions, adminPermissions } from '@/permissions/roles'; import { hasScope, type ScopeOptions, type Scope } from '@n8n/permissions'; export const MIN_PASSWORD_LENGTH = 8; @@ -30,6 +30,7 @@ export const MAX_PASSWORD_LENGTH = 64; const STATIC_SCOPE_MAP: Record = { owner: ownerPermissions, member: memberPermissions, + admin: adminPermissions, }; @Entity() diff --git a/packages/cli/src/databases/migrations/common/1700571993961-AddGlobalAdminRole.ts b/packages/cli/src/databases/migrations/common/1700571993961-AddGlobalAdminRole.ts new file mode 100644 index 0000000000..5c90027dcc --- /dev/null +++ b/packages/cli/src/databases/migrations/common/1700571993961-AddGlobalAdminRole.ts @@ -0,0 +1,58 @@ +import type { MigrationContext, ReversibleMigration } from '@db/types'; + +export class AddGlobalAdminRole1700571993961 implements ReversibleMigration { + async up({ escape, runQuery }: MigrationContext) { + const tableName = escape.tableName('role'); + + await runQuery(`INSERT INTO ${tableName} (name, scope) VALUES (:name, :scope)`, { + name: 'admin', + scope: 'global', + }); + } + + async down({ escape, runQuery }: MigrationContext) { + const roleTableName = escape.tableName('role'); + const userTableName = escape.tableName('user'); + + const adminRoleIdResult = await runQuery>( + `SELECT id FROM ${roleTableName} WHERE name = :name AND scope = :scope`, + { + name: 'admin', + scope: 'global', + }, + ); + + const memberRoleIdResult = await runQuery>( + `SELECT id FROM ${roleTableName} WHERE name = :name AND scope = :scope`, + { + name: 'member', + scope: 'global', + }, + ); + + const adminRoleId = adminRoleIdResult[0]?.id; + if (adminRoleId === undefined) { + // Couldn't find admin role. It's a bit odd but it means we don't + // have anything to do. + return; + } + + const memberRoleId = memberRoleIdResult[0]?.id; + if (!memberRoleId) { + throw new Error('Could not find global member role!'); + } + + await runQuery( + `UPDATE ${userTableName} SET globalRoleId = :memberRoleId WHERE globalRoleId = :adminRoleId`, + { + memberRoleId, + adminRoleId, + }, + ); + + await runQuery(`DELETE FROM ${roleTableName} WHERE name = :name AND scope = :scope`, { + name: 'admin', + scope: 'global', + }); + } +} diff --git a/packages/cli/src/databases/migrations/mysqldb/index.ts b/packages/cli/src/databases/migrations/mysqldb/index.ts index 8dbc688895..66effc584b 100644 --- a/packages/cli/src/databases/migrations/mysqldb/index.ts +++ b/packages/cli/src/databases/migrations/mysqldb/index.ts @@ -50,6 +50,7 @@ import { DisallowOrphanExecutions1693554410387 } from '../common/1693554410387-D import { ExecutionSoftDelete1693491613982 } from '../common/1693491613982-ExecutionSoftDelete'; import { AddWorkflowMetadata1695128658538 } from '../common/1695128658538-AddWorkflowMetadata'; import { ModifyWorkflowHistoryNodesAndConnections1695829275184 } from '../common/1695829275184-ModifyWorkflowHistoryNodesAndConnections'; +import { AddGlobalAdminRole1700571993961 } from '../common/1700571993961-AddGlobalAdminRole'; export const mysqlMigrations: Migration[] = [ InitialMigration1588157391238, @@ -103,4 +104,5 @@ export const mysqlMigrations: Migration[] = [ ExecutionSoftDelete1693491613982, AddWorkflowMetadata1695128658538, ModifyWorkflowHistoryNodesAndConnections1695829275184, + AddGlobalAdminRole1700571993961, ]; diff --git a/packages/cli/src/databases/migrations/postgresdb/index.ts b/packages/cli/src/databases/migrations/postgresdb/index.ts index f827b91390..6af140bd08 100644 --- a/packages/cli/src/databases/migrations/postgresdb/index.ts +++ b/packages/cli/src/databases/migrations/postgresdb/index.ts @@ -49,6 +49,7 @@ import { ExecutionSoftDelete1693491613982 } from '../common/1693491613982-Execut import { AddWorkflowMetadata1695128658538 } from '../common/1695128658538-AddWorkflowMetadata'; import { MigrateToTimestampTz1694091729095 } from './1694091729095-MigrateToTimestampTz'; import { ModifyWorkflowHistoryNodesAndConnections1695829275184 } from '../common/1695829275184-ModifyWorkflowHistoryNodesAndConnections'; +import { AddGlobalAdminRole1700571993961 } from '../common/1700571993961-AddGlobalAdminRole'; export const postgresMigrations: Migration[] = [ InitialMigration1587669153312, @@ -101,4 +102,5 @@ export const postgresMigrations: Migration[] = [ AddWorkflowMetadata1695128658538, MigrateToTimestampTz1694091729095, ModifyWorkflowHistoryNodesAndConnections1695829275184, + AddGlobalAdminRole1700571993961, ]; diff --git a/packages/cli/src/databases/migrations/sqlite/index.ts b/packages/cli/src/databases/migrations/sqlite/index.ts index 024c3bbc79..d92a567bce 100644 --- a/packages/cli/src/databases/migrations/sqlite/index.ts +++ b/packages/cli/src/databases/migrations/sqlite/index.ts @@ -47,6 +47,7 @@ import { DisallowOrphanExecutions1693554410387 } from '../common/1693554410387-D import { ExecutionSoftDelete1693491613982 } from './1693491613982-ExecutionSoftDelete'; import { AddWorkflowMetadata1695128658538 } from '../common/1695128658538-AddWorkflowMetadata'; import { ModifyWorkflowHistoryNodesAndConnections1695829275184 } from '../common/1695829275184-ModifyWorkflowHistoryNodesAndConnections'; +import { AddGlobalAdminRole1700571993961 } from '../common/1700571993961-AddGlobalAdminRole'; const sqliteMigrations: Migration[] = [ InitialMigration1588102412422, @@ -97,6 +98,7 @@ const sqliteMigrations: Migration[] = [ ExecutionSoftDelete1693491613982, AddWorkflowMetadata1695128658538, ModifyWorkflowHistoryNodesAndConnections1695829275184, + AddGlobalAdminRole1700571993961, ]; export { sqliteMigrations };