mirror of
https://github.com/awatertrevi/infisical.git
synced 2026-10-08 17:28:18 +00:00
feat: completed all role routers
This commit is contained in:
Vendored
+13
@@ -53,6 +53,7 @@ import { TSshHostServiceFactory } from "@app/ee/services/ssh-host/ssh-host-servi
|
|||||||
import { TSshHostGroupServiceFactory } from "@app/ee/services/ssh-host-group/ssh-host-group-service";
|
import { TSshHostGroupServiceFactory } from "@app/ee/services/ssh-host-group/ssh-host-group-service";
|
||||||
import { TTrustedIpServiceFactory } from "@app/ee/services/trusted-ip/trusted-ip-types";
|
import { TTrustedIpServiceFactory } from "@app/ee/services/trusted-ip/trusted-ip-types";
|
||||||
import { TAuthMode } from "@app/server/plugins/auth/inject-identity";
|
import { TAuthMode } from "@app/server/plugins/auth/inject-identity";
|
||||||
|
import { TAdditionalPrivilegeServiceFactory } from "@app/services/additional-privilege/additional-privilege-service";
|
||||||
import { TApiKeyServiceFactory } from "@app/services/api-key/api-key-service";
|
import { TApiKeyServiceFactory } from "@app/services/api-key/api-key-service";
|
||||||
import { TAppConnectionServiceFactory } from "@app/services/app-connection/app-connection-service";
|
import { TAppConnectionServiceFactory } from "@app/services/app-connection/app-connection-service";
|
||||||
import { TAuthLoginFactory } from "@app/services/auth/auth-login-service";
|
import { TAuthLoginFactory } from "@app/services/auth/auth-login-service";
|
||||||
@@ -88,6 +89,9 @@ import { TIdentityTokenAuthServiceFactory } from "@app/services/identity-token-a
|
|||||||
import { TIdentityUaServiceFactory } from "@app/services/identity-ua/identity-ua-service";
|
import { TIdentityUaServiceFactory } from "@app/services/identity-ua/identity-ua-service";
|
||||||
import { TIntegrationServiceFactory } from "@app/services/integration/integration-service";
|
import { TIntegrationServiceFactory } from "@app/services/integration/integration-service";
|
||||||
import { TIntegrationAuthServiceFactory } from "@app/services/integration-auth/integration-auth-service";
|
import { TIntegrationAuthServiceFactory } from "@app/services/integration-auth/integration-auth-service";
|
||||||
|
import { TMembershipGroupServiceFactory } from "@app/services/membership-group/membership-group-service";
|
||||||
|
import { TMembershipIdentityServiceFactory } from "@app/services/membership-identity/membership-identity-service";
|
||||||
|
import { TMembershipUserServiceFactory } from "@app/services/membership-user/membership-user-service";
|
||||||
import { TMicrosoftTeamsServiceFactory } from "@app/services/microsoft-teams/microsoft-teams-service";
|
import { TMicrosoftTeamsServiceFactory } from "@app/services/microsoft-teams/microsoft-teams-service";
|
||||||
import { TNotificationServiceFactory } from "@app/services/notification/notification-service";
|
import { TNotificationServiceFactory } from "@app/services/notification/notification-service";
|
||||||
import { TOfflineUsageReportServiceFactory } from "@app/services/offline-usage-report/offline-usage-report-service";
|
import { TOfflineUsageReportServiceFactory } from "@app/services/offline-usage-report/offline-usage-report-service";
|
||||||
@@ -106,6 +110,7 @@ import { TProjectKeyServiceFactory } from "@app/services/project-key/project-key
|
|||||||
import { TProjectMembershipServiceFactory } from "@app/services/project-membership/project-membership-service";
|
import { TProjectMembershipServiceFactory } from "@app/services/project-membership/project-membership-service";
|
||||||
import { TProjectRoleServiceFactory } from "@app/services/project-role/project-role-service";
|
import { TProjectRoleServiceFactory } from "@app/services/project-role/project-role-service";
|
||||||
import { TReminderServiceFactory } from "@app/services/reminder/reminder-types";
|
import { TReminderServiceFactory } from "@app/services/reminder/reminder-types";
|
||||||
|
import { TRoleServiceFactory } from "@app/services/role/role-service";
|
||||||
import { TSecretServiceFactory } from "@app/services/secret/secret-service";
|
import { TSecretServiceFactory } from "@app/services/secret/secret-service";
|
||||||
import { TSecretBlindIndexServiceFactory } from "@app/services/secret-blind-index/secret-blind-index-service";
|
import { TSecretBlindIndexServiceFactory } from "@app/services/secret-blind-index/secret-blind-index-service";
|
||||||
import { TSecretFolderServiceFactory } from "@app/services/secret-folder/secret-folder-service";
|
import { TSecretFolderServiceFactory } from "@app/services/secret-folder/secret-folder-service";
|
||||||
@@ -125,6 +130,7 @@ import { TUserServiceFactory } from "@app/services/user/user-service";
|
|||||||
import { TUserEngagementServiceFactory } from "@app/services/user-engagement/user-engagement-service";
|
import { TUserEngagementServiceFactory } from "@app/services/user-engagement/user-engagement-service";
|
||||||
import { TWebhookServiceFactory } from "@app/services/webhook/webhook-service";
|
import { TWebhookServiceFactory } from "@app/services/webhook/webhook-service";
|
||||||
import { TWorkflowIntegrationServiceFactory } from "@app/services/workflow-integration/workflow-integration-service";
|
import { TWorkflowIntegrationServiceFactory } from "@app/services/workflow-integration/workflow-integration-service";
|
||||||
|
import { TConvertorServiceFactory } from "@app/services/convertor/convertor-service";
|
||||||
|
|
||||||
declare module "@fastify/request-context" {
|
declare module "@fastify/request-context" {
|
||||||
interface RequestContextData {
|
interface RequestContextData {
|
||||||
@@ -324,6 +330,13 @@ declare module "fastify" {
|
|||||||
pamAccount: TPamAccountServiceFactory;
|
pamAccount: TPamAccountServiceFactory;
|
||||||
pamSession: TPamSessionServiceFactory;
|
pamSession: TPamSessionServiceFactory;
|
||||||
upgradePath: TUpgradePathService;
|
upgradePath: TUpgradePathService;
|
||||||
|
|
||||||
|
membershipUser: TMembershipUserServiceFactory;
|
||||||
|
membershipIdentity: TMembershipIdentityServiceFactory;
|
||||||
|
membershipGroup: TMembershipGroupServiceFactory;
|
||||||
|
role: TRoleServiceFactory;
|
||||||
|
additionalPrivilege: TAdditionalPrivilegeServiceFactory;
|
||||||
|
convertor: TConvertorServiceFactory;
|
||||||
};
|
};
|
||||||
// this is exclusive use for middlewares in which we need to inject data
|
// this is exclusive use for middlewares in which we need to inject data
|
||||||
// everywhere else access using service layer
|
// everywhere else access using service layer
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { packRules } from "@casl/ability/extra";
|
import { packRules } from "@casl/ability/extra";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
|
||||||
import { ProjectMembershipRole, ProjectRolesSchema } from "@app/db/schemas";
|
import { AccessScope, ProjectMembershipRole, ProjectRolesSchema } from "@app/db/schemas";
|
||||||
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
||||||
import {
|
import {
|
||||||
backfillPermissionV1SchemaToV2Schema,
|
backfillPermissionV1SchemaToV2Schema,
|
||||||
@@ -13,7 +13,6 @@ import { slugSchema } from "@app/server/lib/schemas";
|
|||||||
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
||||||
import { SanitizedRoleSchemaV1 } from "@app/server/routes/sanitizedSchemas";
|
import { SanitizedRoleSchemaV1 } from "@app/server/routes/sanitizedSchemas";
|
||||||
import { AuthMode } from "@app/services/auth/auth-type";
|
import { AuthMode } from "@app/services/auth/auth-type";
|
||||||
import { ProjectRoleServiceIdentifierType } from "@app/services/project-role/project-role-types";
|
|
||||||
|
|
||||||
export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProvider) => {
|
export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProvider) => {
|
||||||
server.route({
|
server.route({
|
||||||
@@ -55,14 +54,16 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
packRules(backfillPermissionV1SchemaToV2Schema(req.body.permissions, true))
|
packRules(backfillPermissionV1SchemaToV2Schema(req.body.permissions, true))
|
||||||
);
|
);
|
||||||
|
|
||||||
const role = await server.services.projectRole.createRole({
|
const { id: projectId } = await server.services.convertor.projectSlugToId({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
slug: req.params.projectSlug,
|
||||||
actorId: req.permission.id,
|
orgId: req.permission.orgId
|
||||||
actorOrgId: req.permission.orgId,
|
});
|
||||||
actor: req.permission.type,
|
const role = await server.services.role.createRole({
|
||||||
filter: {
|
permission: req.permission,
|
||||||
type: ProjectRoleServiceIdentifierType.SLUG,
|
scopeData: {
|
||||||
projectSlug: req.params.projectSlug
|
scope: AccessScope.Project,
|
||||||
|
orgId: req.permission.orgId,
|
||||||
|
projectId
|
||||||
},
|
},
|
||||||
data: {
|
data: {
|
||||||
...req.body,
|
...req.body,
|
||||||
@@ -73,7 +74,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.CREATE_PROJECT_ROLE,
|
type: EventType.CREATE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -86,7 +87,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -131,12 +132,21 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
? JSON.stringify(packRules(backfillPermissionV1SchemaToV2Schema(req.body.permissions, true)))
|
? JSON.stringify(packRules(backfillPermissionV1SchemaToV2Schema(req.body.permissions, true)))
|
||||||
: undefined;
|
: undefined;
|
||||||
|
|
||||||
const role = await server.services.projectRole.updateRole({
|
const { id: projectId } = await server.services.convertor.projectSlugToId({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
slug: req.params.projectSlug,
|
||||||
actorId: req.permission.id,
|
orgId: req.permission.orgId
|
||||||
actorOrgId: req.permission.orgId,
|
});
|
||||||
actor: req.permission.type,
|
|
||||||
roleId: req.params.roleId,
|
const role = await server.services.role.updateRole({
|
||||||
|
permission: req.permission,
|
||||||
|
scopeData: {
|
||||||
|
scope: AccessScope.Project,
|
||||||
|
orgId: req.permission.orgId,
|
||||||
|
projectId
|
||||||
|
},
|
||||||
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
},
|
||||||
data: {
|
data: {
|
||||||
...req.body,
|
...req.body,
|
||||||
permissions: stringifiedPermissions
|
permissions: stringifiedPermissions
|
||||||
@@ -146,7 +156,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.UPDATE_PROJECT_ROLE,
|
type: EventType.UPDATE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -159,7 +169,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -188,18 +198,27 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.projectRole.deleteRole({
|
const { id: projectId } = await server.services.convertor.projectSlugToId({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
slug: req.params.projectSlug,
|
||||||
actorId: req.permission.id,
|
orgId: req.permission.orgId
|
||||||
actorOrgId: req.permission.orgId,
|
});
|
||||||
actor: req.permission.type,
|
|
||||||
roleId: req.params.roleId
|
const role = await server.services.role.deleteRole({
|
||||||
|
permission: req.permission,
|
||||||
|
scopeData: {
|
||||||
|
scope: AccessScope.Project,
|
||||||
|
orgId: req.permission.orgId,
|
||||||
|
projectId
|
||||||
|
},
|
||||||
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.DELETE_PROJECT_ROLE,
|
type: EventType.DELETE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -210,7 +229,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -238,17 +257,21 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const roles = await server.services.projectRole.listRoles({
|
const { id: projectId } = await server.services.convertor.projectSlugToId({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
slug: req.params.projectSlug,
|
||||||
actorId: req.permission.id,
|
orgId: req.permission.orgId
|
||||||
actorOrgId: req.permission.orgId,
|
|
||||||
actor: req.permission.type,
|
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.SLUG,
|
|
||||||
projectSlug: req.params.projectSlug
|
|
||||||
}
|
|
||||||
});
|
});
|
||||||
return { roles };
|
|
||||||
|
const { roles } = await server.services.role.listRoles({
|
||||||
|
permission: req.permission,
|
||||||
|
scopeData: {
|
||||||
|
scope: AccessScope.Project,
|
||||||
|
orgId: req.permission.orgId,
|
||||||
|
projectId
|
||||||
|
},
|
||||||
|
data: {}
|
||||||
|
});
|
||||||
|
return { roles: roles.map((el) => ({ ...el, projectId: el.projectId as string })) };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -265,78 +288,30 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}),
|
}),
|
||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
role: SanitizedRoleSchemaV1.omit({ version: true })
|
role: SanitizedRoleSchemaV1
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.projectRole.getRoleBySlug({
|
const { id: projectId } = await server.services.convertor.projectSlugToId({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
slug: req.params.projectSlug,
|
||||||
actorId: req.permission.id,
|
orgId: req.permission.orgId
|
||||||
actorOrgId: req.permission.orgId,
|
|
||||||
actor: req.permission.type,
|
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.SLUG,
|
|
||||||
projectSlug: req.params.projectSlug
|
|
||||||
},
|
|
||||||
roleSlug: req.params.slug
|
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
const role = await server.services.role.getRoleBySlug({
|
||||||
}
|
permission: req.permission,
|
||||||
});
|
scopeData: {
|
||||||
|
scope: AccessScope.Project,
|
||||||
server.route({
|
orgId: req.permission.orgId,
|
||||||
method: "GET",
|
projectId
|
||||||
url: "/:projectId/permissions",
|
},
|
||||||
config: {
|
selector: {
|
||||||
rateLimit: readLimit
|
slug: req.params.slug
|
||||||
},
|
|
||||||
schema: {
|
|
||||||
params: z.object({
|
|
||||||
projectId: z.string().trim()
|
|
||||||
}),
|
|
||||||
response: {
|
|
||||||
200: z.object({
|
|
||||||
data: z.object({
|
|
||||||
membership: z.object({
|
|
||||||
id: z.string(),
|
|
||||||
roles: z
|
|
||||||
.object({
|
|
||||||
role: z.string()
|
|
||||||
})
|
|
||||||
.array()
|
|
||||||
}),
|
|
||||||
assumedPrivilegeDetails: z
|
|
||||||
.object({
|
|
||||||
actorId: z.string(),
|
|
||||||
actorType: z.string(),
|
|
||||||
actorName: z.string(),
|
|
||||||
actorEmail: z.string().optional()
|
|
||||||
})
|
|
||||||
.optional(),
|
|
||||||
permissions: z.any().array()
|
|
||||||
})
|
|
||||||
})
|
|
||||||
}
|
|
||||||
},
|
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
|
||||||
handler: async (req) => {
|
|
||||||
const { permissions, membership, assumedPrivilegeDetails } = await server.services.projectRole.getUserPermission(
|
|
||||||
req.permission.id,
|
|
||||||
req.params.projectId,
|
|
||||||
req.permission.authMethod,
|
|
||||||
req.permission.orgId
|
|
||||||
);
|
|
||||||
|
|
||||||
return {
|
|
||||||
data: {
|
|
||||||
permissions,
|
|
||||||
membership,
|
|
||||||
assumedPrivilegeDetails
|
|
||||||
}
|
}
|
||||||
};
|
});
|
||||||
|
|
||||||
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,7 +1,9 @@
|
|||||||
|
import { packRules } from "@casl/ability/extra";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
|
||||||
import { OrgMembershipRole, OrgMembershipsSchema, OrgRolesSchema } from "@app/db/schemas";
|
import { AccessScope, OrgMembershipRole, OrgMembershipsSchema, OrgRolesSchema } from "@app/db/schemas";
|
||||||
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
||||||
|
import { OrgPermissionSchema } from "@app/ee/services/permission/org-permission";
|
||||||
import { readLimit, writeLimit } from "@app/server/config/rateLimiter";
|
import { readLimit, writeLimit } from "@app/server/config/rateLimiter";
|
||||||
import { slugSchema } from "@app/server/lib/schemas";
|
import { slugSchema } from "@app/server/lib/schemas";
|
||||||
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
||||||
@@ -25,8 +27,7 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
),
|
),
|
||||||
name: z.string().trim(),
|
name: z.string().trim(),
|
||||||
description: z.string().trim().nullish(),
|
description: z.string().trim().nullish(),
|
||||||
// TODO(scott): once UI refactored permissions: OrgPermissionSchema.array()
|
permissions: OrgPermissionSchema.array()
|
||||||
permissions: z.any().array()
|
|
||||||
}),
|
}),
|
||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
@@ -36,13 +37,18 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.orgRole.createRole(
|
const stringifiedPermissions = JSON.stringify(packRules(req.body.permissions));
|
||||||
req.permission.id,
|
const role = await server.services.role.createRole({
|
||||||
req.params.organizationId,
|
permission: req.permission,
|
||||||
req.body,
|
scopeData: {
|
||||||
req.permission.authMethod,
|
scope: AccessScope.Organization,
|
||||||
req.permission.orgId
|
orgId: req.params.organizationId
|
||||||
);
|
},
|
||||||
|
data: {
|
||||||
|
...req.body,
|
||||||
|
permissions: stringifiedPermissions
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
@@ -59,7 +65,7 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, orgId: role.orgId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -82,14 +88,17 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.orgRole.getRole(
|
const role = await server.services.role.getRoleById({
|
||||||
req.permission.id,
|
permission: req.permission,
|
||||||
req.params.organizationId,
|
scopeData: {
|
||||||
req.params.roleId,
|
scope: AccessScope.Organization,
|
||||||
req.permission.authMethod,
|
orgId: req.params.organizationId
|
||||||
req.permission.orgId
|
},
|
||||||
);
|
selector: {
|
||||||
return { role };
|
id: req.params.roleId
|
||||||
|
}
|
||||||
|
});
|
||||||
|
return { role: { ...role, orgId: role.orgId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -114,8 +123,7 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
.optional(),
|
.optional(),
|
||||||
name: z.string().trim().optional(),
|
name: z.string().trim().optional(),
|
||||||
description: z.string().trim().nullish(),
|
description: z.string().trim().nullish(),
|
||||||
// TODO(scott): once UI refactored permissions: OrgPermissionSchema.array().optional()
|
permissions: OrgPermissionSchema.array().optional()
|
||||||
permissions: z.any().array().optional()
|
|
||||||
}),
|
}),
|
||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
@@ -125,14 +133,21 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.orgRole.updateRole(
|
const stringifiedPermissions = req.body.permissions ? JSON.stringify(packRules(req.body.permissions)) : undefined;
|
||||||
req.permission.id,
|
const role = await server.services.role.updateRole({
|
||||||
req.params.organizationId,
|
permission: req.permission,
|
||||||
req.params.roleId,
|
scopeData: {
|
||||||
req.body,
|
scope: AccessScope.Organization,
|
||||||
req.permission.authMethod,
|
orgId: req.params.organizationId
|
||||||
req.permission.orgId
|
},
|
||||||
);
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
},
|
||||||
|
data: {
|
||||||
|
...req.body,
|
||||||
|
permissions: stringifiedPermissions
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
@@ -149,7 +164,7 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, orgId: role.orgId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -172,13 +187,16 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.orgRole.deleteRole(
|
const role = await server.services.role.deleteRole({
|
||||||
req.permission.id,
|
permission: req.permission,
|
||||||
req.params.organizationId,
|
scopeData: {
|
||||||
req.params.roleId,
|
scope: AccessScope.Organization,
|
||||||
req.permission.authMethod,
|
orgId: req.params.organizationId
|
||||||
req.permission.orgId
|
},
|
||||||
);
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
}
|
||||||
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
@@ -189,10 +207,11 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, orgId: role.orgId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// TODO(simp): switch to top level roles
|
||||||
server.route({
|
server.route({
|
||||||
method: "GET",
|
method: "GET",
|
||||||
url: "/:organizationId/roles",
|
url: "/:organizationId/roles",
|
||||||
@@ -206,25 +225,30 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
data: z.object({
|
data: z.object({
|
||||||
roles: OrgRolesSchema.omit({ permissions: true })
|
roles: OrgRolesSchema.omit({ permissions: true }).array()
|
||||||
.merge(z.object({ permissions: z.unknown() }))
|
|
||||||
.array()
|
|
||||||
})
|
})
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const roles = await server.services.orgRole.listRoles(
|
const { roles } = await server.services.role.listRoles({
|
||||||
req.permission.id,
|
permission: req.permission,
|
||||||
req.params.organizationId,
|
scopeData: {
|
||||||
req.permission.authMethod,
|
scope: AccessScope.Organization,
|
||||||
req.permission.orgId
|
orgId: req.permission.orgId
|
||||||
);
|
},
|
||||||
return { data: { roles } };
|
data: {}
|
||||||
|
});
|
||||||
|
return {
|
||||||
|
data: {
|
||||||
|
roles: roles.map((el) => ({ ...el, orgId: el.orgId as string }))
|
||||||
|
}
|
||||||
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
// TODO(simp): get this fixed
|
||||||
server.route({
|
server.route({
|
||||||
method: "GET",
|
method: "GET",
|
||||||
url: "/:organizationId/permissions",
|
url: "/:organizationId/permissions",
|
||||||
@@ -237,20 +261,20 @@ export const registerOrgRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}),
|
}),
|
||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
membership: OrgMembershipsSchema,
|
memberships: OrgMembershipsSchema.array(),
|
||||||
permissions: z.any().array()
|
permissions: z.any().array()
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const { permissions, membership } = await server.services.orgRole.getUserPermission(
|
const { permissions, memberships } = await server.services.orgRole.getUserPermission(
|
||||||
req.permission.id,
|
req.permission.id,
|
||||||
req.params.organizationId,
|
req.params.organizationId,
|
||||||
req.permission.authMethod,
|
req.permission.authMethod,
|
||||||
req.permission.orgId
|
req.permission.orgId
|
||||||
);
|
);
|
||||||
return { permissions, membership };
|
return { permissions, memberships };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { packRules } from "@casl/ability/extra";
|
import { packRules } from "@casl/ability/extra";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
|
||||||
import { ProjectMembershipRole, ProjectRolesSchema } from "@app/db/schemas";
|
import { ProjectMembershipRole, ProjectRolesSchema, AccessScope } from "@app/db/schemas";
|
||||||
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
||||||
import { checkForInvalidPermissionCombination } from "@app/ee/services/permission/permission-fns";
|
import { checkForInvalidPermissionCombination } from "@app/ee/services/permission/permission-fns";
|
||||||
import { ProjectPermissionV2Schema } from "@app/ee/services/permission/project-permission";
|
import { ProjectPermissionV2Schema } from "@app/ee/services/permission/project-permission";
|
||||||
@@ -11,7 +11,6 @@ import { slugSchema } from "@app/server/lib/schemas";
|
|||||||
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
||||||
import { SanitizedRoleSchema } from "@app/server/routes/sanitizedSchemas";
|
import { SanitizedRoleSchema } from "@app/server/routes/sanitizedSchemas";
|
||||||
import { AuthMode } from "@app/services/auth/auth-type";
|
import { AuthMode } from "@app/services/auth/auth-type";
|
||||||
import { ProjectRoleServiceIdentifierType } from "@app/services/project-role/project-role-types";
|
|
||||||
|
|
||||||
export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
||||||
server.route({
|
server.route({
|
||||||
@@ -55,13 +54,11 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const stringifiedPermissions = JSON.stringify(packRules(req.body.permissions));
|
const stringifiedPermissions = JSON.stringify(packRules(req.body.permissions));
|
||||||
|
|
||||||
const role = await server.services.projectRole.createRole({
|
const role = await server.services.role.createRole({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.ID,
|
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
},
|
},
|
||||||
data: {
|
data: {
|
||||||
@@ -73,7 +70,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.CREATE_PROJECT_ROLE,
|
type: EventType.CREATE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -86,7 +83,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -133,12 +130,16 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const stringifiedPermissions = req.body.permissions ? JSON.stringify(packRules(req.body.permissions)) : undefined;
|
const stringifiedPermissions = req.body.permissions ? JSON.stringify(packRules(req.body.permissions)) : undefined;
|
||||||
const role = await server.services.projectRole.updateRole({
|
const role = await server.services.role.updateRole({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
roleId: req.params.roleId,
|
projectId: req.params.projectId
|
||||||
|
},
|
||||||
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
},
|
||||||
data: {
|
data: {
|
||||||
...req.body,
|
...req.body,
|
||||||
permissions: stringifiedPermissions
|
permissions: stringifiedPermissions
|
||||||
@@ -148,7 +149,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.UPDATE_PROJECT_ROLE,
|
type: EventType.UPDATE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -161,7 +162,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -192,18 +193,22 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.projectRole.deleteRole({
|
const role = await server.services.role.deleteRole({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
roleId: req.params.roleId
|
projectId: req.params.projectId
|
||||||
|
},
|
||||||
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.DELETE_PROJECT_ROLE,
|
type: EventType.DELETE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -214,7 +219,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -244,17 +249,16 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const roles = await server.services.projectRole.listRoles({
|
const { roles } = await server.services.role.listRoles({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.ID,
|
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
}
|
},
|
||||||
|
data: {}
|
||||||
});
|
});
|
||||||
return { roles };
|
return { roles: roles.map((el) => ({ ...el, projectId: el.projectId as string })) };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -273,24 +277,25 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
}),
|
}),
|
||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
role: SanitizedRoleSchema.omit({ version: true })
|
role: SanitizedRoleSchema
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.projectRole.getRoleBySlug({
|
const role = await server.services.role.getRoleBySlug({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.ID,
|
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
},
|
},
|
||||||
roleSlug: req.params.roleSlug
|
selector: {
|
||||||
|
slug: req.params.roleSlug
|
||||||
|
}
|
||||||
});
|
});
|
||||||
return { role };
|
|
||||||
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -307,14 +312,16 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
data: z.object({
|
data: z.object({
|
||||||
membership: z.object({
|
memberships: z
|
||||||
id: z.string(),
|
.object({
|
||||||
roles: z
|
id: z.string(),
|
||||||
.object({
|
roles: z
|
||||||
role: z.string()
|
.object({
|
||||||
})
|
role: z.string()
|
||||||
.array()
|
})
|
||||||
}),
|
.array()
|
||||||
|
})
|
||||||
|
.array(),
|
||||||
assumedPrivilegeDetails: z
|
assumedPrivilegeDetails: z
|
||||||
.object({
|
.object({
|
||||||
actorId: z.string(),
|
actorId: z.string(),
|
||||||
@@ -330,7 +337,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT]),
|
onRequest: verifyAuth([AuthMode.JWT]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const { permissions, membership, assumedPrivilegeDetails } = await server.services.projectRole.getUserPermission(
|
const { permissions, memberships, assumedPrivilegeDetails } = await server.services.projectRole.getUserPermission(
|
||||||
req.permission.id,
|
req.permission.id,
|
||||||
req.params.projectId,
|
req.params.projectId,
|
||||||
req.permission.authMethod,
|
req.permission.authMethod,
|
||||||
@@ -340,7 +347,7 @@ export const registerProjectRoleRouter = async (server: FastifyZodProvider) => {
|
|||||||
return {
|
return {
|
||||||
data: {
|
data: {
|
||||||
permissions,
|
permissions,
|
||||||
membership,
|
memberships,
|
||||||
assumedPrivilegeDetails
|
assumedPrivilegeDetails
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { packRules } from "@casl/ability/extra";
|
import { packRules } from "@casl/ability/extra";
|
||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
|
||||||
import { ProjectMembershipRole, ProjectRolesSchema } from "@app/db/schemas";
|
import { AccessScope, ProjectMembershipRole, ProjectRolesSchema } from "@app/db/schemas";
|
||||||
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
import { EventType } from "@app/ee/services/audit-log/audit-log-types";
|
||||||
import { checkForInvalidPermissionCombination } from "@app/ee/services/permission/permission-fns";
|
import { checkForInvalidPermissionCombination } from "@app/ee/services/permission/permission-fns";
|
||||||
import { ProjectPermissionV2Schema } from "@app/ee/services/permission/project-permission";
|
import { ProjectPermissionV2Schema } from "@app/ee/services/permission/project-permission";
|
||||||
@@ -11,7 +11,6 @@ import { slugSchema } from "@app/server/lib/schemas";
|
|||||||
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
import { verifyAuth } from "@app/server/plugins/auth/verify-auth";
|
||||||
import { SanitizedRoleSchema } from "@app/server/routes/sanitizedSchemas";
|
import { SanitizedRoleSchema } from "@app/server/routes/sanitizedSchemas";
|
||||||
import { AuthMode } from "@app/services/auth/auth-type";
|
import { AuthMode } from "@app/services/auth/auth-type";
|
||||||
import { ProjectRoleServiceIdentifierType } from "@app/services/project-role/project-role-types";
|
|
||||||
|
|
||||||
export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProvider) => {
|
export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProvider) => {
|
||||||
server.route({
|
server.route({
|
||||||
@@ -55,13 +54,11 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const stringifiedPermissions = JSON.stringify(packRules(req.body.permissions));
|
const stringifiedPermissions = JSON.stringify(packRules(req.body.permissions));
|
||||||
|
|
||||||
const role = await server.services.projectRole.createRole({
|
const role = await server.services.role.createRole({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.ID,
|
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
},
|
},
|
||||||
data: {
|
data: {
|
||||||
@@ -73,7 +70,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: req.params.projectId,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.CREATE_PROJECT_ROLE,
|
type: EventType.CREATE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -86,7 +83,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -133,12 +130,16 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const stringifiedPermissions = req.body.permissions ? JSON.stringify(packRules(req.body.permissions)) : undefined;
|
const stringifiedPermissions = req.body.permissions ? JSON.stringify(packRules(req.body.permissions)) : undefined;
|
||||||
const role = await server.services.projectRole.updateRole({
|
const role = await server.services.role.updateRole({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
roleId: req.params.roleId,
|
projectId: req.params.projectId
|
||||||
|
},
|
||||||
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
},
|
||||||
data: {
|
data: {
|
||||||
...req.body,
|
...req.body,
|
||||||
permissions: stringifiedPermissions
|
permissions: stringifiedPermissions
|
||||||
@@ -148,7 +149,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.UPDATE_PROJECT_ROLE,
|
type: EventType.UPDATE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -161,7 +162,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -192,18 +193,22 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.projectRole.deleteRole({
|
const role = await server.services.role.deleteRole({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
roleId: req.params.roleId
|
projectId: req.params.projectId
|
||||||
|
},
|
||||||
|
selector: {
|
||||||
|
id: req.params.roleId
|
||||||
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
orgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: role.projectId,
|
projectId: role.projectId as string,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.DELETE_PROJECT_ROLE,
|
type: EventType.DELETE_PROJECT_ROLE,
|
||||||
metadata: {
|
metadata: {
|
||||||
@@ -214,7 +219,7 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { role };
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -244,17 +249,16 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const roles = await server.services.projectRole.listRoles({
|
const { roles } = await server.services.role.listRoles({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.ID,
|
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
}
|
},
|
||||||
|
data: {}
|
||||||
});
|
});
|
||||||
return { roles };
|
return { roles: roles.map((el) => ({ ...el, projectId: el.projectId as string })) };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -273,24 +277,25 @@ export const registerDeprecatedProjectRoleRouter = async (server: FastifyZodProv
|
|||||||
}),
|
}),
|
||||||
response: {
|
response: {
|
||||||
200: z.object({
|
200: z.object({
|
||||||
role: SanitizedRoleSchema.omit({ version: true })
|
role: SanitizedRoleSchema
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const role = await server.services.projectRole.getRoleBySlug({
|
const role = await server.services.role.getRoleBySlug({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
filter: {
|
|
||||||
type: ProjectRoleServiceIdentifierType.ID,
|
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
},
|
},
|
||||||
roleSlug: req.params.roleSlug
|
selector: {
|
||||||
|
slug: req.params.roleSlug
|
||||||
|
}
|
||||||
});
|
});
|
||||||
return { role };
|
|
||||||
|
return { role: { ...role, projectId: role.projectId as string } };
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -44,10 +44,7 @@ type TGroupServiceFactoryDep = {
|
|||||||
projectDAL: Pick<TProjectDALFactory, "findProjectGhostUser" | "findById">;
|
projectDAL: Pick<TProjectDALFactory, "findProjectGhostUser" | "findById">;
|
||||||
projectBotDAL: Pick<TProjectBotDALFactory, "findOne">;
|
projectBotDAL: Pick<TProjectBotDALFactory, "findOne">;
|
||||||
projectKeyDAL: Pick<TProjectKeyDALFactory, "find" | "delete" | "findLatestProjectKey" | "insertMany">;
|
projectKeyDAL: Pick<TProjectKeyDALFactory, "find" | "delete" | "findLatestProjectKey" | "insertMany">;
|
||||||
permissionService: Pick<
|
permissionService: Pick<TPermissionServiceFactory, "getOrgPermission" | "getOrgPermissionByRoles" | "invalidateProjectPermissionCache">;
|
||||||
TPermissionServiceFactory,
|
|
||||||
"getOrgPermission" | "getOrgPermissionByRole" | "invalidateProjectPermissionCache"
|
|
||||||
>;
|
|
||||||
licenseService: Pick<TLicenseServiceFactory, "getPlan">;
|
licenseService: Pick<TLicenseServiceFactory, "getPlan">;
|
||||||
oidcConfigDAL: Pick<TOidcConfigDALFactory, "findOne">;
|
oidcConfigDAL: Pick<TOidcConfigDALFactory, "findOne">;
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -66,12 +66,12 @@ export type TPermissionServiceFactory = {
|
|||||||
actorOrgId: string | undefined
|
actorOrgId: string | undefined
|
||||||
) => Promise<{
|
) => Promise<{
|
||||||
permission: MongoAbility<OrgPermissionSet, MongoQuery>;
|
permission: MongoAbility<OrgPermissionSet, MongoQuery>;
|
||||||
memberships: TMemberships[];
|
memberships: Array<TMemberships & { roles: { role: string; customRoleSlug?: string | null }[] }>;
|
||||||
hasRole: (role: string) => boolean;
|
hasRole: (role: string) => boolean;
|
||||||
}>;
|
}>;
|
||||||
getProjectPermission: (arg: TGetProjectPermissionArg) => Promise<{
|
getProjectPermission: (arg: TGetProjectPermissionArg) => Promise<{
|
||||||
permission: MongoAbility<ProjectPermissionSet, MongoQuery>;
|
permission: MongoAbility<ProjectPermissionSet, MongoQuery>;
|
||||||
memberships: TMemberships[];
|
memberships: Array<TMemberships & { roles: { role: string; customRoleSlug?: string | null }[] }>;
|
||||||
hasRole: (role: string) => boolean;
|
hasRole: (role: string) => boolean;
|
||||||
}>;
|
}>;
|
||||||
// TODO(simp): check what is this doing
|
// TODO(simp): check what is this doing
|
||||||
|
|||||||
@@ -147,6 +147,8 @@ import { TQueueServiceFactory } from "@app/queue";
|
|||||||
import { readLimit } from "@app/server/config/rateLimiter";
|
import { readLimit } from "@app/server/config/rateLimiter";
|
||||||
import { registerSecretScanningV2Webhooks } from "@app/server/plugins/secret-scanner-v2";
|
import { registerSecretScanningV2Webhooks } from "@app/server/plugins/secret-scanner-v2";
|
||||||
import { accessTokenQueueServiceFactory } from "@app/services/access-token-queue/access-token-queue";
|
import { accessTokenQueueServiceFactory } from "@app/services/access-token-queue/access-token-queue";
|
||||||
|
import { additionalPrivilegeDALFactory } from "@app/services/additional-privilege/additional-privilege-dal";
|
||||||
|
import { additionalPrivilegeServiceFactory } from "@app/services/additional-privilege/additional-privilege-service";
|
||||||
import { apiKeyDALFactory } from "@app/services/api-key/api-key-dal";
|
import { apiKeyDALFactory } from "@app/services/api-key/api-key-dal";
|
||||||
import { apiKeyServiceFactory } from "@app/services/api-key/api-key-service";
|
import { apiKeyServiceFactory } from "@app/services/api-key/api-key-service";
|
||||||
import { appConnectionDALFactory } from "@app/services/app-connection/app-connection-dal";
|
import { appConnectionDALFactory } from "@app/services/app-connection/app-connection-dal";
|
||||||
@@ -231,6 +233,14 @@ import { internalKmsDALFactory } from "@app/services/kms/internal-kms-dal";
|
|||||||
import { kmskeyDALFactory } from "@app/services/kms/kms-key-dal";
|
import { kmskeyDALFactory } from "@app/services/kms/kms-key-dal";
|
||||||
import { kmsRootConfigDALFactory } from "@app/services/kms/kms-root-config-dal";
|
import { kmsRootConfigDALFactory } from "@app/services/kms/kms-root-config-dal";
|
||||||
import { kmsServiceFactory } from "@app/services/kms/kms-service";
|
import { kmsServiceFactory } from "@app/services/kms/kms-service";
|
||||||
|
import { membershipDALFactory } from "@app/services/membership/membership-dal";
|
||||||
|
import { membershipRoleDALFactory } from "@app/services/membership/membership-role-dal";
|
||||||
|
import { membershipGroupDALFactory } from "@app/services/membership-group/membership-group-dal";
|
||||||
|
import { membershipGroupServiceFactory } from "@app/services/membership-group/membership-group-service";
|
||||||
|
import { membershipIdentityDALFactory } from "@app/services/membership-identity/membership-identity-dal";
|
||||||
|
import { membershipIdentityServiceFactory } from "@app/services/membership-identity/membership-identity-service";
|
||||||
|
import { membershipUserDALFactory } from "@app/services/membership-user/membership-user-dal";
|
||||||
|
import { membershipUserServiceFactory } from "@app/services/membership-user/membership-user-service";
|
||||||
import { microsoftTeamsIntegrationDALFactory } from "@app/services/microsoft-teams/microsoft-teams-integration-dal";
|
import { microsoftTeamsIntegrationDALFactory } from "@app/services/microsoft-teams/microsoft-teams-integration-dal";
|
||||||
import { microsoftTeamsServiceFactory } from "@app/services/microsoft-teams/microsoft-teams-service";
|
import { microsoftTeamsServiceFactory } from "@app/services/microsoft-teams/microsoft-teams-service";
|
||||||
import { projectMicrosoftTeamsConfigDALFactory } from "@app/services/microsoft-teams/project-microsoft-teams-config-dal";
|
import { projectMicrosoftTeamsConfigDALFactory } from "@app/services/microsoft-teams/project-microsoft-teams-config-dal";
|
||||||
@@ -283,6 +293,8 @@ import { reminderServiceFactory } from "@app/services/reminder/reminder-service"
|
|||||||
import { reminderRecipientDALFactory } from "@app/services/reminder-recipients/reminder-recipient-dal";
|
import { reminderRecipientDALFactory } from "@app/services/reminder-recipients/reminder-recipient-dal";
|
||||||
import { dailyResourceCleanUpQueueServiceFactory } from "@app/services/resource-cleanup/resource-cleanup-queue";
|
import { dailyResourceCleanUpQueueServiceFactory } from "@app/services/resource-cleanup/resource-cleanup-queue";
|
||||||
import { resourceMetadataDALFactory } from "@app/services/resource-metadata/resource-metadata-dal";
|
import { resourceMetadataDALFactory } from "@app/services/resource-metadata/resource-metadata-dal";
|
||||||
|
import { roleDALFactory } from "@app/services/role/role-dal";
|
||||||
|
import { roleServiceFactory } from "@app/services/role/role-service";
|
||||||
import { secretDALFactory } from "@app/services/secret/secret-dal";
|
import { secretDALFactory } from "@app/services/secret/secret-dal";
|
||||||
import { secretQueueFactory } from "@app/services/secret/secret-queue";
|
import { secretQueueFactory } from "@app/services/secret/secret-queue";
|
||||||
import { secretServiceFactory } from "@app/services/secret/secret-service";
|
import { secretServiceFactory } from "@app/services/secret/secret-service";
|
||||||
@@ -531,17 +543,27 @@ export const registerRoutes = async (
|
|||||||
const secretScanningV2DAL = secretScanningV2DALFactory(db);
|
const secretScanningV2DAL = secretScanningV2DALFactory(db);
|
||||||
const keyValueStoreDAL = keyValueStoreDALFactory(db);
|
const keyValueStoreDAL = keyValueStoreDALFactory(db);
|
||||||
|
|
||||||
|
const membershipDAL = membershipDALFactory(db);
|
||||||
|
const membershipUserDAL = membershipUserDALFactory(db);
|
||||||
|
const membershipIdentityDAL = membershipIdentityDALFactory(db);
|
||||||
|
const membershipGroupDAL = membershipGroupDALFactory(db);
|
||||||
|
const additionalPrivilegeDAL = additionalPrivilegeDALFactory(db);
|
||||||
|
const membershipRoleDAL = membershipRoleDALFactory(db);
|
||||||
|
const roleDAL = roleDALFactory(db);
|
||||||
|
|
||||||
const eventBusService = eventBusFactory(server.redis);
|
const eventBusService = eventBusFactory(server.redis);
|
||||||
const sseService = sseServiceFactory(eventBusService, server.redis);
|
const sseService = sseServiceFactory(eventBusService, server.redis);
|
||||||
|
|
||||||
const permissionService = permissionServiceFactory({
|
const permissionService = permissionServiceFactory({
|
||||||
permissionDAL,
|
permissionDAL,
|
||||||
orgRoleDAL,
|
|
||||||
projectRoleDAL,
|
|
||||||
serviceTokenDAL,
|
serviceTokenDAL,
|
||||||
projectDAL,
|
projectDAL,
|
||||||
keyStore
|
keyStore,
|
||||||
|
roleDAL,
|
||||||
|
userDAL,
|
||||||
|
identityDAL
|
||||||
});
|
});
|
||||||
|
|
||||||
const assumePrivilegeService = assumePrivilegeServiceFactory({
|
const assumePrivilegeService = assumePrivilegeServiceFactory({
|
||||||
projectDAL,
|
projectDAL,
|
||||||
permissionService
|
permissionService
|
||||||
@@ -556,6 +578,41 @@ export const registerRoutes = async (
|
|||||||
projectDAL
|
projectDAL
|
||||||
});
|
});
|
||||||
|
|
||||||
|
const membershipUserService = membershipUserServiceFactory({
|
||||||
|
licenseService,
|
||||||
|
membershipRoleDAL,
|
||||||
|
membershipUserDAL,
|
||||||
|
orgDAL,
|
||||||
|
permissionService,
|
||||||
|
roleDAL,
|
||||||
|
userDAL
|
||||||
|
});
|
||||||
|
|
||||||
|
const membershipIdentityService = membershipIdentityServiceFactory({
|
||||||
|
membershipIdentityDAL,
|
||||||
|
membershipRoleDAL,
|
||||||
|
orgDAL,
|
||||||
|
permissionService,
|
||||||
|
roleDAL
|
||||||
|
});
|
||||||
|
|
||||||
|
const membershipGroupService = membershipGroupServiceFactory({
|
||||||
|
membershipGroupDAL,
|
||||||
|
membershipRoleDAL,
|
||||||
|
roleDAL
|
||||||
|
});
|
||||||
|
|
||||||
|
const roleService = roleServiceFactory({
|
||||||
|
permissionService,
|
||||||
|
roleDAL
|
||||||
|
});
|
||||||
|
const additionalPrivilegeService = additionalPrivilegeServiceFactory({
|
||||||
|
additionalPrivilegeDAL,
|
||||||
|
membershipDAL,
|
||||||
|
orgDAL,
|
||||||
|
permissionService
|
||||||
|
});
|
||||||
|
|
||||||
const hsmService = hsmServiceFactory({
|
const hsmService = hsmServiceFactory({
|
||||||
hsmModule,
|
hsmModule,
|
||||||
envConfig
|
envConfig
|
||||||
@@ -1538,7 +1595,8 @@ export const registerRoutes = async (
|
|||||||
identityProjectDAL,
|
identityProjectDAL,
|
||||||
licenseService,
|
licenseService,
|
||||||
identityMetadataDAL,
|
identityMetadataDAL,
|
||||||
keyStore
|
keyStore,
|
||||||
|
orgDAL
|
||||||
});
|
});
|
||||||
|
|
||||||
const identityAuthTemplateService = identityAuthTemplateServiceFactory({
|
const identityAuthTemplateService = identityAuthTemplateServiceFactory({
|
||||||
@@ -1563,8 +1621,10 @@ export const registerRoutes = async (
|
|||||||
identityProjectDAL,
|
identityProjectDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
identityProjectMembershipRoleDAL,
|
identityProjectMembershipRoleDAL,
|
||||||
projectRoleDAL
|
projectRoleDAL,
|
||||||
|
orgDAL
|
||||||
});
|
});
|
||||||
|
|
||||||
const identityProjectAdditionalPrivilegeService = identityProjectAdditionalPrivilegeServiceFactory({
|
const identityProjectAdditionalPrivilegeService = identityProjectAdditionalPrivilegeServiceFactory({
|
||||||
projectDAL,
|
projectDAL,
|
||||||
identityProjectAdditionalPrivilegeDAL,
|
identityProjectAdditionalPrivilegeDAL,
|
||||||
@@ -1584,7 +1644,8 @@ export const registerRoutes = async (
|
|||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
permissionService,
|
permissionService,
|
||||||
licenseService
|
licenseService,
|
||||||
|
orgDAL
|
||||||
});
|
});
|
||||||
|
|
||||||
const identityUaService = identityUaServiceFactory({
|
const identityUaService = identityUaServiceFactory({
|
||||||
@@ -1594,7 +1655,8 @@ export const registerRoutes = async (
|
|||||||
identityUaClientSecretDAL,
|
identityUaClientSecretDAL,
|
||||||
identityUaDAL,
|
identityUaDAL,
|
||||||
licenseService,
|
licenseService,
|
||||||
keyStore
|
keyStore,
|
||||||
|
orgDAL
|
||||||
});
|
});
|
||||||
|
|
||||||
const identityKubernetesAuthService = identityKubernetesAuthServiceFactory({
|
const identityKubernetesAuthService = identityKubernetesAuthServiceFactory({
|
||||||
@@ -1604,6 +1666,7 @@ export const registerRoutes = async (
|
|||||||
permissionService,
|
permissionService,
|
||||||
licenseService,
|
licenseService,
|
||||||
gatewayService,
|
gatewayService,
|
||||||
|
orgDAL,
|
||||||
gatewayV2Service,
|
gatewayV2Service,
|
||||||
gatewayV2DAL,
|
gatewayV2DAL,
|
||||||
gatewayDAL,
|
gatewayDAL,
|
||||||
@@ -1611,6 +1674,7 @@ export const registerRoutes = async (
|
|||||||
});
|
});
|
||||||
const identityGcpAuthService = identityGcpAuthServiceFactory({
|
const identityGcpAuthService = identityGcpAuthServiceFactory({
|
||||||
identityGcpAuthDAL,
|
identityGcpAuthDAL,
|
||||||
|
orgDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
permissionService,
|
permissionService,
|
||||||
@@ -1619,6 +1683,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityAliCloudAuthService = identityAliCloudAuthServiceFactory({
|
const identityAliCloudAuthService = identityAliCloudAuthServiceFactory({
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
|
orgDAL,
|
||||||
identityAliCloudAuthDAL,
|
identityAliCloudAuthDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
licenseService,
|
licenseService,
|
||||||
@@ -1627,6 +1692,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityTlsCertAuthService = identityTlsCertAuthServiceFactory({
|
const identityTlsCertAuthService = identityTlsCertAuthServiceFactory({
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
|
orgDAL,
|
||||||
identityTlsCertAuthDAL,
|
identityTlsCertAuthDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
licenseService,
|
licenseService,
|
||||||
@@ -1636,6 +1702,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityAwsAuthService = identityAwsAuthServiceFactory({
|
const identityAwsAuthService = identityAwsAuthServiceFactory({
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
|
orgDAL,
|
||||||
identityAwsAuthDAL,
|
identityAwsAuthDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
licenseService,
|
licenseService,
|
||||||
@@ -1644,6 +1711,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityAzureAuthService = identityAzureAuthServiceFactory({
|
const identityAzureAuthService = identityAzureAuthServiceFactory({
|
||||||
identityAzureAuthDAL,
|
identityAzureAuthDAL,
|
||||||
|
orgDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
permissionService,
|
permissionService,
|
||||||
@@ -1652,6 +1720,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityOciAuthService = identityOciAuthServiceFactory({
|
const identityOciAuthService = identityOciAuthServiceFactory({
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
|
orgDAL,
|
||||||
identityOciAuthDAL,
|
identityOciAuthDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
licenseService,
|
licenseService,
|
||||||
@@ -1674,6 +1743,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityOidcAuthService = identityOidcAuthServiceFactory({
|
const identityOidcAuthService = identityOidcAuthServiceFactory({
|
||||||
identityOidcAuthDAL,
|
identityOidcAuthDAL,
|
||||||
|
orgDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
permissionService,
|
permissionService,
|
||||||
@@ -1683,6 +1753,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityJwtAuthService = identityJwtAuthServiceFactory({
|
const identityJwtAuthService = identityJwtAuthServiceFactory({
|
||||||
identityJwtAuthDAL,
|
identityJwtAuthDAL,
|
||||||
|
orgDAL,
|
||||||
permissionService,
|
permissionService,
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
identityOrgMembershipDAL,
|
identityOrgMembershipDAL,
|
||||||
@@ -1692,6 +1763,7 @@ export const registerRoutes = async (
|
|||||||
|
|
||||||
const identityLdapAuthService = identityLdapAuthServiceFactory({
|
const identityLdapAuthService = identityLdapAuthServiceFactory({
|
||||||
identityLdapAuthDAL,
|
identityLdapAuthDAL,
|
||||||
|
orgDAL,
|
||||||
permissionService,
|
permissionService,
|
||||||
kmsService,
|
kmsService,
|
||||||
identityAccessTokenDAL,
|
identityAccessTokenDAL,
|
||||||
@@ -2300,7 +2372,13 @@ export const registerRoutes = async (
|
|||||||
pamResource: pamResourceService,
|
pamResource: pamResourceService,
|
||||||
pamAccount: pamAccountService,
|
pamAccount: pamAccountService,
|
||||||
pamSession: pamSessionService,
|
pamSession: pamSessionService,
|
||||||
upgradePath: upgradePathService
|
upgradePath: upgradePathService,
|
||||||
|
|
||||||
|
membershipUser: membershipUserService,
|
||||||
|
membershipIdentity: membershipIdentityService,
|
||||||
|
membershipGroup: membershipGroupService,
|
||||||
|
role: roleService,
|
||||||
|
additionalPrivilege: additionalPrivilegeService
|
||||||
});
|
});
|
||||||
|
|
||||||
const cronJobs: CronJob[] = [];
|
const cronJobs: CronJob[] = [];
|
||||||
|
|||||||
@@ -209,11 +209,11 @@ export const SanitizedIdentityPrivilegeSchema = IdentityProjectAdditionalPrivile
|
|||||||
)
|
)
|
||||||
});
|
});
|
||||||
|
|
||||||
export const SanitizedRoleSchema = ProjectRolesSchema.extend({
|
export const SanitizedRoleSchema = ProjectRolesSchema.omit({ version: true }).extend({
|
||||||
permissions: UnpackedPermissionSchema.array()
|
permissions: UnpackedPermissionSchema.array()
|
||||||
});
|
});
|
||||||
|
|
||||||
export const SanitizedRoleSchemaV1 = ProjectRolesSchema.extend({
|
export const SanitizedRoleSchemaV1 = ProjectRolesSchema.omit({ version: true }).extend({
|
||||||
permissions: UnpackedPermissionSchema.array().transform((caslPermission) =>
|
permissions: UnpackedPermissionSchema.array().transform((caslPermission) =>
|
||||||
// first map and remove other actions of folder permission
|
// first map and remove other actions of folder permission
|
||||||
caslPermission
|
caslPermission
|
||||||
|
|||||||
@@ -1,7 +1,7 @@
|
|||||||
import { z } from "zod";
|
import { z } from "zod";
|
||||||
|
|
||||||
import {
|
import {
|
||||||
OrgMembershipRole,
|
AccessScope,
|
||||||
ProjectMembershipRole,
|
ProjectMembershipRole,
|
||||||
ProjectMembershipsSchema,
|
ProjectMembershipsSchema,
|
||||||
ProjectUserMembershipRolesSchema,
|
ProjectUserMembershipRolesSchema,
|
||||||
@@ -67,14 +67,23 @@ export const registerProjectMembershipRouter = async (server: FastifyZodProvider
|
|||||||
},
|
},
|
||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.API_KEY, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.API_KEY, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const memberships = await server.services.projectMembership.getProjectMemberships({
|
const { data: memberships } = await server.services.membershipUser.listMemberships({
|
||||||
actorId: req.permission.id,
|
permission: req.permission,
|
||||||
actor: req.permission.type,
|
scopeData: {
|
||||||
actorAuthMethod: req.permission.authMethod,
|
scope: AccessScope.Project,
|
||||||
actorOrgId: req.permission.orgId,
|
orgId: req.permission.orgId,
|
||||||
projectId: req.params.projectId
|
projectId: req.params.projectId
|
||||||
|
},
|
||||||
|
data: {}
|
||||||
});
|
});
|
||||||
return { memberships };
|
|
||||||
|
return {
|
||||||
|
memberships: memberships.map((el) => ({
|
||||||
|
...el,
|
||||||
|
userId: el.actorUserId as string,
|
||||||
|
projectId: req.params.projectId
|
||||||
|
}))
|
||||||
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
@@ -242,20 +251,17 @@ export const registerProjectMembershipRouter = async (server: FastifyZodProvider
|
|||||||
onRequest: verifyAuth([AuthMode.JWT, AuthMode.API_KEY, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
onRequest: verifyAuth([AuthMode.JWT, AuthMode.API_KEY, AuthMode.IDENTITY_ACCESS_TOKEN]),
|
||||||
handler: async (req) => {
|
handler: async (req) => {
|
||||||
const usernamesAndEmails = [...req.body.emails, ...req.body.usernames];
|
const usernamesAndEmails = [...req.body.emails, ...req.body.usernames];
|
||||||
const { projectMemberships: memberships } = await server.services.org.inviteUserToOrganization({
|
const { memberships } = await server.services.membershipUser.createMembership({
|
||||||
actorAuthMethod: req.permission.authMethod,
|
permission: req.permission,
|
||||||
actorId: req.permission.id,
|
scopeData: {
|
||||||
actorOrgId: req.permission.orgId,
|
scope: AccessScope.Project,
|
||||||
actor: req.permission.type,
|
orgId: req.permission.orgId,
|
||||||
inviteeEmails: usernamesAndEmails,
|
projectId: req.params.projectId
|
||||||
orgId: req.permission.orgId,
|
},
|
||||||
organizationRoleSlug: OrgMembershipRole.NoAccess,
|
data: {
|
||||||
projects: [
|
roles: (req.body.roleSlugs || [ProjectMembershipRole.Member]).map((role) => ({ isTemporary: false, role })),
|
||||||
{
|
usernames: usernamesAndEmails
|
||||||
id: req.params.projectId,
|
}
|
||||||
projectRoleSlug: req.body.roleSlugs || [ProjectMembershipRole.Member]
|
|
||||||
}
|
|
||||||
]
|
|
||||||
});
|
});
|
||||||
|
|
||||||
await server.services.auditLog.createAuditLog({
|
await server.services.auditLog.createAuditLog({
|
||||||
@@ -263,15 +269,21 @@ export const registerProjectMembershipRouter = async (server: FastifyZodProvider
|
|||||||
...req.auditLogInfo,
|
...req.auditLogInfo,
|
||||||
event: {
|
event: {
|
||||||
type: EventType.ADD_BATCH_PROJECT_MEMBER,
|
type: EventType.ADD_BATCH_PROJECT_MEMBER,
|
||||||
metadata: memberships.map(({ userId, id }) => ({
|
metadata: memberships.map(({ actorUserId, id }) => ({
|
||||||
userId: userId || "",
|
userId: actorUserId || "",
|
||||||
membershipId: id,
|
membershipId: id,
|
||||||
email: ""
|
email: ""
|
||||||
}))
|
}))
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
return { memberships };
|
return {
|
||||||
|
memberships: memberships.map((el) => ({
|
||||||
|
...el,
|
||||||
|
userId: el.actorUserId as string,
|
||||||
|
projectId: req.params.projectId
|
||||||
|
}))
|
||||||
|
};
|
||||||
}
|
}
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,88 @@
|
|||||||
|
import { NotFoundError } from "@app/lib/errors";
|
||||||
|
import { TMembershipDALFactory } from "../membership/membership-dal";
|
||||||
|
import { TProjectDALFactory } from "../project/project-dal";
|
||||||
|
import { AccessScope, AccessScopeData } from "@app/db/schemas";
|
||||||
|
|
||||||
|
type TConvertorServiceFactoryDep = {
|
||||||
|
projectDAL: Pick<TProjectDALFactory, "findOne">;
|
||||||
|
membershipDAL: Pick<TMembershipDALFactory, "findOne">;
|
||||||
|
};
|
||||||
|
|
||||||
|
export type TConvertorServiceFactory = ReturnType<typeof convertorServiceFactory>;
|
||||||
|
|
||||||
|
export const convertorServiceFactory = ({ projectDAL, membershipDAL }: TConvertorServiceFactoryDep) => {
|
||||||
|
const $getScopeDatabaseFields = (scopeData: AccessScopeData) => {
|
||||||
|
if (scopeData.scope === AccessScope.Organization) {
|
||||||
|
return { scopeOrgId: scopeData.orgId };
|
||||||
|
}
|
||||||
|
|
||||||
|
if (scopeData.scope === AccessScope.Namespace) {
|
||||||
|
return { scopeNamespaceId: scopeData.namespaceId, scopeOrgId: scopeData.orgId };
|
||||||
|
}
|
||||||
|
|
||||||
|
return { scopeProjectId: scopeData.projectId, scopeOrgId: scopeData.orgId };
|
||||||
|
};
|
||||||
|
|
||||||
|
const projectSlugToId = async (dto: { slug: string; orgId: string }) => {
|
||||||
|
const project = await projectDAL.findOne({
|
||||||
|
orgId: dto.orgId,
|
||||||
|
slug: dto.slug
|
||||||
|
});
|
||||||
|
if (!project) throw new NotFoundError({ message: `Project with slug ${slug} not found` });
|
||||||
|
return project;
|
||||||
|
};
|
||||||
|
|
||||||
|
const userMembershipIdToUserId = async (scopeData: AccessScopeData, membershipId: string) => {
|
||||||
|
const dbFields = $getScopeDatabaseFields(scopeData);
|
||||||
|
|
||||||
|
const membership = await membershipDAL.findOne({
|
||||||
|
scope: scopeData.scope,
|
||||||
|
id: membershipId,
|
||||||
|
...dbFields,
|
||||||
|
scopeOrgId: scopeData.orgId
|
||||||
|
});
|
||||||
|
if (!membership || !membership.actorUserId) {
|
||||||
|
throw new NotFoundError({ message: `Membership with id ${membershipId} not found` });
|
||||||
|
}
|
||||||
|
return membership.actorUserId;
|
||||||
|
};
|
||||||
|
|
||||||
|
const groupMembershipIdToGroupId = async (scopeData: AccessScopeData, membershipId: string) => {
|
||||||
|
const dbFields = $getScopeDatabaseFields(scopeData);
|
||||||
|
|
||||||
|
const membership = await membershipDAL.findOne({
|
||||||
|
scope: scopeData.scope,
|
||||||
|
id: membershipId,
|
||||||
|
...dbFields,
|
||||||
|
scopeOrgId: scopeData.orgId
|
||||||
|
});
|
||||||
|
if (!membership || !membership.actorGroupId) {
|
||||||
|
throw new NotFoundError({ message: `Membership with id ${membershipId} not found` });
|
||||||
|
}
|
||||||
|
|
||||||
|
return membership.actorGroupId;
|
||||||
|
};
|
||||||
|
|
||||||
|
const identityMembershipIdToGroupId = async (scopeData: AccessScopeData, membershipId: string) => {
|
||||||
|
const dbFields = $getScopeDatabaseFields(scopeData);
|
||||||
|
|
||||||
|
const membership = await membershipDAL.findOne({
|
||||||
|
scope: scopeData.scope,
|
||||||
|
id: membershipId,
|
||||||
|
...dbFields,
|
||||||
|
scopeOrgId: scopeData.orgId
|
||||||
|
});
|
||||||
|
if (!membership || !membership.actorIdentityId) {
|
||||||
|
throw new NotFoundError({ message: `Membership with id ${membershipId} not found` });
|
||||||
|
}
|
||||||
|
|
||||||
|
return membership.actorIdentityId;
|
||||||
|
};
|
||||||
|
|
||||||
|
return {
|
||||||
|
projectSlugToId,
|
||||||
|
userMembershipIdToUserId,
|
||||||
|
groupMembershipIdToGroupId,
|
||||||
|
identityMembershipIdToGroupId
|
||||||
|
};
|
||||||
|
};
|
||||||
@@ -43,10 +43,7 @@ type TGroupProjectServiceFactoryDep = {
|
|||||||
projectRoleDAL: Pick<TProjectRoleDALFactory, "find">;
|
projectRoleDAL: Pick<TProjectRoleDALFactory, "find">;
|
||||||
projectBotDAL: TProjectBotDALFactory;
|
projectBotDAL: TProjectBotDALFactory;
|
||||||
groupDAL: Pick<TGroupDALFactory, "findOne" | "findAllGroupPossibleMembers">;
|
groupDAL: Pick<TGroupDALFactory, "findOne" | "findAllGroupPossibleMembers">;
|
||||||
permissionService: Pick<
|
permissionService: Pick<TPermissionServiceFactory, "getProjectPermission" | "getProjectPermissionByRoles" | "invalidateProjectPermissionCache">;
|
||||||
TPermissionServiceFactory,
|
|
||||||
"getProjectPermission" | "getProjectPermissionByRole" | "invalidateProjectPermissionCache"
|
|
||||||
>;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
export type TGroupProjectServiceFactory = ReturnType<typeof groupProjectServiceFactory>;
|
export type TGroupProjectServiceFactory = ReturnType<typeof groupProjectServiceFactory>;
|
||||||
|
|||||||
+18
-20
@@ -115,29 +115,27 @@ export const newProjectMembershipIdentityFactory = ({
|
|||||||
|
|
||||||
const { shouldUseNewPrivilegeSystem } = await orgDAL.findById(dto.permission.orgId);
|
const { shouldUseNewPrivilegeSystem } = await orgDAL.findById(dto.permission.orgId);
|
||||||
const permissionRoles = await permissionService.getProjectPermissionByRoles(
|
const permissionRoles = await permissionService.getProjectPermissionByRoles(
|
||||||
dto.data.roles.map((el) => el.role),
|
dto.data.roles.filter((el) => el.role !== ProjectMembershipRole.NoAccess).map((el) => el.role),
|
||||||
scope.value
|
scope.value
|
||||||
);
|
);
|
||||||
for (const permissionRole of permissionRoles) {
|
for (const permissionRole of permissionRoles) {
|
||||||
if (permissionRole?.role?.name !== ProjectMembershipRole.NoAccess) {
|
const permissionBoundary = validatePrivilegeChangeOperation(
|
||||||
const permissionBoundary = validatePrivilegeChangeOperation(
|
shouldUseNewPrivilegeSystem,
|
||||||
shouldUseNewPrivilegeSystem,
|
ProjectPermissionIdentityActions.GrantPrivileges,
|
||||||
ProjectPermissionIdentityActions.GrantPrivileges,
|
ProjectPermissionSub.Identity,
|
||||||
ProjectPermissionSub.Identity,
|
permission,
|
||||||
permission,
|
permissionRole.permission
|
||||||
permissionRole.permission
|
);
|
||||||
);
|
if (!permissionBoundary.isValid)
|
||||||
if (!permissionBoundary.isValid)
|
throw new PermissionBoundaryError({
|
||||||
throw new PermissionBoundaryError({
|
message: constructPermissionErrorMessage(
|
||||||
message: constructPermissionErrorMessage(
|
"Failed to create identity project membership",
|
||||||
"Failed to create identity project membership",
|
shouldUseNewPrivilegeSystem,
|
||||||
shouldUseNewPrivilegeSystem,
|
ProjectPermissionIdentityActions.GrantPrivileges,
|
||||||
ProjectPermissionIdentityActions.GrantPrivileges,
|
ProjectPermissionSub.Identity
|
||||||
ProjectPermissionSub.Identity
|
),
|
||||||
),
|
details: { missingPermissions: permissionBoundary.missingPermissions }
|
||||||
details: { missingPermissions: permissionBoundary.missingPermissions }
|
});
|
||||||
});
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -44,6 +44,7 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
})
|
})
|
||||||
.where(`${TableName.Membership}.scopeOrgId`, scopeData.orgId)
|
.where(`${TableName.Membership}.scopeOrgId`, scopeData.orgId)
|
||||||
.where(`${TableName.Membership}.actorUserId`, userId)
|
.where(`${TableName.Membership}.actorUserId`, userId)
|
||||||
|
.where(`${TableName.Users}.isGhost`, false)
|
||||||
.where((qb) => {
|
.where((qb) => {
|
||||||
if (scopeData.scope === AccessScope.Organization) {
|
if (scopeData.scope === AccessScope.Organization) {
|
||||||
void qb.where(`${TableName.Membership}.scope`, AccessScope.Organization);
|
void qb.where(`${TableName.Membership}.scope`, AccessScope.Organization);
|
||||||
@@ -60,7 +61,9 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
})
|
})
|
||||||
.select(selectAllTableCols(TableName.Membership))
|
.select(selectAllTableCols(TableName.Membership))
|
||||||
.select(
|
.select(
|
||||||
db.ref("slug").withSchema(TableName.Role).as("roleSlug"),
|
db.ref("slug").withSchema(TableName.Role).as("customRoleSlug"),
|
||||||
|
db.ref("name").withSchema(TableName.Role).as("customRoleName"),
|
||||||
|
db.ref("id").withSchema(TableName.Role).as("customRoleId"),
|
||||||
db.ref("id").withSchema(TableName.MembershipRole).as("membershipRoleId"),
|
db.ref("id").withSchema(TableName.MembershipRole).as("membershipRoleId"),
|
||||||
db.ref("role").withSchema(TableName.MembershipRole).as("membershipRole"),
|
db.ref("role").withSchema(TableName.MembershipRole).as("membershipRole"),
|
||||||
db.ref("temporaryMode").withSchema(TableName.MembershipRole).as("membershipRoleTemporaryMode"),
|
db.ref("temporaryMode").withSchema(TableName.MembershipRole).as("membershipRoleTemporaryMode"),
|
||||||
@@ -78,19 +81,35 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
db.ref("updatedAt").withSchema(TableName.MembershipRole).as("membershipRoleUpdatedAt"),
|
db.ref("updatedAt").withSchema(TableName.MembershipRole).as("membershipRoleUpdatedAt"),
|
||||||
db.ref("id").withSchema(TableName.IdentityMetadata).as("metadataId"),
|
db.ref("id").withSchema(TableName.IdentityMetadata).as("metadataId"),
|
||||||
db.ref("key").withSchema(TableName.IdentityMetadata).as("metadataKey"),
|
db.ref("key").withSchema(TableName.IdentityMetadata).as("metadataKey"),
|
||||||
db.ref("value").withSchema(TableName.IdentityMetadata).as("metadataValue")
|
db.ref("value").withSchema(TableName.IdentityMetadata).as("metadataValue"),
|
||||||
|
db.ref("username").withSchema(TableName.Users).as("userUsername"),
|
||||||
|
db.ref("email").withSchema(TableName.Users).as("userEmail"),
|
||||||
|
db.ref("firstName").withSchema(TableName.Users).as("userFirstName"),
|
||||||
|
db.ref("lastName").withSchema(TableName.Users).as("userLastName"),
|
||||||
|
db.ref("id").withSchema(TableName.Users).as("userId")
|
||||||
);
|
);
|
||||||
|
|
||||||
const data = sqlNestRelationships({
|
const data = sqlNestRelationships({
|
||||||
data: docs,
|
data: docs,
|
||||||
key: "id",
|
key: "id",
|
||||||
parentMapper: (el) => MembershipsSchema.parse(el),
|
parentMapper: (el) => ({
|
||||||
|
...MembershipsSchema.parse(el),
|
||||||
|
user: {
|
||||||
|
username: el.userUsername,
|
||||||
|
email: el.userEmail,
|
||||||
|
firstName: el.userFirstName,
|
||||||
|
lastName: el.userLastName,
|
||||||
|
id: el.userId
|
||||||
|
}
|
||||||
|
}),
|
||||||
childrenMapper: [
|
childrenMapper: [
|
||||||
{
|
{
|
||||||
key: "membershipRoleId",
|
key: "membershipRoleId",
|
||||||
label: "roles" as const,
|
label: "roles" as const,
|
||||||
mapper: ({
|
mapper: ({
|
||||||
roleSlug,
|
customRoleSlug,
|
||||||
|
customRoleName,
|
||||||
|
customRoleId,
|
||||||
membershipRoleId,
|
membershipRoleId,
|
||||||
membershipRole,
|
membershipRole,
|
||||||
membershipRoleIsTemporary,
|
membershipRoleIsTemporary,
|
||||||
@@ -103,7 +122,9 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
}) => ({
|
}) => ({
|
||||||
id: membershipRoleId,
|
id: membershipRoleId,
|
||||||
role: membershipRole,
|
role: membershipRole,
|
||||||
customRoleSlug: roleSlug,
|
customRoleSlug,
|
||||||
|
customRoleName,
|
||||||
|
customRoleId,
|
||||||
temporaryRange: membershipRoleTemporaryRange,
|
temporaryRange: membershipRoleTemporaryRange,
|
||||||
temporaryMode: membershipRoleTemporaryMode,
|
temporaryMode: membershipRoleTemporaryMode,
|
||||||
temporaryAccessStartTime: membershipRoleTemporaryAccessStartTime,
|
temporaryAccessStartTime: membershipRoleTemporaryAccessStartTime,
|
||||||
@@ -140,6 +161,7 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
.leftJoin(TableName.Role, `${TableName.MembershipRole}.customRoleId`, `${TableName.Role}.id`)
|
.leftJoin(TableName.Role, `${TableName.MembershipRole}.customRoleId`, `${TableName.Role}.id`)
|
||||||
.distinct(`${TableName.Membership}.id`)
|
.distinct(`${TableName.Membership}.id`)
|
||||||
.where(`${TableName.Membership}.scopeOrgId`, scopeData.orgId)
|
.where(`${TableName.Membership}.scopeOrgId`, scopeData.orgId)
|
||||||
|
.where(`${TableName.Users}.isGhost`, false)
|
||||||
.where((qb) => {
|
.where((qb) => {
|
||||||
if (scopeData.scope === AccessScope.Organization) {
|
if (scopeData.scope === AccessScope.Organization) {
|
||||||
void qb.where(`${TableName.Membership}.scope`, AccessScope.Organization);
|
void qb.where(`${TableName.Membership}.scope`, AccessScope.Organization);
|
||||||
@@ -188,7 +210,9 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
.whereIn(`${TableName.Membership}.id`, paginatedUsers)
|
.whereIn(`${TableName.Membership}.id`, paginatedUsers)
|
||||||
.select(selectAllTableCols(TableName.Membership))
|
.select(selectAllTableCols(TableName.Membership))
|
||||||
.select(
|
.select(
|
||||||
db.ref("slug").withSchema(TableName.Role).as("roleSlug"),
|
db.ref("slug").withSchema(TableName.Role).as("customRoleSlug"),
|
||||||
|
db.ref("name").withSchema(TableName.Role).as("customRoleName"),
|
||||||
|
db.ref("id").withSchema(TableName.Role).as("customRoleId"),
|
||||||
db.ref("id").withSchema(TableName.MembershipRole).as("membershipRoleId"),
|
db.ref("id").withSchema(TableName.MembershipRole).as("membershipRoleId"),
|
||||||
db.ref("role").withSchema(TableName.MembershipRole).as("membershipRole"),
|
db.ref("role").withSchema(TableName.MembershipRole).as("membershipRole"),
|
||||||
db.ref("temporaryMode").withSchema(TableName.MembershipRole).as("membershipRoleTemporaryMode"),
|
db.ref("temporaryMode").withSchema(TableName.MembershipRole).as("membershipRoleTemporaryMode"),
|
||||||
@@ -203,7 +227,12 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
.withSchema(TableName.MembershipRole)
|
.withSchema(TableName.MembershipRole)
|
||||||
.as("membershipRoleTemporaryAccessEndTime"),
|
.as("membershipRoleTemporaryAccessEndTime"),
|
||||||
db.ref("createdAt").withSchema(TableName.MembershipRole).as("membershipRoleCreatedAt"),
|
db.ref("createdAt").withSchema(TableName.MembershipRole).as("membershipRoleCreatedAt"),
|
||||||
db.ref("updatedAt").withSchema(TableName.MembershipRole).as("membershipRoleUpdatedAt")
|
db.ref("updatedAt").withSchema(TableName.MembershipRole).as("membershipRoleUpdatedAt"),
|
||||||
|
db.ref("username").withSchema(TableName.Users).as("userUsername"),
|
||||||
|
db.ref("email").withSchema(TableName.Users).as("userEmail"),
|
||||||
|
db.ref("firstName").withSchema(TableName.Users).as("userFirstName"),
|
||||||
|
db.ref("lastName").withSchema(TableName.Users).as("userLastName"),
|
||||||
|
db.ref("id").withSchema(TableName.Users).as("userId")
|
||||||
)
|
)
|
||||||
.select(
|
.select(
|
||||||
db.raw(
|
db.raw(
|
||||||
@@ -214,13 +243,24 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
const data = sqlNestRelationships({
|
const data = sqlNestRelationships({
|
||||||
data: docs,
|
data: docs,
|
||||||
key: "id",
|
key: "id",
|
||||||
parentMapper: (el) => MembershipsSchema.parse(el),
|
parentMapper: (el) => ({
|
||||||
|
...MembershipsSchema.parse(el),
|
||||||
|
user: {
|
||||||
|
username: el.userUsername,
|
||||||
|
email: el.userEmail,
|
||||||
|
firstName: el.userFirstName,
|
||||||
|
lastName: el.userLastName,
|
||||||
|
id: el.userId
|
||||||
|
}
|
||||||
|
}),
|
||||||
childrenMapper: [
|
childrenMapper: [
|
||||||
{
|
{
|
||||||
key: "membershipRoleId",
|
key: "membershipRoleId",
|
||||||
label: "roles" as const,
|
label: "roles" as const,
|
||||||
mapper: ({
|
mapper: ({
|
||||||
roleSlug,
|
customRoleSlug,
|
||||||
|
customRoleName,
|
||||||
|
customRoleId,
|
||||||
membershipRoleId,
|
membershipRoleId,
|
||||||
membershipRole,
|
membershipRole,
|
||||||
membershipRoleIsTemporary,
|
membershipRoleIsTemporary,
|
||||||
@@ -233,7 +273,9 @@ export const membershipUserDALFactory = (db: TDbClient) => {
|
|||||||
}) => ({
|
}) => ({
|
||||||
id: membershipRoleId,
|
id: membershipRoleId,
|
||||||
role: membershipRole,
|
role: membershipRole,
|
||||||
customRoleSlug: roleSlug,
|
customRoleSlug,
|
||||||
|
customRoleName,
|
||||||
|
customRoleId,
|
||||||
temporaryRange: membershipRoleTemporaryRange,
|
temporaryRange: membershipRoleTemporaryRange,
|
||||||
temporaryMode: membershipRoleTemporaryMode,
|
temporaryMode: membershipRoleTemporaryMode,
|
||||||
temporaryAccessStartTime: membershipRoleTemporaryAccessStartTime,
|
temporaryAccessStartTime: membershipRoleTemporaryAccessStartTime,
|
||||||
|
|||||||
@@ -386,7 +386,7 @@ export const membershipUserServiceFactory = ({
|
|||||||
limit: dto.data.limit,
|
limit: dto.data.limit,
|
||||||
offset: dto.data.offset,
|
offset: dto.data.offset,
|
||||||
username: dto.data.username,
|
username: dto.data.username,
|
||||||
role: dto.data.roles.length
|
role: dto.data?.roles?.length
|
||||||
? {
|
? {
|
||||||
[SearchResourceOperators.$in]: dto.data.roles
|
[SearchResourceOperators.$in]: dto.data.roles
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -55,14 +55,11 @@ export type TUpdateMembershipUserDTO = {
|
|||||||
export type TListMembershipUserDTO = {
|
export type TListMembershipUserDTO = {
|
||||||
permission: OrgServiceActor;
|
permission: OrgServiceActor;
|
||||||
scopeData: AccessScopeData;
|
scopeData: AccessScopeData;
|
||||||
selector: {
|
|
||||||
actorId: string;
|
|
||||||
};
|
|
||||||
data: {
|
data: {
|
||||||
limit?: number;
|
limit?: number;
|
||||||
offset?: number;
|
offset?: number;
|
||||||
username?: string;
|
username?: string;
|
||||||
roles: string[];
|
roles?: string[];
|
||||||
};
|
};
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -43,10 +43,7 @@ import {
|
|||||||
import { TProjectUserMembershipRoleDALFactory } from "./project-user-membership-role-dal";
|
import { TProjectUserMembershipRoleDALFactory } from "./project-user-membership-role-dal";
|
||||||
|
|
||||||
type TProjectMembershipServiceFactoryDep = {
|
type TProjectMembershipServiceFactoryDep = {
|
||||||
permissionService: Pick<
|
permissionService: Pick<TPermissionServiceFactory, "getProjectPermission" | "getProjectPermissionByRoles"| "invalidateProjectPermissionCache">;
|
||||||
TPermissionServiceFactory,
|
|
||||||
"getProjectPermission" | "getProjectPermissionByRole" | "invalidateProjectPermissionCache"
|
|
||||||
>;
|
|
||||||
smtpService: TSmtpService;
|
smtpService: TSmtpService;
|
||||||
projectBotDAL: TProjectBotDALFactory;
|
projectBotDAL: TProjectBotDALFactory;
|
||||||
projectMembershipDAL: TProjectMembershipDALFactory;
|
projectMembershipDAL: TProjectMembershipDALFactory;
|
||||||
@@ -573,6 +570,8 @@ export const projectMembershipServiceFactory = ({
|
|||||||
tx
|
tx
|
||||||
);
|
);
|
||||||
|
|
||||||
|
// TODO(simp): likewise check in all services if i am missing anything
|
||||||
|
// Deletion should handle all cleanups like wise
|
||||||
await secretReminderRecipientsDAL.delete(
|
await secretReminderRecipientsDAL.delete(
|
||||||
{
|
{
|
||||||
projectId,
|
projectId,
|
||||||
|
|||||||
@@ -2,6 +2,7 @@ import { AccessScope, TableName } from "@app/db/schemas";
|
|||||||
import { TPermissionServiceFactory } from "@app/ee/services/permission/permission-service-types";
|
import { TPermissionServiceFactory } from "@app/ee/services/permission/permission-service-types";
|
||||||
import { BadRequestError, NotFoundError } from "@app/lib/errors";
|
import { BadRequestError, NotFoundError } from "@app/lib/errors";
|
||||||
import { validateHandlebarTemplate } from "@app/lib/template/validate-handlebars";
|
import { validateHandlebarTemplate } from "@app/lib/template/validate-handlebars";
|
||||||
|
import { unpackPermissions } from "@app/server/routes/sanitizedSchema/permission";
|
||||||
|
|
||||||
import { newNamespaceRoleFactory } from "./namespace/namespace-role-factory";
|
import { newNamespaceRoleFactory } from "./namespace/namespace-role-factory";
|
||||||
import { newOrgRoleFactory } from "./org/org-role-factory";
|
import { newOrgRoleFactory } from "./org/org-role-factory";
|
||||||
@@ -63,7 +64,7 @@ export const roleServiceFactory = ({ roleDAL, permissionService }: TRoleServiceF
|
|||||||
[scope.key]: scope.value
|
[scope.key]: scope.value
|
||||||
});
|
});
|
||||||
|
|
||||||
return { ...role, [scope.key]: scope.value };
|
return { ...role, [scope.key]: scope.value, permissions: unpackPermissions(role.permissions) };
|
||||||
};
|
};
|
||||||
|
|
||||||
const updateRole = async (dto: TUpdateRoleDTO) => {
|
const updateRole = async (dto: TUpdateRoleDTO) => {
|
||||||
@@ -99,7 +100,7 @@ export const roleServiceFactory = ({ roleDAL, permissionService }: TRoleServiceF
|
|||||||
permissions: data?.permissions
|
permissions: data?.permissions
|
||||||
});
|
});
|
||||||
|
|
||||||
return { ...role, [scope.key]: scope.value };
|
return { ...role, [scope.key]: scope.value, permissions: unpackPermissions(role.permissions) };
|
||||||
};
|
};
|
||||||
|
|
||||||
const deleteRole = async (dto: TDeleteRoleDTO) => {
|
const deleteRole = async (dto: TDeleteRoleDTO) => {
|
||||||
@@ -119,7 +120,7 @@ export const roleServiceFactory = ({ roleDAL, permissionService }: TRoleServiceF
|
|||||||
[scope.key]: scope.value
|
[scope.key]: scope.value
|
||||||
});
|
});
|
||||||
|
|
||||||
return { ...role, [scope.key]: scope.value };
|
return { ...role, [scope.key]: scope.value, permissions: unpackPermissions(role.permissions) };
|
||||||
};
|
};
|
||||||
|
|
||||||
const listRoles = async (dto: TListRoleDTO) => {
|
const listRoles = async (dto: TListRoleDTO) => {
|
||||||
@@ -136,7 +137,7 @@ export const roleServiceFactory = ({ roleDAL, permissionService }: TRoleServiceF
|
|||||||
{ limit: dto.data.limit, offset: dto.data.offset, sort: [[`${TableName.Role}.slug` as "slug", "asc"]] }
|
{ limit: dto.data.limit, offset: dto.data.offset, sort: [[`${TableName.Role}.slug` as "slug", "asc"]] }
|
||||||
);
|
);
|
||||||
|
|
||||||
return { roles };
|
return { roles: roles.map((el) => ({ ...el, permissions: unpackPermissions(el.permissions) })) };
|
||||||
};
|
};
|
||||||
|
|
||||||
const getRoleById = async (dto: TGetRoleByIdDTO) => {
|
const getRoleById = async (dto: TGetRoleByIdDTO) => {
|
||||||
@@ -152,7 +153,7 @@ export const roleServiceFactory = ({ roleDAL, permissionService }: TRoleServiceF
|
|||||||
});
|
});
|
||||||
if (!role) throw new NotFoundError({ message: `Role with id ${dto.selector.id} not found` });
|
if (!role) throw new NotFoundError({ message: `Role with id ${dto.selector.id} not found` });
|
||||||
|
|
||||||
return { ...role, [scope.key]: scope.value };
|
return { ...role, [scope.key]: scope.value, permissions: unpackPermissions(role.permissions) };
|
||||||
};
|
};
|
||||||
|
|
||||||
const getRoleBySlug = async (dto: TGetRoleBySlugDTO) => {
|
const getRoleBySlug = async (dto: TGetRoleBySlugDTO) => {
|
||||||
@@ -168,7 +169,7 @@ export const roleServiceFactory = ({ roleDAL, permissionService }: TRoleServiceF
|
|||||||
});
|
});
|
||||||
if (!role) throw new NotFoundError({ message: `Role with slug ${dto.selector.slug} not found` });
|
if (!role) throw new NotFoundError({ message: `Role with slug ${dto.selector.slug} not found` });
|
||||||
|
|
||||||
return { ...role, [scope.key]: scope.value };
|
return { ...role, [scope.key]: scope.value, permissions: unpackPermissions(role.permissions) };
|
||||||
};
|
};
|
||||||
|
|
||||||
return {
|
return {
|
||||||
|
|||||||
@@ -16,7 +16,7 @@ export type TCreateRoleDTO = {
|
|||||||
scopeData: AccessScopeData;
|
scopeData: AccessScopeData;
|
||||||
data: {
|
data: {
|
||||||
name: string;
|
name: string;
|
||||||
description?: string;
|
description?: string | null;
|
||||||
slug: string;
|
slug: string;
|
||||||
permissions: unknown;
|
permissions: unknown;
|
||||||
};
|
};
|
||||||
@@ -30,7 +30,7 @@ export type TUpdateRoleDTO = {
|
|||||||
};
|
};
|
||||||
data: Partial<{
|
data: Partial<{
|
||||||
name: string;
|
name: string;
|
||||||
description?: string;
|
description?: string | null;
|
||||||
slug: string;
|
slug: string;
|
||||||
permissions: unknown;
|
permissions: unknown;
|
||||||
}>;
|
}>;
|
||||||
|
|||||||
@@ -76,6 +76,7 @@ export const useCreateOrgRole = () => {
|
|||||||
data: { role }
|
data: { role }
|
||||||
} = await apiRequest.post(`/api/v1/organization/${orgId}/roles`, {
|
} = await apiRequest.post(`/api/v1/organization/${orgId}/roles`, {
|
||||||
...dto,
|
...dto,
|
||||||
|
// TODO(simp): removing packing
|
||||||
permissions: permissions.length ? packRules(permissions) : []
|
permissions: permissions.length ? packRules(permissions) : []
|
||||||
});
|
});
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user