@solidxai/core 0.1.12-beta.3 → 0.1.12-beta.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/commands/seed.command.d.ts.map +1 -1
- package/dist/commands/seed.command.js +15 -2
- package/dist/commands/seed.command.js.map +1 -1
- package/dist/dtos/create-role-metadata.dto.d.ts +2 -0
- package/dist/dtos/create-role-metadata.dto.d.ts.map +1 -1
- package/dist/dtos/create-role-metadata.dto.js +3 -1
- package/dist/dtos/create-role-metadata.dto.js.map +1 -1
- package/dist/interfaces.d.ts +19 -1
- package/dist/interfaces.d.ts.map +1 -1
- package/dist/interfaces.js +2 -0
- package/dist/interfaces.js.map +1 -1
- package/dist/seeders/module-metadata-seeder.service.d.ts +7 -1
- package/dist/seeders/module-metadata-seeder.service.d.ts.map +1 -1
- package/dist/seeders/module-metadata-seeder.service.js +87 -3
- package/dist/seeders/module-metadata-seeder.service.js.map +1 -1
- package/dist/seeders/permission-metadata-seeder.service.d.ts +1 -0
- package/dist/seeders/permission-metadata-seeder.service.d.ts.map +1 -1
- package/dist/seeders/permission-metadata-seeder.service.js +6 -1
- package/dist/seeders/permission-metadata-seeder.service.js.map +1 -1
- package/dist/seeders/seed-data/solid-core-metadata.json +26 -10
- package/dist/services/authentication.service.d.ts +1 -0
- package/dist/services/authentication.service.d.ts.map +1 -1
- package/dist/services/authentication.service.js +19 -1
- package/dist/services/authentication.service.js.map +1 -1
- package/dist/services/role-metadata.service.d.ts +1 -0
- package/dist/services/role-metadata.service.d.ts.map +1 -1
- package/dist/services/role-metadata.service.js +8 -5
- package/dist/services/role-metadata.service.js.map +1 -1
- package/package.json +1 -1
- package/src/commands/seed.command.ts +17 -3
- package/src/dtos/create-role-metadata.dto.ts +2 -0
- package/src/interfaces.ts +20 -0
- package/src/seeders/module-metadata-seeder.service.ts +109 -3
- package/src/seeders/permission-metadata-seeder.service.ts +6 -1
- package/src/seeders/seed-data/solid-core-metadata.json +26 -10
- package/src/services/authentication.service.ts +24 -1
- package/src/services/role-metadata.service.ts +17 -5
|
@@ -18,6 +18,7 @@ export declare class RoleMetadataService extends CRUDService<RoleMetadata> {
|
|
|
18
18
|
createRolesIfNotExists(roles: CreateRoleMetadataDto[]): Promise<void>;
|
|
19
19
|
private resolveRoleModule;
|
|
20
20
|
addAllPermissionsToRole(roleName: string): Promise<RoleMetadata>;
|
|
21
|
+
addAllPermissionsToRoleExceptPrefixes(roleName: string, excludedPermissionPrefixes: string[]): Promise<RoleMetadata>;
|
|
21
22
|
addPermissionsToRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata>;
|
|
22
23
|
addPermissionToRole(roleName: string, permissionName: string[]): Promise<RoleMetadata>;
|
|
23
24
|
private _addPermissionsToRole;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"role-metadata.service.d.ts","sourceRoot":"","sources":["../../src/services/role-metadata.service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AAEzC,OAAO,EAAE,WAAW,EAAE,MAAM,2BAA2B,CAAC;AACxD,OAAO,EAAE,aAAa,EAAM,MAAM,SAAS,CAAC;AAG5C,OAAO,EAAE,4BAA4B,EAAE,MAAM,+CAA+C,CAAC;AAC7F,OAAO,EAAE,sBAAsB,EAAE,MAAM,yCAAyC,CAAC;AACjF,OAAO,EAAE,qBAAqB,EAAE,MAAM,kCAAkC,CAAC;AAGzE,OAAO,EAAE,YAAY,EAAE,MAAM,kCAAkC,CAAC;AAEhE,qBACa,mBAAoB,SAAQ,WAAW,CAAC,YAAY,CAAC;IAM9D,QAAQ,CAAC,aAAa,EAAE,aAAa;IAGrC,QAAQ,CAAC,IAAI,EAAE,sBAAsB;IAGrC,QAAQ,CAAC,oBAAoB,EAAE,4BAA4B;IAC3D,QAAQ,CAAC,SAAS,EAAE,SAAS;IAZ/B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAwC;IAC/D,OAAO,CAAC,QAAQ,CAAC,6BAA6B,CAAO;gBAI1C,aAAa,EAAE,aAAa,EAG5B,IAAI,EAAE,sBAAsB,EAG5B,oBAAoB,EAAE,4BAA4B,EAClD,SAAS,EAAE,SAAS;IAMzB,cAAc,CAAC,QAAQ,EAAE,MAAM;IAe/B,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAevD,sBAAsB,CAAC,KAAK,EAAE,qBAAqB,EAAE;YA0D7C,iBAAiB;IAgBzB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC;IAIhE,oBAAoB,CAAC,QAAQ,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,YAAY,CAAC;IAIxF,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,cAAc,EAAE,MAAM,EAAE;YAItD,qBAAqB;
|
|
1
|
+
{"version":3,"file":"role-metadata.service.d.ts","sourceRoot":"","sources":["../../src/services/role-metadata.service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AAEzC,OAAO,EAAE,WAAW,EAAE,MAAM,2BAA2B,CAAC;AACxD,OAAO,EAAE,aAAa,EAAM,MAAM,SAAS,CAAC;AAG5C,OAAO,EAAE,4BAA4B,EAAE,MAAM,+CAA+C,CAAC;AAC7F,OAAO,EAAE,sBAAsB,EAAE,MAAM,yCAAyC,CAAC;AACjF,OAAO,EAAE,qBAAqB,EAAE,MAAM,kCAAkC,CAAC;AAGzE,OAAO,EAAE,YAAY,EAAE,MAAM,kCAAkC,CAAC;AAEhE,qBACa,mBAAoB,SAAQ,WAAW,CAAC,YAAY,CAAC;IAM9D,QAAQ,CAAC,aAAa,EAAE,aAAa;IAGrC,QAAQ,CAAC,IAAI,EAAE,sBAAsB;IAGrC,QAAQ,CAAC,oBAAoB,EAAE,4BAA4B;IAC3D,QAAQ,CAAC,SAAS,EAAE,SAAS;IAZ/B,OAAO,CAAC,QAAQ,CAAC,MAAM,CAAwC;IAC/D,OAAO,CAAC,QAAQ,CAAC,6BAA6B,CAAO;gBAI1C,aAAa,EAAE,aAAa,EAG5B,IAAI,EAAE,sBAAsB,EAG5B,oBAAoB,EAAE,4BAA4B,EAClD,SAAS,EAAE,SAAS;IAMzB,cAAc,CAAC,QAAQ,EAAE,MAAM;IAe/B,sBAAsB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,IAAI,CAAC;IAevD,sBAAsB,CAAC,KAAK,EAAE,qBAAqB,EAAE;YA0D7C,iBAAiB;IAgBzB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,GAAG,OAAO,CAAC,YAAY,CAAC;IAIhE,qCAAqC,CAAC,QAAQ,EAAE,MAAM,EAAE,0BAA0B,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,YAAY,CAAC;IAIpH,oBAAoB,CAAC,QAAQ,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,YAAY,CAAC;IAIxF,mBAAmB,CAAC,QAAQ,EAAE,MAAM,EAAE,cAAc,EAAE,MAAM,EAAE;YAItD,qBAAqB;IAkD7B,yBAAyB,CAAC,QAAQ,EAAE,MAAM,EAAE,eAAe,EAAE,MAAM,EAAE,GAAG,OAAO,CAAC,YAAY,CAAC;YAsBrF,uBAAuB;YAUvB,qBAAqB;IAqBnC,OAAO,CAAC,yBAAyB;YAmBnB,4BAA4B;CAsB3C"}
|
|
@@ -110,13 +110,16 @@ let RoleMetadataService = RoleMetadataService_1 = class RoleMetadataService exte
|
|
|
110
110
|
async addAllPermissionsToRole(roleName) {
|
|
111
111
|
return await this._addPermissionsToRole(roleName, null);
|
|
112
112
|
}
|
|
113
|
+
async addAllPermissionsToRoleExceptPrefixes(roleName, excludedPermissionPrefixes) {
|
|
114
|
+
return await this._addPermissionsToRole(roleName, null, excludedPermissionPrefixes);
|
|
115
|
+
}
|
|
113
116
|
async addPermissionsToRole(roleName, permissionNames) {
|
|
114
117
|
return await this._addPermissionsToRole(roleName, permissionNames);
|
|
115
118
|
}
|
|
116
119
|
async addPermissionToRole(roleName, permissionName) {
|
|
117
120
|
return await this._addPermissionsToRole(roleName, permissionName);
|
|
118
121
|
}
|
|
119
|
-
async _addPermissionsToRole(roleName, permissionNames) {
|
|
122
|
+
async _addPermissionsToRole(roleName, permissionNames, excludedPermissionPrefixes = []) {
|
|
120
123
|
const role = await this.repo.findOne({
|
|
121
124
|
where: { name: roleName },
|
|
122
125
|
select: {
|
|
@@ -128,7 +131,7 @@ let RoleMetadataService = RoleMetadataService_1 = class RoleMetadataService exte
|
|
|
128
131
|
throw new Error(`Role '${roleName}' not found.`);
|
|
129
132
|
}
|
|
130
133
|
const joinInfo = this.getRolePermissionJoinInfo();
|
|
131
|
-
const targetPermissions = await this.loadTargetPermissions(permissionNames);
|
|
134
|
+
const targetPermissions = await this.loadTargetPermissions(permissionNames, excludedPermissionPrefixes);
|
|
132
135
|
if (!permissionNames || permissionNames.length === 0) {
|
|
133
136
|
await this.entityManager
|
|
134
137
|
.createQueryBuilder()
|
|
@@ -179,20 +182,20 @@ let RoleMetadataService = RoleMetadataService_1 = class RoleMetadataService exte
|
|
|
179
182
|
}
|
|
180
183
|
return existingPermission;
|
|
181
184
|
}
|
|
182
|
-
async loadTargetPermissions(permissionNames) {
|
|
185
|
+
async loadTargetPermissions(permissionNames, excludedPermissionPrefixes = []) {
|
|
183
186
|
if (permissionNames && permissionNames.length !== 0) {
|
|
184
187
|
const uniquePermissionNames = [...new Set(permissionNames)];
|
|
185
188
|
const permissions = await this.permissionRepository.find({ where: { name: (0, typeorm_2.In)(uniquePermissionNames) } });
|
|
186
189
|
if (permissions.length !== uniquePermissionNames.length) {
|
|
187
190
|
throw new Error(`One or more permissions not found.`);
|
|
188
191
|
}
|
|
189
|
-
return permissions;
|
|
192
|
+
return permissions.filter((permission) => !excludedPermissionPrefixes.some((prefix) => permission.name.startsWith(prefix)));
|
|
190
193
|
}
|
|
191
194
|
const permissions = await this.permissionRepository.find();
|
|
192
195
|
if (permissions.length === 0) {
|
|
193
196
|
throw new Error(`No permissions configured in the system. Did you forget to run the PermissionSeederService?`);
|
|
194
197
|
}
|
|
195
|
-
return permissions;
|
|
198
|
+
return permissions.filter((permission) => !excludedPermissionPrefixes.some((prefix) => permission.name.startsWith(prefix)));
|
|
196
199
|
}
|
|
197
200
|
getRolePermissionJoinInfo() {
|
|
198
201
|
const relation = this.repo.metadata.relations.find((candidate) => candidate.propertyName === 'permissions');
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"role-metadata.service.js","sourceRoot":"","sources":["../../src/services/role-metadata.service.ts"],"names":[],"mappings":"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","sourcesContent":["import { Injectable, Logger, NotFoundException } from '@nestjs/common';\nimport { ModuleRef } from \"@nestjs/core\";\nimport { InjectEntityManager } from '@nestjs/typeorm';\nimport { CRUDService } from 'src/services/crud.service';\nimport { EntityManager, In } from 'typeorm';\n\nimport { ERROR_MESSAGES } from 'src/constants/error-messages';\nimport { PermissionMetadataRepository } from 'src/repository/permission-metadata.repository';\nimport { RoleMetadataRepository } from 'src/repository/role-metadata.repository';\nimport { CreateRoleMetadataDto } from '../dtos/create-role-metadata.dto';\nimport { ModuleMetadata } from '../entities/module-metadata.entity';\nimport { PermissionMetadata } from '../entities/permission-metadata.entity';\nimport { RoleMetadata } from '../entities/role-metadata.entity';\n\n@Injectable()\nexport class RoleMetadataService extends CRUDService<RoleMetadata> {\n private readonly logger = new Logger(RoleMetadataService.name);\n private readonly permissionAssignmentBatchSize = 500;\n\n constructor(\n @InjectEntityManager()\n readonly entityManager: EntityManager,\n // @InjectRepository(RoleMetadata, 'default')\n // readonly repo: Repository<RoleMetadata>,\n readonly repo: RoleMetadataRepository,\n // @InjectRepository(PermissionMetadata)\n // private readonly permissionRepository: Repository<PermissionMetadata>,\n readonly permissionRepository: PermissionMetadataRepository,\n readonly moduleRef: ModuleRef\n\n ) {\n super(entityManager, repo, 'roleMetadata', 'solid-core', moduleRef);\n }\n\n async findRoleByName(roleName: string) {\n const entity = await this.repo.findOne({\n where: {\n name: roleName\n },\n relations: {\n permissions: true\n }\n });\n if (!entity) {\n throw new NotFoundException(`Entity #${roleName} not found`);\n }\n return entity;\n }\n\n async assertRoleExistsByName(roleName: string): Promise<void> {\n const entity = await this.repo.findOne({\n where: {\n name: roleName\n },\n select: {\n id: true\n }\n });\n if (!entity) {\n throw new NotFoundException(`Entity #${roleName} not found`);\n }\n }\n\n // OK\n async createRolesIfNotExists(roles: CreateRoleMetadataDto[]) {\n for (let id = 0; id < roles.length; id++) {\n try {\n const roleObj = roles[id];\n const module = await this.resolveRoleModule(roleObj);\n // this.logger.log(`Resolving role: ${JSON.stringify(roleObj)}`);\n\n const existingRole = await this.repo.findOne({\n where: {\n name: roleObj.name,\n },\n relations: {\n module: true,\n },\n });\n\n // Create only if not existing already.\n if (!existingRole) {\n this.logger.debug(`Role ${roleObj.name} does not exist, hence creating`);\n\n let permissions = [];\n\n if (roleObj.permissions && roleObj.permissions.length > 0) {\n await Promise.all(\n roleObj.permissions.map(permission => this.preloadPermissionByName(permission.name)),\n );\n }\n\n // const role = this.repo.create({ ...roleObj, permissions });\n const role = this.repo.create({ ...roleObj, ...(module ? { module } : {}) });\n await this.repo.save(role);\n } else {\n if (module && existingRole.module?.id !== module.id) {\n existingRole.module = module;\n await this.repo.save(existingRole);\n }\n /*\n this.logger.debug(`Role ${roleObj.name} already exists`);\n const existingPermissions = existingRole.permissions.map(permission => permission.name);\n const newPermissions = roleObj.permissions.map(permission => permission.name);\n const permissionsToAdd = newPermissions.filter(permission => !existingPermissions.includes(permission));\n const permissionsToRemove = existingPermissions.filter(permission => !newPermissions.includes(permission));\n this.logger.debug(`Permissions to add: ${JSON.stringify(permissionsToAdd)}`);\n if (permissionsToAdd.length > 0) {\n await this.addPermissionsToRole(roleObj.name, permissionsToAdd);\n }\n this.logger.debug(`Permissions to remove: ${JSON.stringify(permissionsToRemove)}`);\n if (permissionsToRemove.length > 0) {\n await this.removePermissionsFromRole(roleObj.name, permissionsToRemove);\n }\n */\n }\n } catch (error: any) {\n this.logger.error(error);\n }\n }\n }\n\n private async resolveRoleModule(roleObj: CreateRoleMetadataDto): Promise<ModuleMetadata | null> {\n if (roleObj.moduleId) {\n return await this.entityManager.getRepository(ModuleMetadata).findOne({\n where: { id: roleObj.moduleId },\n });\n }\n\n if (roleObj.moduleUserKey) {\n return await this.entityManager.getRepository(ModuleMetadata).findOne({\n where: { name: roleObj.moduleUserKey },\n });\n }\n\n return null;\n }\n\n async addAllPermissionsToRole(roleName: string): Promise<RoleMetadata> {\n return await this._addPermissionsToRole(roleName, null);\n }\n\n async addPermissionsToRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata> {\n return await this._addPermissionsToRole(roleName, permissionNames);\n }\n\n async addPermissionToRole(roleName: string, permissionName: string[]) {\n return await this._addPermissionsToRole(roleName, permissionName);\n }\n\n private async _addPermissionsToRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata> {\n const role = await this.repo.findOne({\n where: { name: roleName },\n select: {\n id: true,\n name: true,\n }\n });\n if (!role) {\n throw new Error(`Role '${roleName}' not found.`);\n }\n\n const joinInfo = this.getRolePermissionJoinInfo();\n const targetPermissions = await this.loadTargetPermissions(permissionNames);\n\n if (!permissionNames || permissionNames.length === 0) {\n await this.entityManager\n .createQueryBuilder()\n .delete()\n .from(joinInfo.tableName)\n .where(`${joinInfo.roleIdColumn} = :roleId`, { roleId: role.id })\n .execute();\n\n await this.insertRolePermissionMappings(role.id, targetPermissions.map((permission) => permission.id), joinInfo);\n }\n else {\n const existingRows = await this.entityManager\n .createQueryBuilder()\n .select(joinInfo.permissionIdColumn, 'permissionId')\n .from(joinInfo.tableName, 'role_permission')\n .where(`${joinInfo.roleIdColumn} = :roleId`, { roleId: role.id })\n .getRawMany();\n\n const existingPermissionIds = new Set(existingRows.map((row) => Number(row.permissionId)));\n const missingPermissionIds = targetPermissions\n .map((permission) => permission.id)\n .filter((permissionId) => !existingPermissionIds.has(permissionId));\n\n if (missingPermissionIds.length > 0) {\n await this.insertRolePermissionMappings(role.id, missingPermissionIds, joinInfo);\n }\n }\n\n return await this.findRoleByName(roleName);\n }\n\n async removePermissionsFromRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata> {\n\n // load the role with the respective permissions.\n const role = await this.repo.findOne({\n where: {\n name: roleName\n },\n relations: {\n permissions: true\n }\n });\n\n if (!role) {\n throw new Error(ERROR_MESSAGES.ROLE_NOT_FOUND(roleName));\n }\n\n // modify the permissions array.\n role.permissions = role.permissions.filter(permission => !permissionNames.includes(permission.name));\n\n return await this.repo.save(role);\n }\n\n private async preloadPermissionByName(name: string): Promise<PermissionMetadata> {\n const existingPermission = await this.permissionRepository.findOne({\n where: { name },\n });\n if (!existingPermission) {\n throw new NotFoundException(ERROR_MESSAGES.PERMISSION_NOT_EXIST(name));\n }\n return existingPermission;\n }\n\n private async loadTargetPermissions(permissionNames: string[] | null): Promise<PermissionMetadata[]> {\n if (permissionNames && permissionNames.length !== 0) {\n const uniquePermissionNames = [...new Set(permissionNames)];\n const permissions = await this.permissionRepository.find({ where: { name: In(uniquePermissionNames) } });\n if (permissions.length !== uniquePermissionNames.length) {\n throw new Error(`One or more permissions not found.`);\n }\n return permissions;\n }\n\n const permissions = await this.permissionRepository.find();\n if (permissions.length === 0) {\n throw new Error(`No permissions configured in the system. Did you forget to run the PermissionSeederService?`);\n }\n return permissions;\n }\n\n private getRolePermissionJoinInfo(): { tableName: string; roleIdColumn: string; permissionIdColumn: string } {\n const relation = this.repo.metadata.relations.find((candidate) => candidate.propertyName === 'permissions');\n if (!relation?.junctionEntityMetadata) {\n throw new Error('Role-permission join table metadata not found.');\n }\n\n const roleIdColumn = relation.joinColumns[0]?.databaseName;\n const permissionIdColumn = relation.inverseJoinColumns[0]?.databaseName;\n if (!roleIdColumn || !permissionIdColumn) {\n throw new Error('Role-permission join table column metadata not found.');\n }\n\n return {\n tableName: relation.junctionEntityMetadata.tableName,\n roleIdColumn,\n permissionIdColumn,\n };\n }\n\n private async insertRolePermissionMappings(\n roleId: number,\n permissionIds: number[],\n joinInfo: { tableName: string; roleIdColumn: string; permissionIdColumn: string },\n ): Promise<void> {\n for (let index = 0; index < permissionIds.length; index += this.permissionAssignmentBatchSize) {\n const batch = permissionIds.slice(index, index + this.permissionAssignmentBatchSize);\n await this.entityManager\n .createQueryBuilder()\n .insert()\n .into(joinInfo.tableName)\n .values(\n batch.map((permissionId) => ({\n [joinInfo.roleIdColumn]: roleId,\n [joinInfo.permissionIdColumn]: permissionId,\n })),\n )\n .execute();\n }\n }\n\n\n}\n"]}
|
|
1
|
+
{"version":3,"file":"role-metadata.service.js","sourceRoot":"","sources":["../../src/services/role-metadata.service.ts"],"names":[],"mappings":"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","sourcesContent":["import { Injectable, Logger, NotFoundException } from '@nestjs/common';\nimport { ModuleRef } from \"@nestjs/core\";\nimport { InjectEntityManager } from '@nestjs/typeorm';\nimport { CRUDService } from 'src/services/crud.service';\nimport { EntityManager, In } from 'typeorm';\n\nimport { ERROR_MESSAGES } from 'src/constants/error-messages';\nimport { PermissionMetadataRepository } from 'src/repository/permission-metadata.repository';\nimport { RoleMetadataRepository } from 'src/repository/role-metadata.repository';\nimport { CreateRoleMetadataDto } from '../dtos/create-role-metadata.dto';\nimport { ModuleMetadata } from '../entities/module-metadata.entity';\nimport { PermissionMetadata } from '../entities/permission-metadata.entity';\nimport { RoleMetadata } from '../entities/role-metadata.entity';\n\n@Injectable()\nexport class RoleMetadataService extends CRUDService<RoleMetadata> {\n private readonly logger = new Logger(RoleMetadataService.name);\n private readonly permissionAssignmentBatchSize = 500;\n\n constructor(\n @InjectEntityManager()\n readonly entityManager: EntityManager,\n // @InjectRepository(RoleMetadata, 'default')\n // readonly repo: Repository<RoleMetadata>,\n readonly repo: RoleMetadataRepository,\n // @InjectRepository(PermissionMetadata)\n // private readonly permissionRepository: Repository<PermissionMetadata>,\n readonly permissionRepository: PermissionMetadataRepository,\n readonly moduleRef: ModuleRef\n\n ) {\n super(entityManager, repo, 'roleMetadata', 'solid-core', moduleRef);\n }\n\n async findRoleByName(roleName: string) {\n const entity = await this.repo.findOne({\n where: {\n name: roleName\n },\n relations: {\n permissions: true\n }\n });\n if (!entity) {\n throw new NotFoundException(`Entity #${roleName} not found`);\n }\n return entity;\n }\n\n async assertRoleExistsByName(roleName: string): Promise<void> {\n const entity = await this.repo.findOne({\n where: {\n name: roleName\n },\n select: {\n id: true\n }\n });\n if (!entity) {\n throw new NotFoundException(`Entity #${roleName} not found`);\n }\n }\n\n // OK\n async createRolesIfNotExists(roles: CreateRoleMetadataDto[]) {\n for (let id = 0; id < roles.length; id++) {\n try {\n const roleObj = roles[id];\n const module = await this.resolveRoleModule(roleObj);\n // this.logger.log(`Resolving role: ${JSON.stringify(roleObj)}`);\n\n const existingRole = await this.repo.findOne({\n where: {\n name: roleObj.name,\n },\n relations: {\n module: true,\n },\n });\n\n // Create only if not existing already.\n if (!existingRole) {\n this.logger.debug(`Role ${roleObj.name} does not exist, hence creating`);\n\n let permissions = [];\n\n if (roleObj.permissions && roleObj.permissions.length > 0) {\n await Promise.all(\n roleObj.permissions.map(permission => this.preloadPermissionByName(permission.name)),\n );\n }\n\n // const role = this.repo.create({ ...roleObj, permissions });\n const role = this.repo.create({ ...roleObj, ...(module ? { module } : {}) });\n await this.repo.save(role);\n } else {\n if (module && existingRole.module?.id !== module.id) {\n existingRole.module = module;\n await this.repo.save(existingRole);\n }\n /*\n this.logger.debug(`Role ${roleObj.name} already exists`);\n const existingPermissions = existingRole.permissions.map(permission => permission.name);\n const newPermissions = roleObj.permissions.map(permission => permission.name);\n const permissionsToAdd = newPermissions.filter(permission => !existingPermissions.includes(permission));\n const permissionsToRemove = existingPermissions.filter(permission => !newPermissions.includes(permission));\n this.logger.debug(`Permissions to add: ${JSON.stringify(permissionsToAdd)}`);\n if (permissionsToAdd.length > 0) {\n await this.addPermissionsToRole(roleObj.name, permissionsToAdd);\n }\n this.logger.debug(`Permissions to remove: ${JSON.stringify(permissionsToRemove)}`);\n if (permissionsToRemove.length > 0) {\n await this.removePermissionsFromRole(roleObj.name, permissionsToRemove);\n }\n */\n }\n } catch (error: any) {\n this.logger.error(error);\n }\n }\n }\n\n private async resolveRoleModule(roleObj: CreateRoleMetadataDto): Promise<ModuleMetadata | null> {\n if (roleObj.moduleId) {\n return await this.entityManager.getRepository(ModuleMetadata).findOne({\n where: { id: roleObj.moduleId },\n });\n }\n\n if (roleObj.moduleUserKey) {\n return await this.entityManager.getRepository(ModuleMetadata).findOne({\n where: { name: roleObj.moduleUserKey },\n });\n }\n\n return null;\n }\n\n async addAllPermissionsToRole(roleName: string): Promise<RoleMetadata> {\n return await this._addPermissionsToRole(roleName, null);\n }\n\n async addAllPermissionsToRoleExceptPrefixes(roleName: string, excludedPermissionPrefixes: string[]): Promise<RoleMetadata> {\n return await this._addPermissionsToRole(roleName, null, excludedPermissionPrefixes);\n }\n\n async addPermissionsToRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata> {\n return await this._addPermissionsToRole(roleName, permissionNames);\n }\n\n async addPermissionToRole(roleName: string, permissionName: string[]) {\n return await this._addPermissionsToRole(roleName, permissionName);\n }\n\n private async _addPermissionsToRole(\n roleName: string,\n permissionNames: string[],\n excludedPermissionPrefixes: string[] = [],\n ): Promise<RoleMetadata> {\n const role = await this.repo.findOne({\n where: { name: roleName },\n select: {\n id: true,\n name: true,\n }\n });\n if (!role) {\n throw new Error(`Role '${roleName}' not found.`);\n }\n\n const joinInfo = this.getRolePermissionJoinInfo();\n const targetPermissions = await this.loadTargetPermissions(permissionNames, excludedPermissionPrefixes);\n\n if (!permissionNames || permissionNames.length === 0) {\n await this.entityManager\n .createQueryBuilder()\n .delete()\n .from(joinInfo.tableName)\n .where(`${joinInfo.roleIdColumn} = :roleId`, { roleId: role.id })\n .execute();\n\n await this.insertRolePermissionMappings(role.id, targetPermissions.map((permission) => permission.id), joinInfo);\n }\n else {\n const existingRows = await this.entityManager\n .createQueryBuilder()\n .select(joinInfo.permissionIdColumn, 'permissionId')\n .from(joinInfo.tableName, 'role_permission')\n .where(`${joinInfo.roleIdColumn} = :roleId`, { roleId: role.id })\n .getRawMany();\n\n const existingPermissionIds = new Set(existingRows.map((row) => Number(row.permissionId)));\n const missingPermissionIds = targetPermissions\n .map((permission) => permission.id)\n .filter((permissionId) => !existingPermissionIds.has(permissionId));\n\n if (missingPermissionIds.length > 0) {\n await this.insertRolePermissionMappings(role.id, missingPermissionIds, joinInfo);\n }\n }\n\n return await this.findRoleByName(roleName);\n }\n\n async removePermissionsFromRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata> {\n\n // load the role with the respective permissions.\n const role = await this.repo.findOne({\n where: {\n name: roleName\n },\n relations: {\n permissions: true\n }\n });\n\n if (!role) {\n throw new Error(ERROR_MESSAGES.ROLE_NOT_FOUND(roleName));\n }\n\n // modify the permissions array.\n role.permissions = role.permissions.filter(permission => !permissionNames.includes(permission.name));\n\n return await this.repo.save(role);\n }\n\n private async preloadPermissionByName(name: string): Promise<PermissionMetadata> {\n const existingPermission = await this.permissionRepository.findOne({\n where: { name },\n });\n if (!existingPermission) {\n throw new NotFoundException(ERROR_MESSAGES.PERMISSION_NOT_EXIST(name));\n }\n return existingPermission;\n }\n\n private async loadTargetPermissions(permissionNames: string[] | null, excludedPermissionPrefixes: string[] = []): Promise<PermissionMetadata[]> {\n if (permissionNames && permissionNames.length !== 0) {\n const uniquePermissionNames = [...new Set(permissionNames)];\n const permissions = await this.permissionRepository.find({ where: { name: In(uniquePermissionNames) } });\n if (permissions.length !== uniquePermissionNames.length) {\n throw new Error(`One or more permissions not found.`);\n }\n return permissions.filter((permission) =>\n !excludedPermissionPrefixes.some((prefix) => permission.name.startsWith(prefix)),\n );\n }\n\n const permissions = await this.permissionRepository.find();\n if (permissions.length === 0) {\n throw new Error(`No permissions configured in the system. Did you forget to run the PermissionSeederService?`);\n }\n return permissions.filter((permission) =>\n !excludedPermissionPrefixes.some((prefix) => permission.name.startsWith(prefix)),\n );\n }\n\n private getRolePermissionJoinInfo(): { tableName: string; roleIdColumn: string; permissionIdColumn: string } {\n const relation = this.repo.metadata.relations.find((candidate) => candidate.propertyName === 'permissions');\n if (!relation?.junctionEntityMetadata) {\n throw new Error('Role-permission join table metadata not found.');\n }\n\n const roleIdColumn = relation.joinColumns[0]?.databaseName;\n const permissionIdColumn = relation.inverseJoinColumns[0]?.databaseName;\n if (!roleIdColumn || !permissionIdColumn) {\n throw new Error('Role-permission join table column metadata not found.');\n }\n\n return {\n tableName: relation.junctionEntityMetadata.tableName,\n roleIdColumn,\n permissionIdColumn,\n };\n }\n\n private async insertRolePermissionMappings(\n roleId: number,\n permissionIds: number[],\n joinInfo: { tableName: string; roleIdColumn: string; permissionIdColumn: string },\n ): Promise<void> {\n for (let index = 0; index < permissionIds.length; index += this.permissionAssignmentBatchSize) {\n const batch = permissionIds.slice(index, index + this.permissionAssignmentBatchSize);\n await this.entityManager\n .createQueryBuilder()\n .insert()\n .into(joinInfo.tableName)\n .values(\n batch.map((permissionId) => ({\n [joinInfo.roleIdColumn]: roleId,\n [joinInfo.permissionIdColumn]: permissionId,\n })),\n )\n .execute();\n }\n }\n\n\n}\n"]}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@solidxai/core",
|
|
3
|
-
"version": "0.1.12-beta.
|
|
3
|
+
"version": "0.1.12-beta.4",
|
|
4
4
|
"description": "This module is a NestJS module containing all the required core providers required by a Solid application",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
6
|
"types": "dist/index.d.ts",
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
import { Logger } from '@nestjs/common';
|
|
2
2
|
import { Command, CommandRunner, Option } from 'nest-commander';
|
|
3
3
|
import { SolidRegistry } from 'src/helpers/solid-registry';
|
|
4
|
+
import { ModuleMetadataSeederOptions } from 'src/interfaces';
|
|
4
5
|
|
|
5
6
|
interface SeedCommandOptions {
|
|
6
7
|
seeder?: string;
|
|
@@ -17,20 +18,33 @@ export class SeedCommand extends CommandRunner {
|
|
|
17
18
|
}
|
|
18
19
|
|
|
19
20
|
async run(passedParam: string[], options?: SeedCommandOptions): Promise<void> {
|
|
20
|
-
let parsedConf:
|
|
21
|
+
let parsedConf: ModuleMetadataSeederOptions | null = null;
|
|
21
22
|
if (options?.modulesToSeed) {
|
|
22
23
|
const modulesToSeed = options.modulesToSeed
|
|
23
24
|
.split(',')
|
|
24
25
|
.map((m) => m.trim())
|
|
25
26
|
.filter(Boolean);
|
|
26
|
-
parsedConf = {
|
|
27
|
+
parsedConf = {
|
|
28
|
+
modulesToSeed,
|
|
29
|
+
pruneMetadata: true,
|
|
30
|
+
seedGlobalMetadata: true,
|
|
31
|
+
};
|
|
27
32
|
this.logger.log(`Modules to seed: ${modulesToSeed.join(', ')}`);
|
|
28
33
|
} else {
|
|
29
34
|
this.logger.log('No --modules-to-seed flag provided. Running with default seeder behavior.');
|
|
35
|
+
parsedConf = {
|
|
36
|
+
modulesToSeed: null,
|
|
37
|
+
pruneMetadata: true,
|
|
38
|
+
seedGlobalMetadata: true,
|
|
39
|
+
};
|
|
30
40
|
}
|
|
31
41
|
|
|
32
42
|
if (options?.prune) {
|
|
33
|
-
parsedConf = parsedConf ?? {
|
|
43
|
+
parsedConf = parsedConf ?? {
|
|
44
|
+
modulesToSeed: null,
|
|
45
|
+
pruneMetadata: true,
|
|
46
|
+
seedGlobalMetadata: true,
|
|
47
|
+
};
|
|
34
48
|
parsedConf.pruneMetadata = true;
|
|
35
49
|
}
|
|
36
50
|
|
|
@@ -8,6 +8,8 @@ import { ApiProperty } from '@nestjs/swagger';
|
|
|
8
8
|
|
|
9
9
|
export const ADMIN_ROLE_NAME = 'Admin';
|
|
10
10
|
export const INTERNAL_ROLE_NAME = 'Internal User';
|
|
11
|
+
export const ALLOWED_TO_IMPORT_ROLE_NAME = 'Allowed To Import';
|
|
12
|
+
export const ALLOWED_TO_EXPORT_ROLE_NAME = 'Allowed To Export';
|
|
11
13
|
export const PUBLIC_ROLE_NAME = 'Public';
|
|
12
14
|
|
|
13
15
|
export class CreateRoleMetadataDto {
|
package/src/interfaces.ts
CHANGED
|
@@ -228,6 +228,8 @@ export interface ISolidDatabaseModule {
|
|
|
228
228
|
|
|
229
229
|
export enum EventType {
|
|
230
230
|
USER_REGISTERED = 'user.registered',
|
|
231
|
+
MODULE_METADATA_SEEDER_STARTED = 'module-metadata-seeder.started',
|
|
232
|
+
MODULE_METADATA_SEEDER_FINISHED = 'module-metadata-seeder.finished',
|
|
231
233
|
}
|
|
232
234
|
|
|
233
235
|
export class EventDetails<T> {
|
|
@@ -237,6 +239,24 @@ export class EventDetails<T> {
|
|
|
237
239
|
) { }
|
|
238
240
|
}
|
|
239
241
|
|
|
242
|
+
export interface ModuleMetadataSeederOptions {
|
|
243
|
+
modulesToSeed: string[] | null;
|
|
244
|
+
pruneMetadata: boolean;
|
|
245
|
+
seedGlobalMetadata: boolean;
|
|
246
|
+
}
|
|
247
|
+
|
|
248
|
+
export interface ModuleMetadataSeederEventPayload {
|
|
249
|
+
seedRunId: string;
|
|
250
|
+
options: ModuleMetadataSeederOptions;
|
|
251
|
+
startedAt: string;
|
|
252
|
+
finishedAt?: string;
|
|
253
|
+
durationMs?: number;
|
|
254
|
+
success?: boolean;
|
|
255
|
+
seededModuleNames?: string[];
|
|
256
|
+
currentStep?: string;
|
|
257
|
+
errorMessage?: string;
|
|
258
|
+
}
|
|
259
|
+
|
|
240
260
|
export interface IExtensionUserCreationProvider<T extends User = User, TDto extends CreateUserDto = CreateUserDto> {
|
|
241
261
|
readonly repo: Repository<T>;
|
|
242
262
|
buildExtensionEntity(dto: TDto): Promise<T>;
|
|
@@ -1,4 +1,5 @@
|
|
|
1
1
|
import { forwardRef, Inject, Injectable, Logger } from '@nestjs/common';
|
|
2
|
+
import { EventEmitter2 } from '@nestjs/event-emitter';
|
|
2
3
|
import * as fs from 'fs';
|
|
3
4
|
import * as os from 'os';
|
|
4
5
|
import * as path from 'path';
|
|
@@ -39,7 +40,12 @@ import { User } from '../entities/user.entity';
|
|
|
39
40
|
import { MENU_ROLE_JOIN_TABLE_NAME, MENU_ROLE_JOIN_TABLE_NAME_MENU_COL, MENU_ROLE_JOIN_TABLE_NAME_ROLE_COL } from '../dtos/create-menu-item-metadata.dto';
|
|
40
41
|
import { DEFAULT_SA_PASSWORD } from '../dtos/create-user.dto';
|
|
41
42
|
import { SignUpDto } from '../dtos/sign-up.dto';
|
|
42
|
-
import {
|
|
43
|
+
import {
|
|
44
|
+
ADMIN_ROLE_NAME,
|
|
45
|
+
ALLOWED_TO_EXPORT_ROLE_NAME,
|
|
46
|
+
ALLOWED_TO_IMPORT_ROLE_NAME,
|
|
47
|
+
CreateRoleMetadataDto,
|
|
48
|
+
} from 'src/dtos/create-role-metadata.dto';
|
|
43
49
|
import { CreateSavedFiltersDto } from 'src/dtos/create-saved-filters.dto';
|
|
44
50
|
import { CreateScheduledJobDto } from 'src/dtos/create-scheduled-job.dto';
|
|
45
51
|
import { CreateLocaleDto } from 'src/dtos/create-locale.dto';
|
|
@@ -60,6 +66,7 @@ import { FieldMetadata } from 'src/entities/field-metadata.entity';
|
|
|
60
66
|
import { ModelMetadata } from 'src/entities/model-metadata.entity';
|
|
61
67
|
import { PermissionMetadata } from 'src/entities/permission-metadata.entity';
|
|
62
68
|
import { ViewMetadata } from 'src/entities/view-metadata.entity';
|
|
69
|
+
import { EventDetails, EventType, ModuleMetadataSeederEventPayload } from 'src/interfaces';
|
|
63
70
|
|
|
64
71
|
/**
|
|
65
72
|
* Central metadata seeder for both solid-core and consuming modules.
|
|
@@ -79,6 +86,11 @@ import { ViewMetadata } from 'src/entities/view-metadata.entity';
|
|
|
79
86
|
*/
|
|
80
87
|
@Injectable()
|
|
81
88
|
export class ModuleMetadataSeederService {
|
|
89
|
+
private readonly adminPermissionExclusionPrefixes = [
|
|
90
|
+
'ImportTransactionController.',
|
|
91
|
+
'ExportTemplateController.',
|
|
92
|
+
'ExportTransactionController.',
|
|
93
|
+
];
|
|
82
94
|
private readonly logger = new Logger(ModuleMetadataSeederService.name);
|
|
83
95
|
// Stable tag used on all verbose seed timing logs so runs can be grepped quickly.
|
|
84
96
|
private readonly seedTimingTag = 'SEED_TIMING';
|
|
@@ -98,6 +110,7 @@ export class ModuleMetadataSeederService {
|
|
|
98
110
|
private readonly moduleMetadataService: ModuleMetadataService,
|
|
99
111
|
@Inject(forwardRef(() => ModelMetadataService))
|
|
100
112
|
private readonly modelMetadataService: ModelMetadataService,
|
|
113
|
+
private readonly eventEmitter: EventEmitter2,
|
|
101
114
|
private readonly fieldMetadataService: FieldMetadataService,
|
|
102
115
|
private readonly mediaStorageProviderMetadataService: MediaStorageProviderMetadataService,
|
|
103
116
|
private readonly roleService: RoleMetadataService,
|
|
@@ -131,7 +144,26 @@ export class ModuleMetadataSeederService {
|
|
|
131
144
|
let currentModule = 'global';
|
|
132
145
|
let currentStep = 'bootstrap';
|
|
133
146
|
let modulesToSeed: string[] | null = null;
|
|
147
|
+
const requestedModulesToSeed = Array.isArray(conf?.modulesToSeed) ? [...conf.modulesToSeed] : null;
|
|
134
148
|
const shouldSeedGlobalMetadata = conf?.seedGlobalMetadata !== false;
|
|
149
|
+
const seedOptions: ModuleMetadataSeederEventPayload['options'] = {
|
|
150
|
+
modulesToSeed: requestedModulesToSeed,
|
|
151
|
+
pruneMetadata: Boolean(conf?.pruneMetadata),
|
|
152
|
+
seedGlobalMetadata: shouldSeedGlobalMetadata,
|
|
153
|
+
};
|
|
154
|
+
const seedRunId = uuidv4();
|
|
155
|
+
const startedAt = new Date();
|
|
156
|
+
const seededModuleNames: string[] = [];
|
|
157
|
+
|
|
158
|
+
this.emitModuleMetadataSeederEvent(
|
|
159
|
+
EventType.MODULE_METADATA_SEEDER_STARTED,
|
|
160
|
+
{
|
|
161
|
+
seedRunId,
|
|
162
|
+
options: seedOptions,
|
|
163
|
+
startedAt: startedAt.toISOString(),
|
|
164
|
+
currentStep,
|
|
165
|
+
},
|
|
166
|
+
);
|
|
135
167
|
|
|
136
168
|
try {
|
|
137
169
|
this.enablePruning = Boolean(conf?.pruneMetadata);
|
|
@@ -190,6 +222,7 @@ export class ModuleMetadataSeederService {
|
|
|
190
222
|
|
|
191
223
|
console.log(`▶ Seeding Metadata for Module: ${moduleMetadata.name}`);
|
|
192
224
|
this.logger.log(`Seeding Metadata for Module: ${moduleMetadata.name}`);
|
|
225
|
+
seededModuleNames.push(moduleMetadata.name);
|
|
193
226
|
|
|
194
227
|
await this.timeOperation('module-total', async () => {
|
|
195
228
|
currentStep = 'seedMediaStorageProviders';
|
|
@@ -283,10 +316,37 @@ export class ModuleMetadataSeederService {
|
|
|
283
316
|
// Add a console log indicating seeding is finished. This needs to be console.log so that it looks proper when this code is run via CLI.
|
|
284
317
|
console.log(`✔ Seeding completed.`);
|
|
285
318
|
//this.logger.log(`All Seeders finished`);
|
|
319
|
+
await this.emitModuleMetadataSeederFinishedEvent(
|
|
320
|
+
EventType.MODULE_METADATA_SEEDER_FINISHED,
|
|
321
|
+
{
|
|
322
|
+
seedRunId,
|
|
323
|
+
options: seedOptions,
|
|
324
|
+
startedAt: startedAt.toISOString(),
|
|
325
|
+
finishedAt: new Date().toISOString(),
|
|
326
|
+
durationMs: Date.now() - startedAt.getTime(),
|
|
327
|
+
success: true,
|
|
328
|
+
seededModuleNames,
|
|
329
|
+
currentStep,
|
|
330
|
+
},
|
|
331
|
+
);
|
|
286
332
|
|
|
287
333
|
//FIXME: Handle displaying the created users credentials in a better way.
|
|
288
334
|
// this.logger.log(`Newly created username is: ${usersDetail?.length > 0 ? usersDetail[0]?.username : ''} and password is ${usersDetail?.length > 0 ? usersDetail[0]?.password : ''}`);
|
|
289
335
|
} catch (error: any) {
|
|
336
|
+
await this.emitModuleMetadataSeederFinishedEvent(
|
|
337
|
+
EventType.MODULE_METADATA_SEEDER_FINISHED,
|
|
338
|
+
{
|
|
339
|
+
seedRunId,
|
|
340
|
+
options: seedOptions,
|
|
341
|
+
startedAt: startedAt.toISOString(),
|
|
342
|
+
finishedAt: new Date().toISOString(),
|
|
343
|
+
durationMs: Date.now() - startedAt.getTime(),
|
|
344
|
+
success: false,
|
|
345
|
+
seededModuleNames,
|
|
346
|
+
currentStep,
|
|
347
|
+
errorMessage: error?.message,
|
|
348
|
+
},
|
|
349
|
+
);
|
|
290
350
|
this.logSeedFailureForCli(error, {
|
|
291
351
|
moduleName: currentModule,
|
|
292
352
|
step: currentStep,
|
|
@@ -297,6 +357,31 @@ export class ModuleMetadataSeederService {
|
|
|
297
357
|
}
|
|
298
358
|
}
|
|
299
359
|
|
|
360
|
+
private emitModuleMetadataSeederEvent(
|
|
361
|
+
type: EventType.MODULE_METADATA_SEEDER_STARTED | EventType.MODULE_METADATA_SEEDER_FINISHED,
|
|
362
|
+
payload: ModuleMetadataSeederEventPayload,
|
|
363
|
+
): void {
|
|
364
|
+
try {
|
|
365
|
+
this.eventEmitter.emit(type, new EventDetails<ModuleMetadataSeederEventPayload>(type, payload));
|
|
366
|
+
} catch (error: any) {
|
|
367
|
+
this.logger.warn(`Failed to emit ${type}: ${error?.message ?? error}`);
|
|
368
|
+
}
|
|
369
|
+
}
|
|
370
|
+
|
|
371
|
+
private async emitModuleMetadataSeederFinishedEvent(
|
|
372
|
+
type: EventType.MODULE_METADATA_SEEDER_FINISHED,
|
|
373
|
+
payload: ModuleMetadataSeederEventPayload,
|
|
374
|
+
): Promise<void> {
|
|
375
|
+
try {
|
|
376
|
+
console.log(`▶ Running post-seed hooks for runId=${payload.seedRunId}`);
|
|
377
|
+
await this.eventEmitter.emitAsync(type, new EventDetails<ModuleMetadataSeederEventPayload>(type, payload));
|
|
378
|
+
console.log(`✔ Post-seed hooks completed for runId=${payload.seedRunId}`);
|
|
379
|
+
} catch (error: any) {
|
|
380
|
+
console.log(`✖ Post-seed hooks failed for runId=${payload.seedRunId}: ${error?.message ?? error}`);
|
|
381
|
+
this.logger.warn(`Failed to emit ${type}: ${error?.message ?? error}`);
|
|
382
|
+
}
|
|
383
|
+
}
|
|
384
|
+
|
|
300
385
|
private buildTimingPrefix(itemTag: string, options?: { moduleName?: string; component?: string; serviceCall?: string }): string {
|
|
301
386
|
const parts = [`[${this.seedTimingTag}]`, `[ITEM:${itemTag}]`];
|
|
302
387
|
if (options?.moduleName) {
|
|
@@ -498,10 +583,17 @@ export class ModuleMetadataSeederService {
|
|
|
498
583
|
|
|
499
584
|
private async setupDefaultRolesWithPermissions() {
|
|
500
585
|
this.logger.debug(`About to add all permissions to the Admin role`);
|
|
501
|
-
await this.timeOperation('role-add-all-permissions', () => this.roleService.
|
|
586
|
+
await this.timeOperation('role-add-all-permissions', () => this.roleService.addAllPermissionsToRoleExceptPrefixes(ADMIN_ROLE_NAME, this.adminPermissionExclusionPrefixes), {
|
|
587
|
+
moduleName: 'global',
|
|
588
|
+
component: 'default-roles',
|
|
589
|
+
serviceCall: 'roleService.addAllPermissionsToRoleExceptPrefixes',
|
|
590
|
+
details: `role=${ADMIN_ROLE_NAME}`,
|
|
591
|
+
});
|
|
592
|
+
|
|
593
|
+
await this.timeOperation('attach-capability-roles-to-admin-users', () => this.attachCapabilityRolesToAdminUsers(), {
|
|
502
594
|
moduleName: 'global',
|
|
503
595
|
component: 'default-roles',
|
|
504
|
-
serviceCall: '
|
|
596
|
+
serviceCall: 'attachCapabilityRolesToAdminUsers',
|
|
505
597
|
details: `role=${ADMIN_ROLE_NAME}`,
|
|
506
598
|
});
|
|
507
599
|
|
|
@@ -514,6 +606,20 @@ export class ModuleMetadataSeederService {
|
|
|
514
606
|
// await this.roleService.addPermissionToRole(PUBLIC_ROLE_NAME, ['SettingController.wrapSettings', 'AuthenticationController.logout']);
|
|
515
607
|
}
|
|
516
608
|
|
|
609
|
+
private async attachCapabilityRolesToAdminUsers(): Promise<void> {
|
|
610
|
+
const adminUsers = await this.userService.findUsersByRole(ADMIN_ROLE_NAME, {});
|
|
611
|
+
if (!adminUsers?.length) {
|
|
612
|
+
return;
|
|
613
|
+
}
|
|
614
|
+
|
|
615
|
+
const capabilityRoles = [ALLOWED_TO_IMPORT_ROLE_NAME, ALLOWED_TO_EXPORT_ROLE_NAME];
|
|
616
|
+
for (const adminUser of adminUsers) {
|
|
617
|
+
for (const capabilityRole of capabilityRoles) {
|
|
618
|
+
await this.userService.addRoleToUser(adminUser.username, capabilityRole);
|
|
619
|
+
}
|
|
620
|
+
}
|
|
621
|
+
}
|
|
622
|
+
|
|
517
623
|
private async seedSecurityRules(overallMetadata: any): Promise<{ pruned: number; upserted: number }> {
|
|
518
624
|
const securityRules = this.getSeedArray<CreateSecurityRuleDto>(overallMetadata?.securityRules);
|
|
519
625
|
const pruned = this.enablePruning ? await this.timeOperation('prune-security-rules', () => this.pruneSecurityRules(securityRules, overallMetadata?.moduleMetadata?.name), {
|
|
@@ -6,6 +6,11 @@ import { RoleMetadataService } from '../services/role-metadata.service';
|
|
|
6
6
|
@Injectable()
|
|
7
7
|
export class PermissionMetadataSeederService {
|
|
8
8
|
private readonly logger = new Logger(PermissionMetadataSeederService.name);
|
|
9
|
+
private readonly adminPermissionExclusionPrefixes = [
|
|
10
|
+
'ImportTransactionController.',
|
|
11
|
+
'ExportTemplateController.',
|
|
12
|
+
'ExportTransactionController.',
|
|
13
|
+
];
|
|
9
14
|
|
|
10
15
|
constructor(
|
|
11
16
|
// @InjectRepository(PermissionMetadata)
|
|
@@ -58,6 +63,6 @@ export class PermissionMetadataSeederService {
|
|
|
58
63
|
}
|
|
59
64
|
|
|
60
65
|
// Associate the Admin role with all existing permissions.
|
|
61
|
-
await this.roleService.
|
|
66
|
+
await this.roleService.addAllPermissionsToRoleExceptPrefixes("Admin", this.adminPermissionExclusionPrefixes);
|
|
62
67
|
}
|
|
63
68
|
}
|
|
@@ -5336,14 +5336,6 @@
|
|
|
5336
5336
|
"ChatterMessageController.findMany",
|
|
5337
5337
|
"ChatterMessageController.markCompleted",
|
|
5338
5338
|
"ChatterMessageController.updateCustomNoteMessage",
|
|
5339
|
-
"ImportTransactionController.getImportTemplate",
|
|
5340
|
-
"ImportTransactionController.getImportInstructions",
|
|
5341
|
-
"ImportTransactionController.getImportMappingInfo",
|
|
5342
|
-
"ImportTransactionController.startImportSync",
|
|
5343
|
-
"ImportTransactionController.startImportAsync",
|
|
5344
|
-
"ImportTransactionController.exportFailedImportedImports",
|
|
5345
|
-
"ExportTemplateController.startExportSync",
|
|
5346
|
-
"ExportTemplateController.startExportAsync",
|
|
5347
5339
|
"ListOfValuesController.findMany",
|
|
5348
5340
|
"ListOfValuesController.findOne",
|
|
5349
5341
|
"SettingController.getAllSettings",
|
|
@@ -5363,6 +5355,31 @@
|
|
|
5363
5355
|
"agent:invoke"
|
|
5364
5356
|
]
|
|
5365
5357
|
},
|
|
5358
|
+
{
|
|
5359
|
+
"name": "Allowed To Import",
|
|
5360
|
+
"permissions": [
|
|
5361
|
+
"ImportTransactionController.create",
|
|
5362
|
+
"ImportTransactionController.delete",
|
|
5363
|
+
"ImportTransactionController.deleteMany",
|
|
5364
|
+
"ImportTransactionController.getImportTemplate",
|
|
5365
|
+
"ImportTransactionController.getImportInstructions",
|
|
5366
|
+
"ImportTransactionController.getImportMappingInfo",
|
|
5367
|
+
"ImportTransactionController.partialUpdate",
|
|
5368
|
+
"ImportTransactionController.startImportSync",
|
|
5369
|
+
"ImportTransactionController.startImportAsync",
|
|
5370
|
+
"ImportTransactionController.exportFailedImportedImports"
|
|
5371
|
+
]
|
|
5372
|
+
},
|
|
5373
|
+
{
|
|
5374
|
+
"name": "Allowed To Export",
|
|
5375
|
+
"permissions": [
|
|
5376
|
+
"ExportTemplateController.create",
|
|
5377
|
+
"ExportTemplateController.delete",
|
|
5378
|
+
"ExportTemplateController.findMany",
|
|
5379
|
+
"ExportTemplateController.startExportSync",
|
|
5380
|
+
"ExportTemplateController.startExportAsync"
|
|
5381
|
+
]
|
|
5382
|
+
},
|
|
5366
5383
|
{
|
|
5367
5384
|
"name": "Public",
|
|
5368
5385
|
"permissions": [
|
|
@@ -8630,8 +8647,7 @@
|
|
|
8630
8647
|
"attrs": {
|
|
8631
8648
|
"name": "form-1",
|
|
8632
8649
|
"label": "User",
|
|
8633
|
-
"className": "grid"
|
|
8634
|
-
"width": "20vw"
|
|
8650
|
+
"className": "grid"
|
|
8635
8651
|
},
|
|
8636
8652
|
"children": [
|
|
8637
8653
|
{
|
|
@@ -109,6 +109,26 @@ export class AuthenticationService {
|
|
|
109
109
|
});
|
|
110
110
|
}
|
|
111
111
|
|
|
112
|
+
private async resolveUserForPasswordSignIn(username: string, email: string) {
|
|
113
|
+
const normalizedEmail = email?.trim().toLowerCase();
|
|
114
|
+
const query = (await this.userRepository
|
|
115
|
+
.createSecurityRuleAwareQueryBuilder("u"))
|
|
116
|
+
.leftJoinAndSelect("u.roles", "roles");
|
|
117
|
+
|
|
118
|
+
if (username) {
|
|
119
|
+
query.where("u.username = :username", { username });
|
|
120
|
+
}
|
|
121
|
+
if (normalizedEmail) {
|
|
122
|
+
if (username) {
|
|
123
|
+
query.orWhere("LOWER(u.email) = :email", { email: normalizedEmail });
|
|
124
|
+
} else {
|
|
125
|
+
query.where("LOWER(u.email) = :email", { email: normalizedEmail });
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
|
|
129
|
+
return await query.getOne();
|
|
130
|
+
}
|
|
131
|
+
|
|
112
132
|
async updatePasswordDetails(user: User, newPassword: string) {
|
|
113
133
|
user.password = await this.hashingService.hash(newPassword);
|
|
114
134
|
user.passwordScheme = this.hashingService.name();
|
|
@@ -985,7 +1005,10 @@ export class AuthenticationService {
|
|
|
985
1005
|
}
|
|
986
1006
|
|
|
987
1007
|
async signIn(signInDto: SignInDto) {
|
|
988
|
-
const user = await this.
|
|
1008
|
+
const user = await this.resolveUserForPasswordSignIn(
|
|
1009
|
+
signInDto.username,
|
|
1010
|
+
signInDto.email,
|
|
1011
|
+
);
|
|
989
1012
|
if (!user) {
|
|
990
1013
|
throw new UnauthorizedException(ERROR_MESSAGES.INVALID_CREDENTIALS);
|
|
991
1014
|
}
|
|
@@ -140,6 +140,10 @@ export class RoleMetadataService extends CRUDService<RoleMetadata> {
|
|
|
140
140
|
return await this._addPermissionsToRole(roleName, null);
|
|
141
141
|
}
|
|
142
142
|
|
|
143
|
+
async addAllPermissionsToRoleExceptPrefixes(roleName: string, excludedPermissionPrefixes: string[]): Promise<RoleMetadata> {
|
|
144
|
+
return await this._addPermissionsToRole(roleName, null, excludedPermissionPrefixes);
|
|
145
|
+
}
|
|
146
|
+
|
|
143
147
|
async addPermissionsToRole(roleName: string, permissionNames: string[]): Promise<RoleMetadata> {
|
|
144
148
|
return await this._addPermissionsToRole(roleName, permissionNames);
|
|
145
149
|
}
|
|
@@ -148,7 +152,11 @@ export class RoleMetadataService extends CRUDService<RoleMetadata> {
|
|
|
148
152
|
return await this._addPermissionsToRole(roleName, permissionName);
|
|
149
153
|
}
|
|
150
154
|
|
|
151
|
-
private async _addPermissionsToRole(
|
|
155
|
+
private async _addPermissionsToRole(
|
|
156
|
+
roleName: string,
|
|
157
|
+
permissionNames: string[],
|
|
158
|
+
excludedPermissionPrefixes: string[] = [],
|
|
159
|
+
): Promise<RoleMetadata> {
|
|
152
160
|
const role = await this.repo.findOne({
|
|
153
161
|
where: { name: roleName },
|
|
154
162
|
select: {
|
|
@@ -161,7 +169,7 @@ export class RoleMetadataService extends CRUDService<RoleMetadata> {
|
|
|
161
169
|
}
|
|
162
170
|
|
|
163
171
|
const joinInfo = this.getRolePermissionJoinInfo();
|
|
164
|
-
const targetPermissions = await this.loadTargetPermissions(permissionNames);
|
|
172
|
+
const targetPermissions = await this.loadTargetPermissions(permissionNames, excludedPermissionPrefixes);
|
|
165
173
|
|
|
166
174
|
if (!permissionNames || permissionNames.length === 0) {
|
|
167
175
|
await this.entityManager
|
|
@@ -226,21 +234,25 @@ export class RoleMetadataService extends CRUDService<RoleMetadata> {
|
|
|
226
234
|
return existingPermission;
|
|
227
235
|
}
|
|
228
236
|
|
|
229
|
-
private async loadTargetPermissions(permissionNames: string[] | null): Promise<PermissionMetadata[]> {
|
|
237
|
+
private async loadTargetPermissions(permissionNames: string[] | null, excludedPermissionPrefixes: string[] = []): Promise<PermissionMetadata[]> {
|
|
230
238
|
if (permissionNames && permissionNames.length !== 0) {
|
|
231
239
|
const uniquePermissionNames = [...new Set(permissionNames)];
|
|
232
240
|
const permissions = await this.permissionRepository.find({ where: { name: In(uniquePermissionNames) } });
|
|
233
241
|
if (permissions.length !== uniquePermissionNames.length) {
|
|
234
242
|
throw new Error(`One or more permissions not found.`);
|
|
235
243
|
}
|
|
236
|
-
return permissions
|
|
244
|
+
return permissions.filter((permission) =>
|
|
245
|
+
!excludedPermissionPrefixes.some((prefix) => permission.name.startsWith(prefix)),
|
|
246
|
+
);
|
|
237
247
|
}
|
|
238
248
|
|
|
239
249
|
const permissions = await this.permissionRepository.find();
|
|
240
250
|
if (permissions.length === 0) {
|
|
241
251
|
throw new Error(`No permissions configured in the system. Did you forget to run the PermissionSeederService?`);
|
|
242
252
|
}
|
|
243
|
-
return permissions
|
|
253
|
+
return permissions.filter((permission) =>
|
|
254
|
+
!excludedPermissionPrefixes.some((prefix) => permission.name.startsWith(prefix)),
|
|
255
|
+
);
|
|
244
256
|
}
|
|
245
257
|
|
|
246
258
|
private getRolePermissionJoinInfo(): { tableName: string; roleIdColumn: string; permissionIdColumn: string } {
|