@solidstarters/solid-core 1.2.48 → 1.2.50
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/controllers/security-rule.controller.d.ts +41 -0
- package/dist/controllers/security-rule.controller.d.ts.map +1 -0
- package/dist/controllers/security-rule.controller.js +179 -0
- package/dist/controllers/security-rule.controller.js.map +1 -0
- package/dist/dtos/create-model-metadata.dto.d.ts +3 -0
- package/dist/dtos/create-model-metadata.dto.d.ts.map +1 -1
- package/dist/dtos/create-model-metadata.dto.js +18 -1
- package/dist/dtos/create-model-metadata.dto.js.map +1 -1
- package/dist/dtos/create-security-rule.dto.d.ts +10 -0
- package/dist/dtos/create-security-rule.dto.d.ts.map +1 -0
- package/dist/dtos/create-security-rule.dto.js +65 -0
- package/dist/dtos/create-security-rule.dto.js.map +1 -0
- package/dist/dtos/security-rule-config.dto.d.ts +4 -0
- package/dist/dtos/security-rule-config.dto.d.ts.map +1 -0
- package/dist/dtos/security-rule-config.dto.js +4 -0
- package/dist/dtos/security-rule-config.dto.js.map +1 -0
- package/dist/dtos/update-security-rule.dto.d.ts +11 -0
- package/dist/dtos/update-security-rule.dto.d.ts.map +1 -0
- package/dist/dtos/update-security-rule.dto.js +72 -0
- package/dist/dtos/update-security-rule.dto.js.map +1 -0
- package/dist/entities/email-template.entity.js +1 -1
- package/dist/entities/email-template.entity.js.map +1 -1
- package/dist/entities/model-metadata.entity.d.ts +2 -0
- package/dist/entities/model-metadata.entity.d.ts.map +1 -1
- package/dist/entities/model-metadata.entity.js +9 -1
- package/dist/entities/model-metadata.entity.js.map +1 -1
- package/dist/entities/security-rule.entity.d.ts +11 -0
- package/dist/entities/security-rule.entity.d.ts.map +1 -0
- package/dist/entities/security-rule.entity.js +53 -0
- package/dist/entities/security-rule.entity.js.map +1 -0
- package/dist/entities/user.entity.d.ts.map +1 -1
- package/dist/entities/user.entity.js +2 -1
- package/dist/entities/user.entity.js.map +1 -1
- package/dist/helpers/solid-registry.d.ts +22 -1
- package/dist/helpers/solid-registry.d.ts.map +1 -1
- package/dist/helpers/solid-registry.js +29 -0
- package/dist/helpers/solid-registry.js.map +1 -1
- package/dist/index.d.ts +7 -0
- package/dist/index.d.ts.map +1 -1
- package/dist/index.js +7 -0
- package/dist/index.js.map +1 -1
- package/dist/interfaces.d.ts +2 -0
- package/dist/interfaces.d.ts.map +1 -1
- package/dist/interfaces.js.map +1 -1
- package/dist/repository/security-rule.repository.d.ts +20 -0
- package/dist/repository/security-rule.repository.d.ts.map +1 -0
- package/dist/repository/security-rule.repository.js +128 -0
- package/dist/repository/security-rule.repository.js.map +1 -0
- package/dist/repository/solid-base.repository.d.ts +14 -0
- package/dist/repository/solid-base.repository.d.ts.map +1 -0
- package/dist/repository/solid-base.repository.js +26 -0
- package/dist/repository/solid-base.repository.js.map +1 -0
- package/dist/seeders/module-metadata-seeder.service.d.ts +5 -1
- package/dist/seeders/module-metadata-seeder.service.d.ts.map +1 -1
- package/dist/seeders/module-metadata-seeder.service.js +22 -2
- package/dist/seeders/module-metadata-seeder.service.js.map +1 -1
- package/dist/seeders/seed-data/solid-core-metadata.json +263 -0
- package/dist/services/field-metadata.service.d.ts.map +1 -1
- package/dist/services/field-metadata.service.js +1 -0
- package/dist/services/field-metadata.service.js.map +1 -1
- package/dist/services/module-metadata.service.d.ts.map +1 -1
- package/dist/services/module-metadata.service.js +1 -0
- package/dist/services/module-metadata.service.js.map +1 -1
- package/dist/services/request-context.service.d.ts +7 -0
- package/dist/services/request-context.service.d.ts.map +1 -0
- package/dist/services/request-context.service.js +33 -0
- package/dist/services/request-context.service.js.map +1 -0
- package/dist/services/security-rule.service.d.ts +27 -0
- package/dist/services/security-rule.service.d.ts.map +1 -0
- package/dist/services/security-rule.service.js +71 -0
- package/dist/services/security-rule.service.js.map +1 -0
- package/dist/services/view-metadata.service.d.ts +1 -0
- package/dist/services/view-metadata.service.d.ts.map +1 -1
- package/dist/services/view-metadata.service.js +22 -7
- package/dist/services/view-metadata.service.js.map +1 -1
- package/dist/solid-core.module.d.ts.map +1 -1
- package/dist/solid-core.module.js +15 -1
- package/dist/solid-core.module.js.map +1 -1
- package/dist/subscribers/security-rule.subscriber.d.ts +16 -0
- package/dist/subscribers/security-rule.subscriber.d.ts.map +1 -0
- package/dist/subscribers/security-rule.subscriber.js +123 -0
- package/dist/subscribers/security-rule.subscriber.js.map +1 -0
- package/dist/tsconfig.tsbuildinfo +1 -1
- package/package.json +1 -1
- package/src/controllers/security-rule.controller.ts +93 -0
- package/src/dtos/create-model-metadata.dto.ts +14 -0
- package/src/dtos/create-security-rule.dto.ts +34 -0
- package/src/dtos/security-rule-config.dto.ts +5 -0
- package/src/dtos/update-security-rule.dto.ts +39 -0
- package/src/entities/email-template.entity.ts +1 -1
- package/src/entities/model-metadata.entity.ts +6 -0
- package/src/entities/security-rule.entity.ts +25 -0
- package/src/entities/user.entity.ts +2 -1
- package/src/helpers/solid-registry.ts +34 -0
- package/src/index.ts +9 -0
- package/src/interfaces.ts +2 -0
- package/src/repository/security-rule.repository.ts +135 -0
- package/src/repository/solid-base.repository.ts +45 -0
- package/src/seeders/module-metadata-seeder.service.ts +28 -1
- package/src/seeders/seed-data/solid-core-metadata.json +264 -0
- package/src/seeders/seed-data/solid-core-metadata.json.bkp +6638 -0
- package/src/services/field-metadata.service.ts +1 -0
- package/src/services/module-metadata.service.ts +1 -0
- package/src/services/request-context.service.ts +16 -0
- package/src/services/security-rule.service.ts +54 -0
- package/src/services/view-metadata.service.ts +26 -7
- package/src/solid-core.module.ts +15 -1
- package/src/subscribers/security-rule.subscriber.ts +78 -0
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { Inject, Injectable, Scope } from "@nestjs/common";
|
|
2
|
+
import { REQUEST } from "@nestjs/core";
|
|
3
|
+
import { REQUEST_USER_KEY } from "src/constants";
|
|
4
|
+
import { ActiveUserData } from "src/interfaces/active-user-data.interface";
|
|
5
|
+
|
|
6
|
+
@Injectable({scope: Scope.REQUEST})
|
|
7
|
+
export class RequestContextService {
|
|
8
|
+
constructor(@Inject(REQUEST) private readonly request: Request) {
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
// This method i.e getActiveUser() will fetch the user from the request object in the context
|
|
12
|
+
getActiveUser() {
|
|
13
|
+
return this.request[REQUEST_USER_KEY] as ActiveUserData| undefined;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
}
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
import { Injectable, OnApplicationBootstrap } from '@nestjs/common';
|
|
2
|
+
import { InjectEntityManager, InjectRepository } from '@nestjs/typeorm';
|
|
3
|
+
import { DiscoveryService, ModuleRef } from "@nestjs/core";
|
|
4
|
+
import { EntityManager, Repository } from 'typeorm';
|
|
5
|
+
|
|
6
|
+
import { CRUDService } from 'src/services/crud.service';
|
|
7
|
+
import { ModelMetadataService } from 'src/services/model-metadata.service';
|
|
8
|
+
import { ModuleMetadataService } from 'src/services/module-metadata.service';
|
|
9
|
+
import { ConfigService } from '@nestjs/config';
|
|
10
|
+
import { FileService } from 'src/services/file.service';
|
|
11
|
+
import { CrudHelperService } from 'src/services/crud-helper.service';
|
|
12
|
+
|
|
13
|
+
|
|
14
|
+
import { SecurityRule } from '../entities/security-rule.entity';
|
|
15
|
+
import { SolidRegistry } from 'src/helpers/solid-registry';
|
|
16
|
+
|
|
17
|
+
@Injectable()
|
|
18
|
+
export class SecurityRuleService extends CRUDService<SecurityRule> implements OnApplicationBootstrap {
|
|
19
|
+
constructor(
|
|
20
|
+
readonly modelMetadataService: ModelMetadataService,
|
|
21
|
+
readonly moduleMetadataService: ModuleMetadataService,
|
|
22
|
+
readonly configService: ConfigService,
|
|
23
|
+
readonly fileService: FileService,
|
|
24
|
+
readonly discoveryService: DiscoveryService,
|
|
25
|
+
readonly crudHelperService: CrudHelperService,
|
|
26
|
+
@InjectEntityManager()
|
|
27
|
+
readonly entityManager: EntityManager,
|
|
28
|
+
@InjectRepository(SecurityRule, 'default')
|
|
29
|
+
readonly repo: Repository<SecurityRule>,
|
|
30
|
+
readonly moduleRef: ModuleRef,
|
|
31
|
+
readonly solidRegistry: SolidRegistry,
|
|
32
|
+
|
|
33
|
+
) {
|
|
34
|
+
super(modelMetadataService, moduleMetadataService, configService, fileService, discoveryService, crudHelperService, entityManager, repo, 'securityRule', 'solid-core', moduleRef);
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
onApplicationBootstrap() {
|
|
38
|
+
// Load the security rules from the database
|
|
39
|
+
this.loadSecurityRules();
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
async loadSecurityRules() {
|
|
43
|
+
const securityRules = await this.repo.find(
|
|
44
|
+
{
|
|
45
|
+
relations: {
|
|
46
|
+
modelMetadata: true,
|
|
47
|
+
role: true,
|
|
48
|
+
}
|
|
49
|
+
}
|
|
50
|
+
);
|
|
51
|
+
this.solidRegistry.registerSecurityRules(securityRules);
|
|
52
|
+
}
|
|
53
|
+
|
|
54
|
+
}
|
|
@@ -108,13 +108,7 @@ export class ViewMetadataService extends CRUDService<ViewMetadata> {
|
|
|
108
108
|
}
|
|
109
109
|
|
|
110
110
|
// We also need to fetch a map of fields.
|
|
111
|
-
const fields = await this.
|
|
112
|
-
where: {
|
|
113
|
-
model: {
|
|
114
|
-
singularName: modelName,
|
|
115
|
-
}
|
|
116
|
-
}
|
|
117
|
-
});
|
|
111
|
+
const fields = await this.loadFieldHierarchy(modelName);
|
|
118
112
|
const fieldsMap = new Map<string, FieldMetadata>();
|
|
119
113
|
for (let i = 0; i < fields.length; i++) {
|
|
120
114
|
const field = fields[i];
|
|
@@ -179,6 +173,31 @@ export class ViewMetadataService extends CRUDService<ViewMetadata> {
|
|
|
179
173
|
return r;
|
|
180
174
|
}
|
|
181
175
|
|
|
176
|
+
private async loadFieldHierarchy(modelName: any) {
|
|
177
|
+
const model = await this.modelMetadataRepo.findOne({
|
|
178
|
+
where: {
|
|
179
|
+
singularName: modelName,
|
|
180
|
+
},
|
|
181
|
+
relations: {
|
|
182
|
+
fields: true,
|
|
183
|
+
parentModel: {
|
|
184
|
+
fields: true,
|
|
185
|
+
}
|
|
186
|
+
}
|
|
187
|
+
});
|
|
188
|
+
const fields = [];
|
|
189
|
+
if (model) {
|
|
190
|
+
// Add the fields of the current model
|
|
191
|
+
fields.push(...model.fields);
|
|
192
|
+
|
|
193
|
+
// Add the fields of the parent model
|
|
194
|
+
if (model.parentModel) {
|
|
195
|
+
fields.push(...model.parentModel.fields);
|
|
196
|
+
}
|
|
197
|
+
}
|
|
198
|
+
return fields;
|
|
199
|
+
}
|
|
200
|
+
|
|
182
201
|
async findOneByUserKey(name: string, relations = {}) {
|
|
183
202
|
const entity = await this.repo.findOne({
|
|
184
203
|
where: {
|
package/src/solid-core.module.ts
CHANGED
|
@@ -144,6 +144,12 @@ import { ViewMetadataSubsciber } from './subscribers/view-metadata.subscriber';
|
|
|
144
144
|
import { UserViewMetadata } from './entities/user-view-metadata.entity';
|
|
145
145
|
import { UserViewMetadataService } from './services/user-view-metadata.service';
|
|
146
146
|
import { UserViewMetadataController } from './controllers/user-view-metadata.controller';
|
|
147
|
+
import { SecurityRule } from './entities/security-rule.entity';
|
|
148
|
+
import { SecurityRuleService } from './services/security-rule.service';
|
|
149
|
+
import { SecurityRuleController } from './controllers/security-rule.controller';
|
|
150
|
+
import { RequestContextService } from './services/request-context.service';
|
|
151
|
+
import { SecurityRuleRepository } from './repository/security-rule.repository';
|
|
152
|
+
import { SecurityRuleSubscriber } from './subscribers/security-rule.subscriber';
|
|
147
153
|
|
|
148
154
|
|
|
149
155
|
@Global()
|
|
@@ -189,6 +195,7 @@ import { UserViewMetadataController } from './controllers/user-view-metadata.con
|
|
|
189
195
|
ConfigModule,
|
|
190
196
|
TypeOrmModule.forFeature([Setting]),
|
|
191
197
|
TypeOrmModule.forFeature([UserViewMetadata]),
|
|
198
|
+
TypeOrmModule.forFeature([SecurityRule]),
|
|
192
199
|
// TypeOrmModule.forFeature([User]),
|
|
193
200
|
],
|
|
194
201
|
controllers: [
|
|
@@ -215,6 +222,7 @@ import { UserViewMetadataController } from './controllers/user-view-metadata.con
|
|
|
215
222
|
UserController,
|
|
216
223
|
SettingController,
|
|
217
224
|
UserViewMetadataController,
|
|
225
|
+
SecurityRuleController,
|
|
218
226
|
],
|
|
219
227
|
providers: [
|
|
220
228
|
{
|
|
@@ -309,7 +317,11 @@ import { UserViewMetadataController } from './controllers/user-view-metadata.con
|
|
|
309
317
|
FileS3StorageProvider,
|
|
310
318
|
MediaRepository,
|
|
311
319
|
ViewMetadataSubsciber,
|
|
312
|
-
UserViewMetadataService
|
|
320
|
+
UserViewMetadataService,
|
|
321
|
+
SecurityRuleService,
|
|
322
|
+
SecurityRuleRepository,
|
|
323
|
+
SecurityRuleSubscriber,
|
|
324
|
+
RequestContextService,
|
|
313
325
|
],
|
|
314
326
|
exports: [
|
|
315
327
|
ModuleMetadataService,
|
|
@@ -337,6 +349,8 @@ import { UserViewMetadataController } from './controllers/user-view-metadata.con
|
|
|
337
349
|
MqMessageService,
|
|
338
350
|
RefreshModelCommand,
|
|
339
351
|
RefreshModuleCommand,
|
|
352
|
+
RequestContextService,
|
|
353
|
+
SecurityRuleRepository,
|
|
340
354
|
],
|
|
341
355
|
})
|
|
342
356
|
export class SolidCoreModule { }
|
|
@@ -0,0 +1,78 @@
|
|
|
1
|
+
import { Injectable, Logger } from '@nestjs/common';
|
|
2
|
+
import { InjectDataSource } from "@nestjs/typeorm";
|
|
3
|
+
import * as fs from 'fs/promises'; // Use the Promise-based version of fs for async/await
|
|
4
|
+
import { ModelMetadata } from 'src/entities/model-metadata.entity';
|
|
5
|
+
import { SecurityRule } from 'src/entities/security-rule.entity';
|
|
6
|
+
import { ModuleMetadataHelperService } from "src/helpers/module-metadata-helper.service";
|
|
7
|
+
import { SecurityRuleRepository } from 'src/repository/security-rule.repository';
|
|
8
|
+
import { DataSource, EntitySubscriberInterface, InsertEvent, UpdateEvent } from "typeorm";
|
|
9
|
+
|
|
10
|
+
@Injectable()
|
|
11
|
+
export class SecurityRuleSubscriber implements EntitySubscriberInterface<SecurityRule> {
|
|
12
|
+
private readonly logger = new Logger(SecurityRuleSubscriber.name);
|
|
13
|
+
constructor(
|
|
14
|
+
@InjectDataSource()
|
|
15
|
+
private readonly dataSource: DataSource,
|
|
16
|
+
readonly moduleMetadataHelperService: ModuleMetadataHelperService,
|
|
17
|
+
readonly securityRuleRepo: SecurityRuleRepository,
|
|
18
|
+
) {
|
|
19
|
+
this.dataSource.subscribers.push(this);
|
|
20
|
+
}
|
|
21
|
+
|
|
22
|
+
listenTo() {
|
|
23
|
+
return SecurityRule;
|
|
24
|
+
}
|
|
25
|
+
|
|
26
|
+
async afterInsert(event: InsertEvent<SecurityRule>) {
|
|
27
|
+
await this.saveSecurityRules(event);
|
|
28
|
+
}
|
|
29
|
+
|
|
30
|
+
async afterUpdate(event: UpdateEvent<SecurityRule>) {
|
|
31
|
+
await this.saveSecurityRules(event);
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
async saveSecurityRules(event: UpdateEvent<SecurityRule>| InsertEvent<SecurityRule>) {
|
|
35
|
+
const securityRule = event.entity as SecurityRule;
|
|
36
|
+
const modelMetadata = event.entity.modelMetadata;
|
|
37
|
+
if (!modelMetadata) {
|
|
38
|
+
this.logger.error(`Model metadata not found for security rule with id ${event.entity.id}`);
|
|
39
|
+
return;
|
|
40
|
+
}
|
|
41
|
+
|
|
42
|
+
const modelMetadataRepo = this.dataSource.getRepository(ModelMetadata);
|
|
43
|
+
const populatedModelMetadata = await modelMetadataRepo.findOne({
|
|
44
|
+
where: {
|
|
45
|
+
id: modelMetadata.id
|
|
46
|
+
},
|
|
47
|
+
relations: {
|
|
48
|
+
module: true,
|
|
49
|
+
}
|
|
50
|
+
});
|
|
51
|
+
|
|
52
|
+
const filePath = this.moduleMetadataHelperService.getModuleMetadataFilePath(populatedModelMetadata.module.name);
|
|
53
|
+
try {
|
|
54
|
+
await fs.access(filePath);
|
|
55
|
+
} catch (error) {
|
|
56
|
+
// FIXME - Should we actually delete the security rule here, if the file is not found?
|
|
57
|
+
this.logger.error(`File not found at path: ${filePath}`);
|
|
58
|
+
return;
|
|
59
|
+
}
|
|
60
|
+
const metaData = await this.moduleMetadataHelperService.getModuleMetadataConfiguration(filePath);
|
|
61
|
+
|
|
62
|
+
if (metaData.securityRule) {
|
|
63
|
+
const securityRuleIndex = metaData.securityRules?.findIndex((ruleFromFile: { name: string }) => ruleFromFile.name === securityRule.name);
|
|
64
|
+
const {id, roleId, modelMetadataId, ...requiredDto} = await this.securityRuleRepo.toDto(securityRule)
|
|
65
|
+
metaData.securityRules[securityRuleIndex] = {requiredDto, securityRuleConfig: JSON.parse(securityRule.securityRuleConfig)}
|
|
66
|
+
}
|
|
67
|
+
else {
|
|
68
|
+
const securityRules = []
|
|
69
|
+
const {id, roleId, modelMetadataId, ...requiredDto} = await this.securityRuleRepo.toDto(securityRule)
|
|
70
|
+
securityRules.push({...requiredDto, securityRuleConfig: JSON.parse(securityRule.securityRuleConfig)})
|
|
71
|
+
metaData.securityRules = securityRules
|
|
72
|
+
}
|
|
73
|
+
// Write the updated object back to the file
|
|
74
|
+
const updatedContent = JSON.stringify(metaData, null, 2);
|
|
75
|
+
await fs.writeFile(filePath, updatedContent);
|
|
76
|
+
}
|
|
77
|
+
|
|
78
|
+
}
|