refacto roles and rules

This commit is contained in:
OxSaitama 2023-06-27 18:06:54 +02:00
parent ad7338cd97
commit 037976a1e6
23 changed files with 1490 additions and 1255 deletions

1
.gitignore vendored
View File

@ -6,6 +6,7 @@ dist
# dependencies
/node_modules
package-lock.json
# envs
.env

547
package-lock.json generated

File diff suppressed because it is too large Load Diff

View File

@ -49,7 +49,7 @@
"cors": "^2.8.5",
"express": "^4.18.2",
"jsonwebtoken": "^9.0.0",
"le-coffre-resources": "git@github.com:smart-chain-fr/leCoffre-resources.git#v2.52",
"le-coffre-resources": "git@github.com:smart-chain-fr/leCoffre-resources.git#v2.54",
"module-alias": "^2.2.2",
"multer": "^1.4.5-lts.1",
"next": "^13.1.5",

View File

@ -17,20 +17,24 @@ export default class UserController extends ApiController {
* @todo Used for test, should be removed
* @returns User
*/
// @Post("/api/v1/idnot/user/:code")
// protected async getUserInfosFromIdnot(req: Request, response: Response) {
// console.warn("/api/v1/idnot/user/:code used for test, should be removed");
@Post("/api/v1/idnot/user/:code")
protected async getUserInfosFromIdnot(req: Request, response: Response) {
console.warn("/api/v1/idnot/user/:code used for test, should be removed");
// try {
// const code = req.params["code"];
// const user = await this.authService.getUserFromIdNotTokens(code!);
// //success
// this.httpSuccess(response, user);
// } catch (error) {
// this.httpInternalError(response);
// return;
// }
// }
try {
const code = req.params["code"];
if (!code) throw new Error("code is required");
const token = await fetch('https://qual-connexion.idnot.fr/IdPOAuth2/token/idnot_idp_v1', {method: 'POST'});
console.log(token);
//const user = await this.authService.getUserFromIdNotTokens(code!);
//success
this.httpSuccess(response);
} catch (error) {
console.log(error)
this.httpInternalError(response);
return;
}
}
@Post("/api/v1/idnot/user/login/:idnot")
protected async login(req: Request, response: Response) {
@ -38,7 +42,7 @@ export default class UserController extends ApiController {
const id = req.params["idnot"];
if (!id) throw new Error("idnot is required");
const payload = await this.authService.getUserPayload(id!);
const payload = await this.authService.getUserJwtPayload(id!);
const accessToken = this.authService.generateAccessToken(payload);
const refreshToken = this.authService.generateRefreshToken(payload);

View File

@ -0,0 +1,147 @@
import { Response, Request } from "express";
import { Controller, Get, Post, Put } from "@ControllerPattern/index";
import ApiController from "@Common/system/controller-pattern/ApiController";
import OfficeRolesService from "@Services/super-admin/OfficeRolesService/OfficeRolesService";
import { Service } from "typedi";
import { validateOrReject } from "class-validator";
import { OfficeRole } from "le-coffre-resources/dist/Notary";
import { OfficeRoles } from "@prisma/client";
import authHandler from "@App/middlewares/AuthHandler";
import ruleHandler from "@App/middlewares/RulesHandler";
@Controller()
@Service()
export default class OfficeRolesController extends ApiController {
constructor(private officeRolesService: OfficeRolesService) {
super();
}
/**
* @description Get all officeRoles
*/
@Get("/api/v1/super-admin/officeRoles", [authHandler,ruleHandler])
protected async get(req: Request, response: Response) {
try {
//get query
const query = JSON.parse(req.query["q"] as string);
//call service to get prisma entity
const officeRolesEntities = await this.officeRolesService.get(query);
//Hydrate ressource with prisma entity
const officeRoles = OfficeRole.hydrateArray<OfficeRole>(officeRolesEntities, { strategy: "excludeAll" });
//success
this.httpSuccess(response, officeRoles);
} catch (error) {
this.httpInternalError(response, error);
return;
}
}
/**
* @description Create a new officeRole
*/
@Post("/api/v1/super-admin/office-roles", [authHandler,ruleHandler])
protected async getAddresses(req: Request, response: Response) {
try {
//init IOfficeRole resource with request body values
const officeRoleEntity = OfficeRole.hydrate<OfficeRole>(req.body);
//validate officeRole
await validateOrReject(officeRoleEntity, { groups: ["createOfficeRole"] });
//call service to get prisma entity
const officeRoleEntityCreated = await this.officeRolesService.create(officeRoleEntity);
//Hydrate ressource with prisma entity
const officeRole = OfficeRole.hydrate<OfficeRole>(officeRoleEntityCreated, {
strategy: "excludeAll",
});
//success
this.httpCreated(response, officeRole);
} catch (error) {
this.httpInternalError(response, error);
return;
}
}
/**
* @description Modify a specific officeRole by uid
*/
@Put("/api/v1/super-admin/office-roles/:uid", [authHandler,ruleHandler])
protected async put(req: Request, response: Response) {
try {
const uid = req.params["uid"];
if (!uid) {
this.httpBadRequest(response, "No uid provided");
return;
}
const officeRoleFound = await this.officeRolesService.getByUid(uid);
if (!officeRoleFound) {
this.httpNotFoundRequest(response, "officeRole not found");
return;
}
//init IOfficeRole resource with request body values
const officeRoleEntity = OfficeRole.hydrate<OfficeRole>(req.body);
//validate officeRole
await validateOrReject(officeRoleEntity, { groups: ["updateOfficeRole"] });
//call service to get prisma entity
const officeRoleEntityUpdated = await this.officeRolesService.update(officeRoleEntity);
//Hydrate ressource with prisma entity
const officeRole = OfficeRole.hydrate<OfficeRole>(officeRoleEntityUpdated, {
strategy: "excludeAll",
});
//success
this.httpSuccess(response, officeRole);
} catch (error) {
this.httpInternalError(response, error);
return;
}
}
/**
* @description Get a specific officeRole by uid
*/
@Get("/api/v1/super-admin/office-roles/:uid", [authHandler,ruleHandler])
protected async getOneByUid(req: Request, response: Response) {
try {
const uid = req.params["uid"];
if (!uid) {
this.httpBadRequest(response, "No uid provided");
return;
}
let officeRoleEntity: OfficeRoles | null;
//get query
if (req.query["q"]) {
const query = JSON.parse(req.query["q"] as string);
officeRoleEntity = await this.officeRolesService.getByUid(uid, query);
} else {
//call service to get prisma entity
officeRoleEntity = await this.officeRolesService.getByUid(uid);
}
if (!officeRoleEntity) {
this.httpNotFoundRequest(response, "officeRole not found");
return;
}
//Hydrate ressource with prisma entity
const officeRole = OfficeRole.hydrate<OfficeRole>(officeRoleEntity, { strategy: "excludeAll" });
//success
this.httpSuccess(response, officeRole);
} catch (error) {
this.httpInternalError(response, error);
return;
}
}
}

View File

@ -0,0 +1,86 @@
/*
Warnings:
- You are about to drop the `office_role_has_rules` table. If the table is not empty, all the data it contains will be lost.
- You are about to drop the `role_has_rules` table. If the table is not empty, all the data it contains will be lost.
*/
-- DropForeignKey
ALTER TABLE "office_role_has_rules" DROP CONSTRAINT "office_role_has_rules_office_uid_fkey";
-- DropForeignKey
ALTER TABLE "office_role_has_rules" DROP CONSTRAINT "office_role_has_rules_role_uid_fkey";
-- DropForeignKey
ALTER TABLE "office_role_has_rules" DROP CONSTRAINT "office_role_has_rules_rule_uid_fkey";
-- DropForeignKey
ALTER TABLE "role_has_rules" DROP CONSTRAINT "role_has_rules_role_uid_fkey";
-- DropForeignKey
ALTER TABLE "role_has_rules" DROP CONSTRAINT "role_has_rules_rule_uid_fkey";
-- AlterTable
ALTER TABLE "users" ADD COLUMN "office_role_uid" VARCHAR(255);
-- DropTable
DROP TABLE "office_role_has_rules";
-- DropTable
DROP TABLE "role_has_rules";
-- CreateTable
CREATE TABLE "office_roles" (
"uid" TEXT NOT NULL,
"name" VARCHAR(255) NOT NULL,
"office_uid" VARCHAR(255) NOT NULL,
"created_at" TIMESTAMP(3) DEFAULT CURRENT_TIMESTAMP,
"updated_at" TIMESTAMP(3),
CONSTRAINT "office_roles_pkey" PRIMARY KEY ("uid")
);
-- CreateTable
CREATE TABLE "_RolesHasRules" (
"A" TEXT NOT NULL,
"B" TEXT NOT NULL
);
-- CreateTable
CREATE TABLE "_OfficeRolesHasRules" (
"A" TEXT NOT NULL,
"B" TEXT NOT NULL
);
-- CreateIndex
CREATE UNIQUE INDEX "office_roles_uid_key" ON "office_roles"("uid");
-- CreateIndex
CREATE UNIQUE INDEX "_RolesHasRules_AB_unique" ON "_RolesHasRules"("A", "B");
-- CreateIndex
CREATE INDEX "_RolesHasRules_B_index" ON "_RolesHasRules"("B");
-- CreateIndex
CREATE UNIQUE INDEX "_OfficeRolesHasRules_AB_unique" ON "_OfficeRolesHasRules"("A", "B");
-- CreateIndex
CREATE INDEX "_OfficeRolesHasRules_B_index" ON "_OfficeRolesHasRules"("B");
-- AddForeignKey
ALTER TABLE "users" ADD CONSTRAINT "users_office_role_uid_fkey" FOREIGN KEY ("office_role_uid") REFERENCES "office_roles"("uid") ON DELETE CASCADE ON UPDATE CASCADE;
-- AddForeignKey
ALTER TABLE "office_roles" ADD CONSTRAINT "office_roles_office_uid_fkey" FOREIGN KEY ("office_uid") REFERENCES "offices"("uid") ON DELETE CASCADE ON UPDATE CASCADE;
-- AddForeignKey
ALTER TABLE "_RolesHasRules" ADD CONSTRAINT "_RolesHasRules_A_fkey" FOREIGN KEY ("A") REFERENCES "roles"("uid") ON DELETE CASCADE ON UPDATE CASCADE;
-- AddForeignKey
ALTER TABLE "_RolesHasRules" ADD CONSTRAINT "_RolesHasRules_B_fkey" FOREIGN KEY ("B") REFERENCES "rules"("uid") ON DELETE CASCADE ON UPDATE CASCADE;
-- AddForeignKey
ALTER TABLE "_OfficeRolesHasRules" ADD CONSTRAINT "_OfficeRolesHasRules_A_fkey" FOREIGN KEY ("A") REFERENCES "office_roles"("uid") ON DELETE CASCADE ON UPDATE CASCADE;
-- AddForeignKey
ALTER TABLE "_OfficeRolesHasRules" ADD CONSTRAINT "_OfficeRolesHasRules_B_fkey" FOREIGN KEY ("B") REFERENCES "rules"("uid") ON DELETE CASCADE ON UPDATE CASCADE;

View File

@ -56,6 +56,8 @@ model Users {
contact_uid String @unique @db.VarChar(255)
role Roles @relation(fields: [roles_uid], references: [uid], onDelete: Cascade)
roles_uid String @db.VarChar(255)
office_role OfficeRoles? @relation(fields: [office_role_uid], references: [uid], onDelete: Cascade)
office_role_uid String? @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
office_membership Offices @relation(fields: [office_uid], references: [uid], onDelete: Cascade)
@ -67,20 +69,20 @@ model Users {
}
model Offices {
uid String @id @unique @default(uuid())
idNot String @unique @db.VarChar(255)
name String @db.VarChar(255)
crpcen String @unique @db.VarChar(255)
address Addresses @relation(fields: [address_uid], references: [uid], onDelete: Cascade)
address_uid String @unique @db.VarChar(255)
office_status EOfficeStatus @default(DESACTIVATED)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
deed_types DeedTypes[]
users Users[]
office_folders OfficeFolders[]
document_types DocumentTypes[]
office_role_has_rules OfficesRolesHasRules[]
uid String @id @unique @default(uuid())
idNot String @unique @db.VarChar(255)
name String @db.VarChar(255)
crpcen String @unique @db.VarChar(255)
address Addresses @relation(fields: [address_uid], references: [uid], onDelete: Cascade)
address_uid String @unique @db.VarChar(255)
office_status EOfficeStatus @default(DESACTIVATED)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
deed_types DeedTypes[]
users Users[]
office_folders OfficeFolders[]
document_types DocumentTypes[]
OfficeRoles OfficeRoles[]
@@map("offices")
}
@ -300,53 +302,63 @@ model DeedTypeHasDocumentTypes {
}
model Roles {
uid String @id @unique @default(uuid())
name String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
role_has_rules RolesHasRules[]
office_role_has_rules OfficesRolesHasRules[]
users Users[]
uid String @id @unique @default(uuid())
name String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
rules Rules[] @relation("RolesHasRules")
users Users[]
@@map("roles")
}
model OfficeRoles {
uid String @id @unique @default(uuid())
name String @db.VarChar(255)
office Offices @relation(fields: [office_uid], references: [uid], onDelete: Cascade)
office_uid String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
rules Rules[] @relation("OfficeRolesHasRules")
users Users[]
@@map("office_roles")
}
model Rules {
uid String @id @unique @default(uuid())
name String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
role_has_rules RolesHasRules[]
office_roles_has_rules OfficesRolesHasRules[]
uid String @id @unique @default(uuid())
name String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
role Roles[] @relation("RolesHasRules")
office_roles OfficeRoles[] @relation("OfficeRolesHasRules")
@@map("rules")
}
model RolesHasRules {
uid String @id @unique @default(uuid())
role Roles @relation(fields: [role_uid], references: [uid], onDelete: Cascade)
role_uid String @db.VarChar(255)
rule Rules @relation(fields: [rule_uid], references: [uid], onDelete: Cascade)
rule_uid String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
// model RolesHasRules {
// uid String @id @unique @default(uuid())
// role Roles @relation(fields: [role_uid], references: [uid], onDelete: Cascade)
// role_uid String @db.VarChar(255)
// rule Rules @relation(fields: [rule_uid], references: [uid], onDelete: Cascade)
// rule_uid String @db.VarChar(255)
// created_at DateTime? @default(now())
// updated_at DateTime? @updatedAt
@@map("role_has_rules")
}
// @@map("role_has_rules")
// }
model OfficesRolesHasRules {
uid String @id @unique @default(uuid())
office Offices @relation(fields: [office_uid], references: [uid], onDelete: Cascade)
role Roles @relation(fields: [role_uid], references: [uid], onDelete: Cascade)
rule Rules @relation(fields: [rule_uid], references: [uid], onDelete: Cascade)
office_uid String @db.VarChar(255)
role_uid String @db.VarChar(255)
rule_uid String @db.VarChar(255)
created_at DateTime? @default(now())
updated_at DateTime? @updatedAt
// model OfficesRolesHasRules {
// uid String @id @unique @default(uuid())
// office_role OfficeRoles @relation(fields: [office_role_uid], references: [uid], onDelete: Cascade)
// rule Rules @relation(fields: [rule_uid], references: [uid], onDelete: Cascade)
// office_role_uid String @db.VarChar(255)
// rule_uid String @db.VarChar(255)
// created_at DateTime? @default(now())
// updated_at DateTime? @updatedAt
@@map("office_role_has_rules")
}
// @@map("office_role_has_rules")
// }
enum ECivility {
MALE

File diff suppressed because it is too large Load Diff

View File

@ -18,9 +18,8 @@ import {
ECustomerStatus,
PrismaClient,
Roles,
OfficesRolesHasRules,
RolesHasRules,
Rules,
OfficeRoles,
} from "@prisma/client";
(async () => {
@ -106,6 +105,8 @@ import {
const uidRole1: string = randomString();
const uidRole2: string = randomString();
const uidOfficeRole1: string = randomString();
const uidOfficeRole2: string = randomString();
const uidRule1: string = randomString();
const uidRule2: string = randomString();
@ -173,12 +174,6 @@ import {
const uidOfficeFolderHasCustomer3: string = randomString();
const uidOfficeFolderHasCustomer4: string = randomString();
const uidOfficeRoleHasRule1: string = randomString();
const uidOfficeRoleHasRule2: string = randomString();
const uidRoleHasRule1: string = randomString();
const uidRoleHasRule2: string = randomString();
const uidDeedHasDocumentType1: string = randomString();
const uidDeedHasDocumentType2: string = randomString();
const uidDeedHasDocumentType3: string = randomString();
@ -801,6 +796,21 @@ import {
}
];
const rules: Rules[] = [
{
uid: uidRule1,
name: 'GET users',
created_at: new Date(),
updated_at: new Date(),
},
{
uid: uidRule2,
name: 'GET offices',
created_at: new Date(),
updated_at: new Date(),
}
];
const roles: Roles[] = [
{
uid: uidRole1,
@ -816,6 +826,23 @@ import {
}
];
const officeRoles: OfficeRoles[] = [
{
uid: uidOfficeRole1,
name: 'super-admin',
created_at: new Date(),
updated_at: new Date(),
office_uid: uidOffice1,
},
{
uid: uidOfficeRole2,
name: 'admin',
created_at: new Date(),
updated_at: new Date(),
office_uid: uidOffice1,
}
];
const users: Users[] = [
{
uid: uidUser1,
@ -825,6 +852,7 @@ import {
contact_uid: uidContact16,
office_uid: uidOffice1,
roles_uid: uidRole1,
office_role_uid: uidOfficeRole1,
},
{
uid: uidUser2,
@ -834,6 +862,7 @@ import {
contact_uid: uidContact17,
office_uid: uidOffice1,
roles_uid: uidRole2,
office_role_uid: uidOfficeRole2,
},
{
uid: uidUser3,
@ -843,6 +872,7 @@ import {
contact_uid: uidContact18,
office_uid: uidOffice1,
roles_uid: uidRole1,
office_role_uid: null,
},
{
uid: uidUser4,
@ -852,6 +882,7 @@ import {
contact_uid: uidContact19,
office_uid: uidOffice1,
roles_uid: uidRole2,
office_role_uid: null,
},
{
uid: uidUser5,
@ -861,6 +892,7 @@ import {
contact_uid: uidContact20,
office_uid: uidOffice1,
roles_uid: uidRole1,
office_role_uid: null,
},
];
@ -1700,57 +1732,6 @@ import {
},
];
const officeRoleHasRules: OfficesRolesHasRules[] = [
{
uid: uidOfficeRoleHasRule1,
office_uid: uidOffice1,
role_uid: uidRole1,
rule_uid: uidRule1,
created_at: new Date(),
updated_at: new Date(),
},
{
uid: uidOfficeRoleHasRule2,
office_uid: uidOffice1,
role_uid: uidRole2,
rule_uid: uidRule2,
created_at: new Date(),
updated_at: new Date(),
},
];
const roleHasRules: RolesHasRules[] = [
{
uid: uidRoleHasRule1,
role_uid: uidRole1,
rule_uid: uidRule2,
created_at: new Date(),
updated_at: new Date(),
},
{
uid: uidRoleHasRule2,
role_uid: uidRole2,
rule_uid: uidRule1,
created_at: new Date(),
updated_at: new Date(),
},
];
const rules: Rules[] = [
{
uid: uidRule1,
name: 'GET users',
created_at: new Date(),
updated_at: new Date(),
},
{
uid: uidRule2,
name: 'GET offices',
created_at: new Date(),
updated_at: new Date(),
}
];
const deedTypeHasDocumentTypes: DeedTypeHasDocumentTypes[] = [
{
uid: uidDeedTypeHasDocumentType1,
@ -1927,12 +1908,16 @@ import {
await prisma.offices.create({ data: office });
}
for (const rule of rules) {
await prisma.rules.create({ data: rule });
}
for (const role of roles) {
await prisma.roles.create({ data: role });
}
for (const rule of rules) {
await prisma.rules.create({ data: rule });
for (const officeRole of officeRoles) {
await prisma.officeRoles.create({ data: officeRole });
}
for (const user of users) {
@ -1966,14 +1951,6 @@ import {
await prisma.officeFolderHasCustomers.create({ data: officeFolderHasCustomer });
}
for (const officeRoleHasRule of officeRoleHasRules) {
await prisma.officesRolesHasRules.create({ data: officeRoleHasRule });
}
for (const roleHasRule of roleHasRules) {
await prisma.rolesHasRules.create({ data: roleHasRule });
}
for (const deedHasDocumentType of deedHasDocumentTypes) {
await prisma.deedHasDocumentTypes.create({ data: deedHasDocumentType });
}

View File

@ -1,38 +0,0 @@
import Database from "@Common/databases/database";
import { DeedTypeHasDocumentTypes } from "@prisma/client";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
@Service()
export default class DeedTypeHasDocumentTypesRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().deedTypeHasDocumentTypes;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many relations between deed type and a document type
*/
public async findMany(query: any): Promise<DeedTypeHasDocumentTypes[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Find unique relation between deed type and a document type
*/
public async findOneByUid(uid: string): Promise<DeedTypeHasDocumentTypes | null> {
const deedTypeHasDoculmentTypesEntity = await this.model.findUnique({
where: {
uid: uid,
},
});
return deedTypeHasDoculmentTypesEntity;
}
}

View File

@ -1,38 +0,0 @@
import Database from "@Common/databases/database";
import { DeedHasDocumentTypes } from "@prisma/client";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
@Service()
export default class DeedHasDocumentTypesRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().deedHasDocumentTypes;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many deeds
*/
public async findMany(query: any): Promise<DeedHasDocumentTypes[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Find unique relation between deed and a document type
*/
public async findOneByUid(uid: string): Promise<DeedHasDocumentTypes | null> {
const deedHasDocumentTypesEntity = await this.model.findUnique({
where: {
uid: uid,
},
});
return deedHasDocumentTypesEntity;
}
}

View File

@ -1,38 +0,0 @@
import Database from "@Common/databases/database";
import { OfficeFolderHasCustomers } from "@prisma/client";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
@Service()
export default class OfficeFoldersHasCustomerRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().officeFolderHasCustomers;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many relations
*/
public async findMany(query: any): Promise<OfficeFolderHasCustomers[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Find a unique relation between an office folder and customers
*/
public async findOneByUid(uid: string): Promise<OfficeFolderHasCustomers | null> {
const officeFolderHasCustomersEntity = await this.model.findUnique({
where: {
uid: uid,
},
});
return officeFolderHasCustomersEntity;
}
}

View File

@ -1,38 +0,0 @@
import Database from "@Common/databases/database";
import { OfficeFolderHasStakeholders } from "@prisma/client";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
@Service()
export default class OfficeFoldersHasStakeholderRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().officeFolderHasStakeholders;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many relations
*/
public async findMany(query: any): Promise<OfficeFolderHasStakeholders[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Find a unique relation between an office folder and stakeholders
*/
public async findOneByUid(uid: string): Promise<OfficeFolderHasStakeholders | null> {
const officeFolderHasStakeholdersEntity = await this.model.findUnique({
where: {
uid: uid,
},
});
return officeFolderHasStakeholdersEntity;
}
}

View File

@ -1,42 +0,0 @@
import Database from "@Common/databases/database";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
import { OfficesRolesHasRules, Prisma } from "@prisma/client";
@Service()
export default class OfficeRoleHasRulesRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().officesRolesHasRules;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many relations between office roles and rules
*/
public async findMany(query: any): Promise<OfficesRolesHasRules[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Find one relation between an office role and rules
*/
public async findOneByUid(uid: string, query?: any): Promise<OfficesRolesHasRules | null> {
const findOneArgs: Prisma.OfficesRolesHasRulesFindUniqueArgs = {
where: {
uid: uid,
},
};
if (query) {
findOneArgs.include = query;
}
const roleEntity = await this.model.findUnique(findOneArgs);
return roleEntity;
}
}

View File

@ -0,0 +1,98 @@
import Database from "@Common/databases/database";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
import { OfficeRoles, Prisma } from "@prisma/client";
import { OfficeRole } from "le-coffre-resources/dist/SuperAdmin";
@Service()
export default class OfficeRolesRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().officeRoles;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many officeRoles
*/
public async findMany(query: any): Promise<OfficeRoles[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Create new officeRole with rules
*/
public async create(officeRole: OfficeRole): Promise<OfficeRoles> {
const createArgs: Prisma.OfficeRolesCreateArgs = {
data: {
name: officeRole.name,
office: {
connect: {
uid: officeRole.office.uid,
},
},
rules: {
connect: officeRole.rules?.map((rule) => ({
uid: rule.uid!,
})),
},
},
};
return this.model.create(createArgs);
}
/**
* @description : Update data of a officeRole with rules
*/
public async update(officeRole: OfficeRole): Promise<OfficeRoles> {
const updateArgs: Prisma.OfficeRolesUpdateArgs = {
where: {
uid: officeRole.uid,
},
data: {
name: officeRole.name,
rules: {
set: officeRole.rules?.map((rule) => ({
uid: rule.uid!,
})),
},
},
};
return this.model.update(updateArgs);
}
/**
* @description : Find one officeRole
*/
public async findOneByUid(uid: string, query?: any): Promise<OfficeRoles | null> {
const findOneArgs: Prisma.OfficeRolesFindUniqueArgs = {
where: {
uid: uid,
},
};
if (query) {
findOneArgs.include = query;
}
const officeRoleEntity = await this.model.findUnique(findOneArgs);
return officeRoleEntity;
}
/**
* @description : Delete a officeRole
*/
public async delete(uid: string): Promise<OfficeRoles> {
return this.model.delete({
where: {
uid: uid,
},
});
}
}

View File

@ -1,42 +0,0 @@
import Database from "@Common/databases/database";
import BaseRepository from "@Repositories/BaseRepository";
import { Service } from "typedi";
import { RolesHasRules, Prisma } from "@prisma/client";
@Service()
export default class RolesHasRulesRepository extends BaseRepository {
constructor(private database: Database) {
super();
}
protected get model() {
return this.database.getClient().rolesHasRules;
}
protected get instanceDb() {
return this.database.getClient();
}
/**
* @description : Find many relations between basic roles and rules
*/
public async findMany(query: any): Promise<RolesHasRules[]> {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
/**
* @description : Find one relation between an basic role and rules
*/
public async findOneByUid(uid: string, query?: any): Promise<RolesHasRules | null> {
const findOneArgs: Prisma.RolesHasRulesFindUniqueArgs = {
where: {
uid: uid,
},
};
if (query) {
findOneArgs.include = query;
}
const roleEntity = await this.model.findUnique(findOneArgs);
return roleEntity;
}
}

View File

@ -31,27 +31,13 @@ export default class RolesRepository extends BaseRepository {
const createArgs: Prisma.RolesCreateArgs = {
data: {
name: role.name,
role_has_rules: {
createMany: {
data: role.role_has_rules!.rules.map((relation) => ({
rule_uid: relation.uid!,
})),
skipDuplicates: true,
},
rules: {
connect: role.rules?.map((rule) => ({
uid: rule.uid!,
})),
},
},
};
if (role.office_role_has_rules) {
createArgs.data.office_role_has_rules = {
createMany: {
data: role.office_role_has_rules.rules.map((relation) => ({
office_uid: role.office_role_has_rules!.office.uid!,
rule_uid: relation.uid!,
})),
skipDuplicates: true,
},
};
}
return this.model.create(createArgs);
}
@ -66,29 +52,13 @@ export default class RolesRepository extends BaseRepository {
},
data: {
name: role.name,
role_has_rules: {
deleteMany: { role_uid: role.uid },
createMany: {
data: role.role_has_rules!.rules.map((relation) => ({
rule_uid: relation.uid!,
})),
skipDuplicates: true,
},
rules: {
set: role.rules?.map((rule) => ({
uid: rule.uid!,
})),
},
},
};
if (role.office_role_has_rules) {
updateArgs.data.office_role_has_rules = {
deleteMany: { role_uid: role.uid },
createMany: {
data: role.office_role_has_rules.rules.map((relation) => ({
office_uid: role.office_role_has_rules!.office.uid!,
rule_uid: relation.uid!,
})),
skipDuplicates: true,
},
};
}
return this.model.update(updateArgs);
}

View File

@ -19,7 +19,7 @@ export default class UsersRepository extends BaseRepository {
/**
* @description : Find many users
*/
public async findMany(query: Prisma.UsersFindManyArgs): Promise<Users[]> {
public async findMany(query: Prisma.UsersFindManyArgs) {
query.take = Math.min(query.take || this.defaultFetchRows, this.maxFetchRows);
return this.model.findMany(query);
}
@ -65,7 +65,7 @@ export default class UsersRepository extends BaseRepository {
connect: {
uid: user.role!.uid,
},
}
},
},
};
if (user.contact!.address) {
@ -75,6 +75,13 @@ export default class UsersRepository extends BaseRepository {
city: user.contact!.address.city,
};
}
if (user.office_role) {
createArgs.data.office_role = {
connect: {
uid: user.office_role.uid,
},
};
}
return this.model.create({ ...createArgs, include: { contact: true, office_membership: { include: { address: true } } } });
}
@ -137,6 +144,13 @@ export default class UsersRepository extends BaseRepository {
city: user.contact!.address!.city,
};
}
if (user.office_role) {
updateArgs.data.office_role = {
connect: {
uid: user.office_role.uid,
},
};
}
return this.model.update({ ...updateArgs, include: { contact: true, office_membership: { include: { address: true } } } });
}
@ -156,4 +170,18 @@ export default class UsersRepository extends BaseRepository {
return userEntity;
}
/**
* @description : Find one user
*/
public async findOneByProvider(providerName: string, id: string) {
return this.model.findUnique({
where: { [providerName]: id },
include: {
role: { include: { rules: true } } ,
office_role: { include: { rules: true } } ,
office_membership: true,
},
});
}
}

View File

@ -10,7 +10,21 @@ export type Tokens = {
token_type: string;
};
export type OpenIdConfig = {
authorization_endpoint: string;
token_endpoint: string;
userinfo_endpoint: string;
claims_supported: string[];
end_session_endpoint: string;
grant_types_supported: string[];
response_types_supported: string[];
scopes_supported: string[];
issuer: string;
jwks_uri: string;
}
export default interface OpenIdInterface {
getOpenIdConfig(): Promise<OpenIdConfig>
verifyIdToken(signingKey: string): Promise<Payload>;
getSigningKeys(jwksUri: string): Promise<string[]>;
}

View File

@ -1,17 +1,24 @@
import "reflect-metadata";
import jwt, { VerifyCallback } from "jsonwebtoken";
import BaseService from "@Services/BaseService";
import "reflect-metadata";
import { BackendVariables } from "@Common/config/variables/Variables";
import { Service } from "typedi";
import UsersService from "@Services/super-admin/UsersService/UsersService";
export type UserPayload = {
uid: string;
idNot: string;
office_idNot: string;
enum PROVIDER_OPENID {
idNot = "idNot",
}
interface IJwtPayload {
userId: string;
openId: {
providerName: PROVIDER_OPENID;
userId: string | number;
};
office_IdNot_Id: string;
role: string;
rules: string[];
};
}
@Service()
export default class AuthService extends BaseService {
@ -19,32 +26,25 @@ export default class AuthService extends BaseService {
super();
}
public async getUserPayload(id: string): Promise<UserPayload> {
const user: any = (
await this.userService.get({
where: { idNot: id },
include: {
role: { include: { role_has_rules: { include: { rule: true } }, office_role_has_rules: { include: { rule: true } } } },
office_membership: true,
},
})
)[0];
public async getUserJwtPayload(id: string, providerName: PROVIDER_OPENID = PROVIDER_OPENID.idNot): Promise<IJwtPayload | null> {
const user = await this.userService.getByProvider(providerName, id);
if (!user) throw new Error("User not found");
if (!user) return null;
let rules: string[] = [];
if (user.role.office_role_has_rules.length) {
user.role.office_role_has_rules.forEach((relation: any) => {
if (relation.office_uid === user.office_membership.uid) rules.push(relation.rule.name);
const rules: string[] = [];
if (user.office_role?.rules.length) {
user.office_role.rules.forEach((relation: any) => {
rules.push(relation.rule.name);
});
return { uid: user.uid, idNot: user.idNot, office_idNot: user.office_membership.idNot, role: user.role.name, rules: rules };
return { userId: user.uid, openId: {providerName: providerName, userId: user.idNot}, office_IdNot_Id: user.office_membership.idNot, role: user.role.name, rules: rules };
}
if (!rules.length) {
user.role.role_has_rules.forEach((relation: any) => {
user.role.rules.forEach((relation: any) => {
rules.push(relation.rule.name);
});
}
return { uid: user.uid, idNot: user.idNot, office_idNot: user.office_membership.idNot, role: user.role.name, rules: rules };
return { userId: user.uid, openId: {providerName: providerName, userId: user.idNot}, office_IdNot_Id: user.office_membership.idNot, role: user.role.name, rules: rules };
}
public generateAccessToken(user: any): string {

View File

@ -0,0 +1,55 @@
import jwt from "jsonwebtoken";
import BaseService from "@Services/BaseService";
import { Service } from "typedi";
export type Tokens = {
access_token: string;
expires_in: number;
id_token: string;
token_type: string;
};
export type OpenIdConfig = {
authorization_endpoint: string;
token_endpoint: string;
userinfo_endpoint: string;
claims_supported: string[];
end_session_endpoint: string;
grant_types_supported: string[];
response_types_supported: string[];
scopes_supported: string[];
issuer: string;
jwks_uri: string;
}
@Service()
export default class OpenIdService extends BaseService {
protected authorizationServerUrl: string;
constructor(authorizationServerUrl: string) {
super();
this.authorizationServerUrl = authorizationServerUrl;
}
public async getOpenIdConfig(): Promise<OpenIdConfig> {
const response = await fetch(this.authorizationServerUrl + "/.well-known/openid-configuration");
return await response.json();
}
public async getSigningKey(kid: string): Promise<string | null> {
const jwksUri = (await this.getOpenIdConfig()).jwks_uri;
const response = await fetch(jwksUri);
const jwks = await response.json();
const signingKey = jwks.keys.find((key: any) => key.kid === kid);
if (!signingKey) return null;
return signingKey;
}
/**
* @throws Error
*/
public async verifyIdToken(idToken: string, kid: string) {
const signingKey = await this.getSigningKey(kid);
if (!signingKey) throw new Error("Signing key not found");
return jwt.verify(idToken, signingKey);
}
}

View File

@ -0,0 +1,44 @@
import BaseService from "@Services/BaseService";
import { Service } from "typedi";
import OfficeRolesRepository from "@Repositories/OfficeRolesRepository";
import { OfficeRole } from "le-coffre-resources/dist/SuperAdmin";
import {Prisma, OfficeRoles } from "@prisma/client";
@Service()
export default class OfficeRolesService extends BaseService {
constructor(private officeRoleRepository: OfficeRolesRepository) {
super();
}
/**
* @description : Get all officeRoles
* @throws {Error} If officeRoles cannot be get
*/
public get(query: Prisma.OfficeRolesFindManyArgs): Promise<OfficeRoles[]> {
return this.officeRoleRepository.findMany(query);
}
/**
* @description : Create a officeRole
* @throws {Error} If officeRole couldn't be created
*/
public create(officeRoleEntity: OfficeRole): Promise<OfficeRoles> {
return this.officeRoleRepository.create(officeRoleEntity);
}
/**
* @description : Modify a officeRole
* @throws {Error} If officeRole modification failed
*/
public update(officeRoleEntity: OfficeRole): Promise<OfficeRoles> {
return this.officeRoleRepository.update(officeRoleEntity);
}
/**
* @description : Get a officeRole by uid
* @throws {Error} If officeRole cannot be get by uid
*/
public getByUid(uid: string, query?: any): Promise<OfficeRoles | null> {
return this.officeRoleRepository.findOneByUid(uid, query);
}
}

View File

@ -15,7 +15,7 @@ export default class UsersService extends BaseService {
* @description : Get all users
* @throws {Error} If users cannot be get
*/
public get(query: Prisma.UsersFindManyArgs): Promise<Users[]> {
public get(query: Prisma.UsersFindManyArgs) {
return this.userRepository.findMany(query);
}
@ -42,4 +42,12 @@ export default class UsersService extends BaseService {
public getByUid(uid: string, query?: any): Promise<Users | null> {
return this.userRepository.findOneByUid(uid, query);
}
/**
* @description : Get a user by uid
* @throws {Error} If user cannot be get by uid
*/
public getByProvider(providerName: string, id: string) {
return this.userRepository.findOneByProvider(providerName, id);
}
}