@carlonicora/nestjs-neo4jsonapi 6.6.2 → 6.8.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agents/operator/controllers/operator.controller.d.ts.map +1 -1
- package/dist/agents/operator/controllers/operator.controller.js +3 -0
- package/dist/agents/operator/controllers/operator.controller.js.map +1 -1
- package/dist/bootstrap/app.module.factory.d.ts.map +1 -1
- package/dist/bootstrap/app.module.factory.js +10 -0
- package/dist/bootstrap/app.module.factory.js.map +1 -1
- package/dist/bootstrap/bootstrap.options.d.ts +34 -0
- package/dist/bootstrap/bootstrap.options.d.ts.map +1 -1
- package/dist/common/constants/core-module.ids.d.ts +40 -0
- package/dist/common/constants/core-module.ids.d.ts.map +1 -0
- package/dist/common/constants/core-module.ids.js +42 -0
- package/dist/common/constants/core-module.ids.js.map +1 -0
- package/dist/common/decorators/module.decorator.d.ts +19 -0
- package/dist/common/decorators/module.decorator.d.ts.map +1 -1
- package/dist/common/decorators/module.decorator.js +8 -2
- package/dist/common/decorators/module.decorator.js.map +1 -1
- package/dist/common/guards/jwt.auth.admin.guard.d.ts +3 -1
- package/dist/common/guards/jwt.auth.admin.guard.d.ts.map +1 -1
- package/dist/common/guards/jwt.auth.admin.guard.js +8 -2
- package/dist/common/guards/jwt.auth.admin.guard.js.map +1 -1
- package/dist/common/guards/jwt.auth.guard.d.ts +3 -1
- package/dist/common/guards/jwt.auth.guard.d.ts.map +1 -1
- package/dist/common/guards/jwt.auth.guard.js +8 -2
- package/dist/common/guards/jwt.auth.guard.js.map +1 -1
- package/dist/common/guards/jwt.auth.optional.guard.d.ts +3 -1
- package/dist/common/guards/jwt.auth.optional.guard.d.ts.map +1 -1
- package/dist/common/guards/jwt.auth.optional.guard.js +12 -3
- package/dist/common/guards/jwt.auth.optional.guard.js.map +1 -1
- package/dist/common/index.d.ts +1 -0
- package/dist/common/index.d.ts.map +1 -1
- package/dist/common/index.js +1 -0
- package/dist/common/index.js.map +1 -1
- package/dist/config/enums/queue.id.d.ts +1 -0
- package/dist/config/enums/queue.id.d.ts.map +1 -1
- package/dist/config/enums/queue.id.js +1 -0
- package/dist/config/enums/queue.id.js.map +1 -1
- package/dist/core/blocknote/services/blocknote.service.d.ts +25 -0
- package/dist/core/blocknote/services/blocknote.service.d.ts.map +1 -1
- package/dist/core/blocknote/services/blocknote.service.js +84 -0
- package/dist/core/blocknote/services/blocknote.service.js.map +1 -1
- package/dist/foundations/ai-connection/controllers/ai-connection.controller.d.ts.map +1 -1
- package/dist/foundations/ai-connection/controllers/ai-connection.controller.js +4 -0
- package/dist/foundations/ai-connection/controllers/ai-connection.controller.js.map +1 -1
- package/dist/foundations/analytics/controllers/analytics.admin.controller.d.ts.map +1 -1
- package/dist/foundations/analytics/controllers/analytics.admin.controller.js +3 -0
- package/dist/foundations/analytics/controllers/analytics.admin.controller.js.map +1 -1
- package/dist/foundations/analytics/controllers/analytics.controller.d.ts.map +1 -1
- package/dist/foundations/analytics/controllers/analytics.controller.js +3 -0
- package/dist/foundations/analytics/controllers/analytics.controller.js.map +1 -1
- package/dist/foundations/assistant/controllers/assistant.controller.d.ts.map +1 -1
- package/dist/foundations/assistant/controllers/assistant.controller.js +3 -0
- package/dist/foundations/assistant/controllers/assistant.controller.js.map +1 -1
- package/dist/foundations/assistant-action/controllers/assistant-action.controller.d.ts.map +1 -1
- package/dist/foundations/assistant-action/controllers/assistant-action.controller.js +3 -0
- package/dist/foundations/assistant-action/controllers/assistant-action.controller.js.map +1 -1
- package/dist/foundations/assistant-message/controllers/assistant-message.controller.d.ts.map +1 -1
- package/dist/foundations/assistant-message/controllers/assistant-message.controller.js +3 -0
- package/dist/foundations/assistant-message/controllers/assistant-message.controller.js.map +1 -1
- package/dist/foundations/audit/controllers/audit.controller.d.ts.map +1 -1
- package/dist/foundations/audit/controllers/audit.controller.js +3 -0
- package/dist/foundations/audit/controllers/audit.controller.js.map +1 -1
- package/dist/foundations/auth/controllers/auth.controller.d.ts.map +1 -1
- package/dist/foundations/auth/controllers/auth.controller.js +3 -0
- package/dist/foundations/auth/controllers/auth.controller.js.map +1 -1
- package/dist/foundations/blog/blog.constants.d.ts +17 -0
- package/dist/foundations/blog/blog.constants.d.ts.map +1 -0
- package/dist/foundations/blog/blog.constants.js +17 -0
- package/dist/foundations/blog/blog.constants.js.map +1 -0
- package/dist/foundations/blog/blog.module.d.ts +28 -0
- package/dist/foundations/blog/blog.module.d.ts.map +1 -0
- package/dist/foundations/blog/blog.module.js +143 -0
- package/dist/foundations/blog/blog.module.js.map +1 -0
- package/dist/foundations/blog/controllers/blog-category-translation.controller.d.ts +17 -0
- package/dist/foundations/blog/controllers/blog-category-translation.controller.d.ts.map +1 -0
- package/dist/foundations/blog/controllers/blog-category-translation.controller.js +81 -0
- package/dist/foundations/blog/controllers/blog-category-translation.controller.js.map +1 -0
- package/dist/foundations/blog/controllers/blog-category.controller.d.ts +24 -0
- package/dist/foundations/blog/controllers/blog-category.controller.d.ts.map +1 -0
- package/dist/foundations/blog/controllers/blog-category.controller.js +125 -0
- package/dist/foundations/blog/controllers/blog-category.controller.js.map +1 -0
- package/dist/foundations/blog/controllers/blog-post-translation.controller.d.ts +17 -0
- package/dist/foundations/blog/controllers/blog-post-translation.controller.d.ts.map +1 -0
- package/dist/foundations/blog/controllers/blog-post-translation.controller.js +81 -0
- package/dist/foundations/blog/controllers/blog-post-translation.controller.js.map +1 -0
- package/dist/foundations/blog/controllers/blog-post.controller.d.ts +28 -0
- package/dist/foundations/blog/controllers/blog-post.controller.d.ts.map +1 -0
- package/dist/foundations/blog/controllers/blog-post.controller.js +157 -0
- package/dist/foundations/blog/controllers/blog-post.controller.js.map +1 -0
- package/dist/foundations/blog/controllers/blog-settings.controller.d.ts +16 -0
- package/dist/foundations/blog/controllers/blog-settings.controller.d.ts.map +1 -0
- package/dist/foundations/blog/controllers/blog-settings.controller.js +73 -0
- package/dist/foundations/blog/controllers/blog-settings.controller.js.map +1 -0
- package/dist/foundations/blog/controllers/blog.public.controller.d.ts +26 -0
- package/dist/foundations/blog/controllers/blog.public.controller.d.ts.map +1 -0
- package/dist/foundations/blog/controllers/blog.public.controller.js +117 -0
- package/dist/foundations/blog/controllers/blog.public.controller.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-category-translation.put.dto.d.ts +16 -0
- package/dist/foundations/blog/dtos/blog-category-translation.put.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-category-translation.put.dto.js +62 -0
- package/dist/foundations/blog/dtos/blog-category-translation.put.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-category.dto.d.ts +11 -0
- package/dist/foundations/blog/dtos/blog-category.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-category.dto.js +45 -0
- package/dist/foundations/blog/dtos/blog-category.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-category.post.dto.d.ts +16 -0
- package/dist/foundations/blog/dtos/blog-category.post.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-category.post.dto.js +68 -0
- package/dist/foundations/blog/dtos/blog-category.post.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-category.put.dto.d.ts +21 -0
- package/dist/foundations/blog/dtos/blog-category.put.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-category.put.dto.js +76 -0
- package/dist/foundations/blog/dtos/blog-category.put.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-post-translation.put.dto.d.ts +19 -0
- package/dist/foundations/blog/dtos/blog-post-translation.put.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-post-translation.put.dto.js +73 -0
- package/dist/foundations/blog/dtos/blog-post-translation.put.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-post.dto.d.ts +11 -0
- package/dist/foundations/blog/dtos/blog-post.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-post.dto.js +45 -0
- package/dist/foundations/blog/dtos/blog-post.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-post.post.dto.d.ts +27 -0
- package/dist/foundations/blog/dtos/blog-post.post.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-post.post.dto.js +98 -0
- package/dist/foundations/blog/dtos/blog-post.post.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-post.put.dto.d.ts +30 -0
- package/dist/foundations/blog/dtos/blog-post.put.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-post.put.dto.js +104 -0
- package/dist/foundations/blog/dtos/blog-post.put.dto.js.map +1 -0
- package/dist/foundations/blog/dtos/blog-settings.put.dto.d.ts +14 -0
- package/dist/foundations/blog/dtos/blog-settings.put.dto.d.ts.map +1 -0
- package/dist/foundations/blog/dtos/blog-settings.put.dto.js +52 -0
- package/dist/foundations/blog/dtos/blog-settings.put.dto.js.map +1 -0
- package/dist/foundations/blog/entities/blog-category-translation.d.ts +36 -0
- package/dist/foundations/blog/entities/blog-category-translation.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-category-translation.js +70 -0
- package/dist/foundations/blog/entities/blog-category-translation.js.map +1 -0
- package/dist/foundations/blog/entities/blog-category-translation.meta.d.ts +3 -0
- package/dist/foundations/blog/entities/blog-category-translation.meta.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-category-translation.meta.js +10 -0
- package/dist/foundations/blog/entities/blog-category-translation.meta.js.map +1 -0
- package/dist/foundations/blog/entities/blog-category.d.ts +35 -0
- package/dist/foundations/blog/entities/blog-category.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-category.js +78 -0
- package/dist/foundations/blog/entities/blog-category.js.map +1 -0
- package/dist/foundations/blog/entities/blog-category.meta.d.ts +3 -0
- package/dist/foundations/blog/entities/blog-category.meta.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-category.meta.js +10 -0
- package/dist/foundations/blog/entities/blog-category.meta.js.map +1 -0
- package/dist/foundations/blog/entities/blog-post-translation.d.ts +43 -0
- package/dist/foundations/blog/entities/blog-post-translation.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-post-translation.js +91 -0
- package/dist/foundations/blog/entities/blog-post-translation.js.map +1 -0
- package/dist/foundations/blog/entities/blog-post-translation.meta.d.ts +3 -0
- package/dist/foundations/blog/entities/blog-post-translation.meta.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-post-translation.meta.js +10 -0
- package/dist/foundations/blog/entities/blog-post-translation.meta.js.map +1 -0
- package/dist/foundations/blog/entities/blog-post.d.ts +63 -0
- package/dist/foundations/blog/entities/blog-post.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-post.js +149 -0
- package/dist/foundations/blog/entities/blog-post.js.map +1 -0
- package/dist/foundations/blog/entities/blog-post.meta.d.ts +3 -0
- package/dist/foundations/blog/entities/blog-post.meta.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-post.meta.js +10 -0
- package/dist/foundations/blog/entities/blog-post.meta.js.map +1 -0
- package/dist/foundations/blog/entities/blog-settings.d.ts +18 -0
- package/dist/foundations/blog/entities/blog-settings.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-settings.js +26 -0
- package/dist/foundations/blog/entities/blog-settings.js.map +1 -0
- package/dist/foundations/blog/entities/blog-settings.meta.d.ts +3 -0
- package/dist/foundations/blog/entities/blog-settings.meta.d.ts.map +1 -0
- package/dist/foundations/blog/entities/blog-settings.meta.js +10 -0
- package/dist/foundations/blog/entities/blog-settings.meta.js.map +1 -0
- package/dist/foundations/blog/index.d.ts +34 -0
- package/dist/foundations/blog/index.d.ts.map +1 -0
- package/dist/foundations/blog/index.js +50 -0
- package/dist/foundations/blog/index.js.map +1 -0
- package/dist/foundations/blog/interfaces/blog.config.interface.d.ts +22 -0
- package/dist/foundations/blog/interfaces/blog.config.interface.d.ts.map +1 -0
- package/dist/foundations/blog/interfaces/blog.config.interface.js +10 -0
- package/dist/foundations/blog/interfaces/blog.config.interface.js.map +1 -0
- package/dist/foundations/blog/processors/blog.processor.d.ts +77 -0
- package/dist/foundations/blog/processors/blog.processor.d.ts.map +1 -0
- package/dist/foundations/blog/processors/blog.processor.js +404 -0
- package/dist/foundations/blog/processors/blog.processor.js.map +1 -0
- package/dist/foundations/blog/prompts/blog-summary.prompt.d.ts +6 -0
- package/dist/foundations/blog/prompts/blog-summary.prompt.d.ts.map +1 -0
- package/dist/foundations/blog/prompts/blog-summary.prompt.js +19 -0
- package/dist/foundations/blog/prompts/blog-summary.prompt.js.map +1 -0
- package/dist/foundations/blog/prompts/blog-translate.prompt.d.ts +7 -0
- package/dist/foundations/blog/prompts/blog-translate.prompt.d.ts.map +1 -0
- package/dist/foundations/blog/prompts/blog-translate.prompt.js +24 -0
- package/dist/foundations/blog/prompts/blog-translate.prompt.js.map +1 -0
- package/dist/foundations/blog/repositories/blog-category-translation.repository.d.ts +78 -0
- package/dist/foundations/blog/repositories/blog-category-translation.repository.d.ts.map +1 -0
- package/dist/foundations/blog/repositories/blog-category-translation.repository.js +199 -0
- package/dist/foundations/blog/repositories/blog-category-translation.repository.js.map +1 -0
- package/dist/foundations/blog/repositories/blog-category.repository.d.ts +56 -0
- package/dist/foundations/blog/repositories/blog-category.repository.d.ts.map +1 -0
- package/dist/foundations/blog/repositories/blog-category.repository.js +166 -0
- package/dist/foundations/blog/repositories/blog-category.repository.js.map +1 -0
- package/dist/foundations/blog/repositories/blog-post-translation.repository.d.ts +88 -0
- package/dist/foundations/blog/repositories/blog-post-translation.repository.d.ts.map +1 -0
- package/dist/foundations/blog/repositories/blog-post-translation.repository.js +220 -0
- package/dist/foundations/blog/repositories/blog-post-translation.repository.js.map +1 -0
- package/dist/foundations/blog/repositories/blog-post.repository.d.ts +118 -0
- package/dist/foundations/blog/repositories/blog-post.repository.d.ts.map +1 -0
- package/dist/foundations/blog/repositories/blog-post.repository.js +350 -0
- package/dist/foundations/blog/repositories/blog-post.repository.js.map +1 -0
- package/dist/foundations/blog/repositories/blog-settings.repository.d.ts +21 -0
- package/dist/foundations/blog/repositories/blog-settings.repository.d.ts.map +1 -0
- package/dist/foundations/blog/repositories/blog-settings.repository.js +60 -0
- package/dist/foundations/blog/repositories/blog-settings.repository.js.map +1 -0
- package/dist/foundations/blog/services/blog-category-translation.service.d.ts +37 -0
- package/dist/foundations/blog/services/blog-category-translation.service.d.ts.map +1 -0
- package/dist/foundations/blog/services/blog-category-translation.service.js +97 -0
- package/dist/foundations/blog/services/blog-category-translation.service.js.map +1 -0
- package/dist/foundations/blog/services/blog-category.service.d.ts +56 -0
- package/dist/foundations/blog/services/blog-category.service.d.ts.map +1 -0
- package/dist/foundations/blog/services/blog-category.service.js +164 -0
- package/dist/foundations/blog/services/blog-category.service.js.map +1 -0
- package/dist/foundations/blog/services/blog-post-translation.service.d.ts +44 -0
- package/dist/foundations/blog/services/blog-post-translation.service.d.ts.map +1 -0
- package/dist/foundations/blog/services/blog-post-translation.service.js +115 -0
- package/dist/foundations/blog/services/blog-post-translation.service.js.map +1 -0
- package/dist/foundations/blog/services/blog-post.service.d.ts +109 -0
- package/dist/foundations/blog/services/blog-post.service.d.ts.map +1 -0
- package/dist/foundations/blog/services/blog-post.service.js +276 -0
- package/dist/foundations/blog/services/blog-post.service.js.map +1 -0
- package/dist/foundations/blog/services/blog-queue.service.d.ts +36 -0
- package/dist/foundations/blog/services/blog-queue.service.d.ts.map +1 -0
- package/dist/foundations/blog/services/blog-queue.service.js +79 -0
- package/dist/foundations/blog/services/blog-queue.service.js.map +1 -0
- package/dist/foundations/blog/services/blog-settings.service.d.ts +21 -0
- package/dist/foundations/blog/services/blog-settings.service.d.ts.map +1 -0
- package/dist/foundations/blog/services/blog-settings.service.js +49 -0
- package/dist/foundations/blog/services/blog-settings.service.js.map +1 -0
- package/dist/foundations/blog/utils/reading-time.d.ts +5 -0
- package/dist/foundations/blog/utils/reading-time.d.ts.map +1 -0
- package/dist/foundations/blog/utils/reading-time.js +12 -0
- package/dist/foundations/blog/utils/reading-time.js.map +1 -0
- package/dist/foundations/blog/utils/slug.d.ts +12 -0
- package/dist/foundations/blog/utils/slug.d.ts.map +1 -0
- package/dist/foundations/blog/utils/slug.js +36 -0
- package/dist/foundations/blog/utils/slug.js.map +1 -0
- package/dist/foundations/chunk/controllers/chunk.controller.d.ts.map +1 -1
- package/dist/foundations/chunk/controllers/chunk.controller.js +3 -0
- package/dist/foundations/chunk/controllers/chunk.controller.js.map +1 -1
- package/dist/foundations/company/controllers/company.controller.d.ts.map +1 -1
- package/dist/foundations/company/controllers/company.controller.js +3 -0
- package/dist/foundations/company/controllers/company.controller.js.map +1 -1
- package/dist/foundations/content/controllers/content.controller.d.ts.map +1 -1
- package/dist/foundations/content/controllers/content.controller.js +3 -0
- package/dist/foundations/content/controllers/content.controller.js.map +1 -1
- package/dist/foundations/email-automation/controllers/email-automation-step.controller.d.ts.map +1 -1
- package/dist/foundations/email-automation/controllers/email-automation-step.controller.js +3 -0
- package/dist/foundations/email-automation/controllers/email-automation-step.controller.js.map +1 -1
- package/dist/foundations/email-automation/controllers/email-automation.controller.d.ts.map +1 -1
- package/dist/foundations/email-automation/controllers/email-automation.controller.js +3 -0
- package/dist/foundations/email-automation/controllers/email-automation.controller.js.map +1 -1
- package/dist/foundations/feature/controllers/feature.controller.d.ts.map +1 -1
- package/dist/foundations/feature/controllers/feature.controller.js +3 -0
- package/dist/foundations/feature/controllers/feature.controller.js.map +1 -1
- package/dist/foundations/foundations.modules.d.ts +8 -0
- package/dist/foundations/foundations.modules.d.ts.map +1 -1
- package/dist/foundations/foundations.modules.js +4 -1
- package/dist/foundations/foundations.modules.js.map +1 -1
- package/dist/foundations/handbook/controllers/handbook-thread.controller.d.ts.map +1 -1
- package/dist/foundations/handbook/controllers/handbook-thread.controller.js +3 -0
- package/dist/foundations/handbook/controllers/handbook-thread.controller.js.map +1 -1
- package/dist/foundations/handbook/controllers/handbook.controller.d.ts.map +1 -1
- package/dist/foundations/handbook/controllers/handbook.controller.js +3 -0
- package/dist/foundations/handbook/controllers/handbook.controller.js.map +1 -1
- package/dist/foundations/how-to/controllers/how-to.controller.d.ts.map +1 -1
- package/dist/foundations/how-to/controllers/how-to.controller.js +3 -0
- package/dist/foundations/how-to/controllers/how-to.controller.js.map +1 -1
- package/dist/foundations/index.d.ts +1 -0
- package/dist/foundations/index.d.ts.map +1 -1
- package/dist/foundations/index.js +1 -0
- package/dist/foundations/index.js.map +1 -1
- package/dist/foundations/keyconcept/controllers/keyconcept.controller.d.ts.map +1 -1
- package/dist/foundations/keyconcept/controllers/keyconcept.controller.js +3 -0
- package/dist/foundations/keyconcept/controllers/keyconcept.controller.js.map +1 -1
- package/dist/foundations/notification/controllers/notification.controller.d.ts.map +1 -1
- package/dist/foundations/notification/controllers/notification.controller.js +4 -0
- package/dist/foundations/notification/controllers/notification.controller.js.map +1 -1
- package/dist/foundations/oauth/controllers/oauth.authorize.controller.d.ts.map +1 -1
- package/dist/foundations/oauth/controllers/oauth.authorize.controller.js +4 -0
- package/dist/foundations/oauth/controllers/oauth.authorize.controller.js.map +1 -1
- package/dist/foundations/oauth/controllers/oauth.management.controller.d.ts.map +1 -1
- package/dist/foundations/oauth/controllers/oauth.management.controller.js +3 -0
- package/dist/foundations/oauth/controllers/oauth.management.controller.js.map +1 -1
- package/dist/foundations/push/controllers/push.controller.d.ts.map +1 -1
- package/dist/foundations/push/controllers/push.controller.js +3 -0
- package/dist/foundations/push/controllers/push.controller.js.map +1 -1
- package/dist/foundations/rbac/controllers/rbac-dev.controller.d.ts.map +1 -1
- package/dist/foundations/rbac/controllers/rbac-dev.controller.js +3 -0
- package/dist/foundations/rbac/controllers/rbac-dev.controller.js.map +1 -1
- package/dist/foundations/rbac/controllers/rbac-module-paths.controller.d.ts.map +1 -1
- package/dist/foundations/rbac/controllers/rbac-module-paths.controller.js +3 -0
- package/dist/foundations/rbac/controllers/rbac-module-paths.controller.js.map +1 -1
- package/dist/foundations/rbac/controllers/rbac.controller.d.ts.map +1 -1
- package/dist/foundations/rbac/controllers/rbac.controller.js +3 -0
- package/dist/foundations/rbac/controllers/rbac.controller.js.map +1 -1
- package/dist/foundations/rbac/index.d.ts +5 -0
- package/dist/foundations/rbac/index.d.ts.map +1 -1
- package/dist/foundations/rbac/index.js +12 -1
- package/dist/foundations/rbac/index.js.map +1 -1
- package/dist/foundations/rbac/rbac-permission.module.d.ts +4 -0
- package/dist/foundations/rbac/rbac-permission.module.d.ts.map +1 -1
- package/dist/foundations/rbac/rbac-permission.module.js +18 -2
- package/dist/foundations/rbac/rbac-permission.module.js.map +1 -1
- package/dist/foundations/rbac/rbac.tokens.d.ts +8 -0
- package/dist/foundations/rbac/rbac.tokens.d.ts.map +1 -1
- package/dist/foundations/rbac/rbac.tokens.js +9 -1
- package/dist/foundations/rbac/rbac.tokens.js.map +1 -1
- package/dist/foundations/rbac/repositories/rbac-permission.repository.d.ts +29 -1
- package/dist/foundations/rbac/repositories/rbac-permission.repository.d.ts.map +1 -1
- package/dist/foundations/rbac/repositories/rbac-permission.repository.js +73 -1
- package/dist/foundations/rbac/repositories/rbac-permission.repository.js.map +1 -1
- package/dist/foundations/rbac/services/module-permission-audit.service.d.ts +34 -0
- package/dist/foundations/rbac/services/module-permission-audit.service.d.ts.map +1 -0
- package/dist/foundations/rbac/services/module-permission-audit.service.js +137 -0
- package/dist/foundations/rbac/services/module-permission-audit.service.js.map +1 -0
- package/dist/foundations/rbac/services/module-permission.gate.d.ts +51 -0
- package/dist/foundations/rbac/services/module-permission.gate.d.ts.map +1 -0
- package/dist/foundations/rbac/services/module-permission.gate.js +108 -0
- package/dist/foundations/rbac/services/module-permission.gate.js.map +1 -0
- package/dist/foundations/rbac/services/module-permission.service.d.ts +34 -0
- package/dist/foundations/rbac/services/module-permission.service.d.ts.map +1 -0
- package/dist/foundations/rbac/services/module-permission.service.js +64 -0
- package/dist/foundations/rbac/services/module-permission.service.js.map +1 -0
- package/dist/foundations/rbac/services/rbac-permission.service.d.ts +10 -1
- package/dist/foundations/rbac/services/rbac-permission.service.d.ts.map +1 -1
- package/dist/foundations/rbac/services/rbac-permission.service.js +32 -2
- package/dist/foundations/rbac/services/rbac-permission.service.js.map +1 -1
- package/dist/foundations/rbac/services/rbac-reconciler.service.d.ts +11 -2
- package/dist/foundations/rbac/services/rbac-reconciler.service.d.ts.map +1 -1
- package/dist/foundations/rbac/services/rbac-reconciler.service.js +19 -6
- package/dist/foundations/rbac/services/rbac-reconciler.service.js.map +1 -1
- package/dist/foundations/referral/controllers/referral.controller.d.ts.map +1 -1
- package/dist/foundations/referral/controllers/referral.controller.js +3 -0
- package/dist/foundations/referral/controllers/referral.controller.js.map +1 -1
- package/dist/foundations/role/controllers/role.controller.d.ts.map +1 -1
- package/dist/foundations/role/controllers/role.controller.js +3 -0
- package/dist/foundations/role/controllers/role.controller.js.map +1 -1
- package/dist/foundations/role/controllers/role.user.controller.d.ts.map +1 -1
- package/dist/foundations/role/controllers/role.user.controller.js +3 -0
- package/dist/foundations/role/controllers/role.user.controller.js.map +1 -1
- package/dist/foundations/s3/controllers/s3.controller.d.ts.map +1 -1
- package/dist/foundations/s3/controllers/s3.controller.js +3 -0
- package/dist/foundations/s3/controllers/s3.controller.js.map +1 -1
- package/dist/foundations/stripe/controllers/billing.controller.d.ts.map +1 -1
- package/dist/foundations/stripe/controllers/billing.controller.js +4 -0
- package/dist/foundations/stripe/controllers/billing.controller.js.map +1 -1
- package/dist/foundations/stripe-customer/controllers/stripe-customer.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-customer/controllers/stripe-customer.controller.js +3 -0
- package/dist/foundations/stripe-customer/controllers/stripe-customer.controller.js.map +1 -1
- package/dist/foundations/stripe-invoice/controllers/stripe-invoice.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-invoice/controllers/stripe-invoice.controller.js +3 -0
- package/dist/foundations/stripe-invoice/controllers/stripe-invoice.controller.js.map +1 -1
- package/dist/foundations/stripe-price/controllers/stripe-price.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-price/controllers/stripe-price.controller.js +3 -0
- package/dist/foundations/stripe-price/controllers/stripe-price.controller.js.map +1 -1
- package/dist/foundations/stripe-product/controllers/stripe-product.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-product/controllers/stripe-product.controller.js +3 -0
- package/dist/foundations/stripe-product/controllers/stripe-product.controller.js.map +1 -1
- package/dist/foundations/stripe-promotion-code/controllers/stripe-promotion-code.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-promotion-code/controllers/stripe-promotion-code.controller.js +4 -0
- package/dist/foundations/stripe-promotion-code/controllers/stripe-promotion-code.controller.js.map +1 -1
- package/dist/foundations/stripe-subscription/controllers/stripe-subscription.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-subscription/controllers/stripe-subscription.controller.js +3 -0
- package/dist/foundations/stripe-subscription/controllers/stripe-subscription.controller.js.map +1 -1
- package/dist/foundations/stripe-usage/controllers/stripe-usage.controller.d.ts.map +1 -1
- package/dist/foundations/stripe-usage/controllers/stripe-usage.controller.js +3 -0
- package/dist/foundations/stripe-usage/controllers/stripe-usage.controller.js.map +1 -1
- package/dist/foundations/tokenusage/controllers/tokenusage.admin.controller.d.ts.map +1 -1
- package/dist/foundations/tokenusage/controllers/tokenusage.admin.controller.js +3 -0
- package/dist/foundations/tokenusage/controllers/tokenusage.admin.controller.js.map +1 -1
- package/dist/foundations/tokenusage/controllers/tokenusage.report.controller.d.ts.map +1 -1
- package/dist/foundations/tokenusage/controllers/tokenusage.report.controller.js +3 -0
- package/dist/foundations/tokenusage/controllers/tokenusage.report.controller.js.map +1 -1
- package/dist/foundations/tokenusage/enums/tokenusage.type.d.ts +3 -1
- package/dist/foundations/tokenusage/enums/tokenusage.type.d.ts.map +1 -1
- package/dist/foundations/tokenusage/enums/tokenusage.type.js +2 -0
- package/dist/foundations/tokenusage/enums/tokenusage.type.js.map +1 -1
- package/dist/foundations/two-factor/controllers/passkey.controller.d.ts.map +1 -1
- package/dist/foundations/two-factor/controllers/passkey.controller.js +7 -0
- package/dist/foundations/two-factor/controllers/passkey.controller.js.map +1 -1
- package/dist/foundations/two-factor/controllers/totp.controller.d.ts.map +1 -1
- package/dist/foundations/two-factor/controllers/totp.controller.js +6 -0
- package/dist/foundations/two-factor/controllers/totp.controller.js.map +1 -1
- package/dist/foundations/two-factor/controllers/two-factor.controller.d.ts.map +1 -1
- package/dist/foundations/two-factor/controllers/two-factor.controller.js +7 -0
- package/dist/foundations/two-factor/controllers/two-factor.controller.js.map +1 -1
- package/dist/foundations/user/controllers/user.controller.d.ts.map +1 -1
- package/dist/foundations/user/controllers/user.controller.js +3 -0
- package/dist/foundations/user/controllers/user.controller.js.map +1 -1
- package/dist/foundations/waitlist/controllers/waitlist.controller.d.ts.map +1 -1
- package/dist/foundations/waitlist/controllers/waitlist.controller.js +3 -0
- package/dist/foundations/waitlist/controllers/waitlist.controller.js.map +1 -1
- package/package.json +1 -1
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { OnApplicationBootstrap } from "@nestjs/common";
|
|
2
|
+
import { DiscoveryService, MetadataScanner, Reflector } from "@nestjs/core";
|
|
3
|
+
import { RbacPermissionRepository } from "../repositories/rbac-permission.repository";
|
|
4
|
+
interface AuditedRoute {
|
|
5
|
+
label: string;
|
|
6
|
+
module: string | undefined;
|
|
7
|
+
isWrite: boolean;
|
|
8
|
+
}
|
|
9
|
+
/**
|
|
10
|
+
* Boot audit for the permission gate. Runs only when the app bootstraps with
|
|
11
|
+
* `permissions: { enforce: true }` (API and worker).
|
|
12
|
+
*
|
|
13
|
+
* Refuses to start when:
|
|
14
|
+
* - a route guarded by a session guard is a write (POST/PUT/PATCH/DELETE, or a
|
|
15
|
+
* `@ModuleACL` action that is a write) and has no section;
|
|
16
|
+
* - a section id referenced by any session-guarded route has no `(:Module)` node.
|
|
17
|
+
*
|
|
18
|
+
* This is what makes the gate fail closed for writes at startup instead of at
|
|
19
|
+
* request time.
|
|
20
|
+
*/
|
|
21
|
+
export declare class ModulePermissionAuditService implements OnApplicationBootstrap {
|
|
22
|
+
private readonly discovery;
|
|
23
|
+
private readonly metadataScanner;
|
|
24
|
+
private readonly reflector;
|
|
25
|
+
private readonly repository;
|
|
26
|
+
private readonly enforce?;
|
|
27
|
+
constructor(discovery: DiscoveryService, metadataScanner: MetadataScanner, reflector: Reflector, repository: RbacPermissionRepository, enforce?: boolean);
|
|
28
|
+
onApplicationBootstrap(): Promise<void>;
|
|
29
|
+
/** Every session-guarded route with its resolved section. Exposed for tests. */
|
|
30
|
+
collectRoutes(): AuditedRoute[];
|
|
31
|
+
audit(): Promise<void>;
|
|
32
|
+
}
|
|
33
|
+
export {};
|
|
34
|
+
//# sourceMappingURL=module-permission-audit.service.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"module-permission-audit.service.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/module-permission-audit.service.ts"],"names":[],"mappings":"AAAA,OAAO,EAAsB,sBAAsB,EAA2B,MAAM,gBAAgB,CAAC;AAErG,OAAO,EAAE,gBAAgB,EAAE,eAAe,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AAM5E,OAAO,EAAE,wBAAwB,EAAE,MAAM,4CAA4C,CAAC;AAatF,UAAU,YAAY;IACpB,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;IAC3B,OAAO,EAAE,OAAO,CAAC;CAClB;AAcD;;;;;;;;;;;GAWG;AACH,qBACa,4BAA6B,YAAW,sBAAsB;IAEvE,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,eAAe;IAChC,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,UAAU;IAG3B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAC;gBANR,SAAS,EAAE,gBAAgB,EAC3B,eAAe,EAAE,eAAe,EAChC,SAAS,EAAE,SAAS,EACpB,UAAU,EAAE,wBAAwB,EAGpC,OAAO,CAAC,EAAE,OAAO;IAG9B,sBAAsB,IAAI,OAAO,CAAC,IAAI,CAAC;IAK7C,gFAAgF;IAChF,aAAa,IAAI,YAAY,EAAE;IAyCzB,KAAK,IAAI,OAAO,CAAC,IAAI,CAAC;CA0B7B"}
|
|
@@ -0,0 +1,137 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
12
|
+
return function (target, key) { decorator(target, key, paramIndex); }
|
|
13
|
+
};
|
|
14
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
+
exports.ModulePermissionAuditService = void 0;
|
|
16
|
+
const common_1 = require("@nestjs/common");
|
|
17
|
+
const constants_1 = require("@nestjs/common/constants");
|
|
18
|
+
const core_1 = require("@nestjs/core");
|
|
19
|
+
const module_decorator_1 = require("../../../common/decorators/module.decorator");
|
|
20
|
+
const jwt_auth_admin_guard_1 = require("../../../common/guards/jwt.auth.admin.guard");
|
|
21
|
+
const jwt_auth_guard_1 = require("../../../common/guards/jwt.auth.guard");
|
|
22
|
+
const jwt_auth_optional_guard_1 = require("../../../common/guards/jwt.auth.optional.guard");
|
|
23
|
+
const rbac_permission_repository_1 = require("../repositories/rbac-permission.repository");
|
|
24
|
+
const rbac_tokens_1 = require("../rbac.tokens");
|
|
25
|
+
const module_permission_gate_1 = require("./module-permission.gate");
|
|
26
|
+
/** The guards that run `ModulePermissionGate`. Subclasses count too. */
|
|
27
|
+
const SESSION_GUARDS = [
|
|
28
|
+
jwt_auth_guard_1.JwtAuthGuard,
|
|
29
|
+
jwt_auth_admin_guard_1.AdminJwtAuthGuard,
|
|
30
|
+
jwt_auth_optional_guard_1.OptionalJwtAuthGuard,
|
|
31
|
+
];
|
|
32
|
+
const WRITE_ACTIONS = new Set(["create", "update", "delete"]);
|
|
33
|
+
function isSessionGuard(guard) {
|
|
34
|
+
const type = typeof guard === "function" ? guard : guard?.constructor;
|
|
35
|
+
if (typeof type !== "function")
|
|
36
|
+
return false;
|
|
37
|
+
return SESSION_GUARDS.some((g) => type === g || type.prototype instanceof g);
|
|
38
|
+
}
|
|
39
|
+
function joinPaths(prefix, path) {
|
|
40
|
+
const first = (value) => (Array.isArray(value) ? String(value[0] ?? "") : String(value ?? ""));
|
|
41
|
+
const parts = [first(prefix), first(path)].map((p) => p.replace(/^\/+|\/+$/g, "")).filter((p) => p.length);
|
|
42
|
+
return `/${parts.join("/")}`;
|
|
43
|
+
}
|
|
44
|
+
/**
|
|
45
|
+
* Boot audit for the permission gate. Runs only when the app bootstraps with
|
|
46
|
+
* `permissions: { enforce: true }` (API and worker).
|
|
47
|
+
*
|
|
48
|
+
* Refuses to start when:
|
|
49
|
+
* - a route guarded by a session guard is a write (POST/PUT/PATCH/DELETE, or a
|
|
50
|
+
* `@ModuleACL` action that is a write) and has no section;
|
|
51
|
+
* - a section id referenced by any session-guarded route has no `(:Module)` node.
|
|
52
|
+
*
|
|
53
|
+
* This is what makes the gate fail closed for writes at startup instead of at
|
|
54
|
+
* request time.
|
|
55
|
+
*/
|
|
56
|
+
let ModulePermissionAuditService = class ModulePermissionAuditService {
|
|
57
|
+
constructor(discovery, metadataScanner, reflector, repository, enforce) {
|
|
58
|
+
this.discovery = discovery;
|
|
59
|
+
this.metadataScanner = metadataScanner;
|
|
60
|
+
this.reflector = reflector;
|
|
61
|
+
this.repository = repository;
|
|
62
|
+
this.enforce = enforce;
|
|
63
|
+
}
|
|
64
|
+
async onApplicationBootstrap() {
|
|
65
|
+
if (this.enforce !== true)
|
|
66
|
+
return;
|
|
67
|
+
await this.audit();
|
|
68
|
+
}
|
|
69
|
+
/** Every session-guarded route with its resolved section. Exposed for tests. */
|
|
70
|
+
collectRoutes() {
|
|
71
|
+
const routes = [];
|
|
72
|
+
for (const wrapper of this.discovery.getControllers()) {
|
|
73
|
+
const controller = wrapper.metatype;
|
|
74
|
+
if (typeof controller !== "function" || !controller.prototype)
|
|
75
|
+
continue;
|
|
76
|
+
const prototype = controller.prototype;
|
|
77
|
+
const classGuards = this.reflector.get(constants_1.GUARDS_METADATA, controller) ?? [];
|
|
78
|
+
const classDefinition = this.reflector.get(module_decorator_1.MODULE_ACL_METADATA, controller);
|
|
79
|
+
const controllerPath = this.reflector.get(constants_1.PATH_METADATA, controller);
|
|
80
|
+
for (const methodName of this.metadataScanner.getAllMethodNames(prototype)) {
|
|
81
|
+
const handler = prototype[methodName];
|
|
82
|
+
if (typeof handler !== "function")
|
|
83
|
+
continue;
|
|
84
|
+
const requestMethod = this.reflector.get(constants_1.METHOD_METADATA, handler);
|
|
85
|
+
const routePath = this.reflector.get(constants_1.PATH_METADATA, handler);
|
|
86
|
+
if (requestMethod === undefined || routePath === undefined)
|
|
87
|
+
continue;
|
|
88
|
+
const handlerGuards = this.reflector.get(constants_1.GUARDS_METADATA, handler) ?? [];
|
|
89
|
+
if (![...classGuards, ...handlerGuards].some(isSessionGuard))
|
|
90
|
+
continue;
|
|
91
|
+
const method = common_1.RequestMethod[requestMethod] ?? String(requestMethod);
|
|
92
|
+
const { module, action } = (0, module_permission_gate_1.resolveRouteAcl)({
|
|
93
|
+
classDefinition,
|
|
94
|
+
handlerDefinition: this.reflector.get(module_decorator_1.MODULE_ACL_METADATA, handler),
|
|
95
|
+
method,
|
|
96
|
+
});
|
|
97
|
+
routes.push({
|
|
98
|
+
label: `${method} ${joinPaths(controllerPath, routePath)} (${controller.name}.${methodName})`,
|
|
99
|
+
module,
|
|
100
|
+
isWrite: WRITE_ACTIONS.has(action),
|
|
101
|
+
});
|
|
102
|
+
}
|
|
103
|
+
}
|
|
104
|
+
return routes;
|
|
105
|
+
}
|
|
106
|
+
async audit() {
|
|
107
|
+
const routes = this.collectRoutes();
|
|
108
|
+
const unsectioned = routes.filter((r) => r.isWrite && !r.module).map((r) => r.label);
|
|
109
|
+
if (unsectioned.length > 0) {
|
|
110
|
+
throw new Error(`Permission audit failed: ${unsectioned.length} session-guarded write route(s) have no @ModuleACL section:\n` +
|
|
111
|
+
unsectioned.map((label) => ` - ${label}`).join("\n"));
|
|
112
|
+
}
|
|
113
|
+
const referenced = Array.from(new Set(routes.map((r) => r.module).filter((m) => !!m))).sort();
|
|
114
|
+
const existing = await this.repository.findExistingModuleIds(referenced);
|
|
115
|
+
const missing = referenced.filter((id) => !existing.has(id));
|
|
116
|
+
if (missing.length > 0) {
|
|
117
|
+
const byModule = missing.map((id) => {
|
|
118
|
+
const example = routes.find((r) => r.module === id)?.label ?? "";
|
|
119
|
+
return ` - ${id} (e.g. ${example})`;
|
|
120
|
+
});
|
|
121
|
+
throw new Error(`Permission audit failed: ${missing.length} section id(s) referenced by @ModuleACL have no (:Module) node. ` +
|
|
122
|
+
`Seed them in a migration before switching permissions.enforce on:\n` +
|
|
123
|
+
byModule.join("\n"));
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
};
|
|
127
|
+
exports.ModulePermissionAuditService = ModulePermissionAuditService;
|
|
128
|
+
exports.ModulePermissionAuditService = ModulePermissionAuditService = __decorate([
|
|
129
|
+
(0, common_1.Injectable)(),
|
|
130
|
+
__param(4, (0, common_1.Optional)()),
|
|
131
|
+
__param(4, (0, common_1.Inject)(rbac_tokens_1.PERMISSIONS_ENFORCE)),
|
|
132
|
+
__metadata("design:paramtypes", [core_1.DiscoveryService,
|
|
133
|
+
core_1.MetadataScanner,
|
|
134
|
+
core_1.Reflector,
|
|
135
|
+
rbac_permission_repository_1.RbacPermissionRepository, Boolean])
|
|
136
|
+
], ModulePermissionAuditService);
|
|
137
|
+
//# sourceMappingURL=module-permission-audit.service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"module-permission-audit.service.js","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/module-permission-audit.service.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,51 @@
|
|
|
1
|
+
import { ExecutionContext } from "@nestjs/common";
|
|
2
|
+
import { Reflector } from "@nestjs/core";
|
|
3
|
+
import { ClsService } from "nestjs-cls";
|
|
4
|
+
import type { ModuleDefinition } from "../../../common/decorators/module.decorator";
|
|
5
|
+
import { ModulePermissionService } from "./module-permission.service";
|
|
6
|
+
import type { RbacAction } from "./rbac-permission.service";
|
|
7
|
+
/**
|
|
8
|
+
* HTTP method → permission action. GET/HEAD/OPTIONS read, POST create, PUT/PATCH
|
|
9
|
+
* update, DELETE delete. Anything else is treated as a write (update), so an
|
|
10
|
+
* unexpected verb never slips through as a read.
|
|
11
|
+
*/
|
|
12
|
+
export declare function rbacActionForHttpMethod(method: string | undefined): RbacAction;
|
|
13
|
+
/**
|
|
14
|
+
* Section and action of a route: the handler `@ModuleACL` wins over the class
|
|
15
|
+
* one, field by field; the action falls back to the HTTP-method mapping.
|
|
16
|
+
*/
|
|
17
|
+
export declare function resolveRouteAcl(params: {
|
|
18
|
+
classDefinition: ModuleDefinition | undefined;
|
|
19
|
+
handlerDefinition: ModuleDefinition | undefined;
|
|
20
|
+
method: string | undefined;
|
|
21
|
+
}): {
|
|
22
|
+
module: string | undefined;
|
|
23
|
+
action: RbacAction;
|
|
24
|
+
};
|
|
25
|
+
/**
|
|
26
|
+
* Request-level permission check, run by the session guards (`JwtAuthGuard`,
|
|
27
|
+
* `AdminJwtAuthGuard`, `OptionalJwtAuthGuard`) right after authentication.
|
|
28
|
+
*
|
|
29
|
+
* Off unless the app bootstraps with `permissions: { enforce: true }`: with it
|
|
30
|
+
* off, `assert` returns before reading metadata or touching the database.
|
|
31
|
+
*
|
|
32
|
+
* Rules:
|
|
33
|
+
* - A read with no section is allowed (company scoping still applies).
|
|
34
|
+
* - A write with no section is refused (the boot audit makes this unreachable).
|
|
35
|
+
* - Otherwise the caller's effective permission in the token's company decides:
|
|
36
|
+
* `true` or a record path allows, `false` or absent refuses with 403.
|
|
37
|
+
* - No administrator bypass.
|
|
38
|
+
*/
|
|
39
|
+
export declare class ModulePermissionGate {
|
|
40
|
+
private readonly reflector;
|
|
41
|
+
private readonly cls;
|
|
42
|
+
private readonly permissions;
|
|
43
|
+
private readonly enforce?;
|
|
44
|
+
constructor(reflector: Reflector, cls: ClsService, permissions: ModulePermissionService, enforce?: boolean);
|
|
45
|
+
get enabled(): boolean;
|
|
46
|
+
assert(params: {
|
|
47
|
+
request: any;
|
|
48
|
+
context: ExecutionContext;
|
|
49
|
+
}): Promise<void>;
|
|
50
|
+
}
|
|
51
|
+
//# sourceMappingURL=module-permission.gate.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"module-permission.gate.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/module-permission.gate.ts"],"names":[],"mappings":"AAAA,OAAO,EAAE,gBAAgB,EAAoD,MAAM,gBAAgB,CAAC;AACpG,OAAO,EAAE,SAAS,EAAE,MAAM,cAAc,CAAC;AACzC,OAAO,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AAExC,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,6CAA6C,CAAC;AAEpF,OAAO,EAAE,uBAAuB,EAAE,MAAM,6BAA6B,CAAC;AACtE,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAE5D;;;;GAIG;AACH,wBAAgB,uBAAuB,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,GAAG,UAAU,CAa9E;AAED;;;GAGG;AACH,wBAAgB,eAAe,CAAC,MAAM,EAAE;IACtC,eAAe,EAAE,gBAAgB,GAAG,SAAS,CAAC;IAC9C,iBAAiB,EAAE,gBAAgB,GAAG,SAAS,CAAC;IAChD,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;CAC5B,GAAG;IAAE,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC;IAAC,MAAM,EAAE,UAAU,CAAA;CAAE,CAKrD;AAED;;;;;;;;;;;;;GAaG;AACH,qBACa,oBAAoB;IAE7B,OAAO,CAAC,QAAQ,CAAC,SAAS;IAC1B,OAAO,CAAC,QAAQ,CAAC,GAAG;IACpB,OAAO,CAAC,QAAQ,CAAC,WAAW;IAG5B,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAC;gBALR,SAAS,EAAE,SAAS,EACpB,GAAG,EAAE,UAAU,EACf,WAAW,EAAE,uBAAuB,EAGpC,OAAO,CAAC,EAAE,OAAO;IAGpC,IAAI,OAAO,IAAI,OAAO,CAErB;IAEK,MAAM,CAAC,MAAM,EAAE;QAAE,OAAO,EAAE,GAAG,CAAC;QAAC,OAAO,EAAE,gBAAgB,CAAA;KAAE,GAAG,OAAO,CAAC,IAAI,CAAC;CAuBjF"}
|
|
@@ -0,0 +1,108 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
12
|
+
return function (target, key) { decorator(target, key, paramIndex); }
|
|
13
|
+
};
|
|
14
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
15
|
+
exports.ModulePermissionGate = void 0;
|
|
16
|
+
exports.rbacActionForHttpMethod = rbacActionForHttpMethod;
|
|
17
|
+
exports.resolveRouteAcl = resolveRouteAcl;
|
|
18
|
+
const common_1 = require("@nestjs/common");
|
|
19
|
+
const core_1 = require("@nestjs/core");
|
|
20
|
+
const nestjs_cls_1 = require("nestjs-cls");
|
|
21
|
+
const module_decorator_1 = require("../../../common/decorators/module.decorator");
|
|
22
|
+
const rbac_tokens_1 = require("../rbac.tokens");
|
|
23
|
+
const module_permission_service_1 = require("./module-permission.service");
|
|
24
|
+
/**
|
|
25
|
+
* HTTP method → permission action. GET/HEAD/OPTIONS read, POST create, PUT/PATCH
|
|
26
|
+
* update, DELETE delete. Anything else is treated as a write (update), so an
|
|
27
|
+
* unexpected verb never slips through as a read.
|
|
28
|
+
*/
|
|
29
|
+
function rbacActionForHttpMethod(method) {
|
|
30
|
+
switch ((method ?? "").toUpperCase()) {
|
|
31
|
+
case "GET":
|
|
32
|
+
case "HEAD":
|
|
33
|
+
case "OPTIONS":
|
|
34
|
+
return "read";
|
|
35
|
+
case "POST":
|
|
36
|
+
return "create";
|
|
37
|
+
case "DELETE":
|
|
38
|
+
return "delete";
|
|
39
|
+
default:
|
|
40
|
+
return "update";
|
|
41
|
+
}
|
|
42
|
+
}
|
|
43
|
+
/**
|
|
44
|
+
* Section and action of a route: the handler `@ModuleACL` wins over the class
|
|
45
|
+
* one, field by field; the action falls back to the HTTP-method mapping.
|
|
46
|
+
*/
|
|
47
|
+
function resolveRouteAcl(params) {
|
|
48
|
+
const module = params.handlerDefinition?.module ?? params.classDefinition?.module;
|
|
49
|
+
const action = params.handlerDefinition?.action ?? params.classDefinition?.action ?? rbacActionForHttpMethod(params.method);
|
|
50
|
+
return { module: module || undefined, action };
|
|
51
|
+
}
|
|
52
|
+
/**
|
|
53
|
+
* Request-level permission check, run by the session guards (`JwtAuthGuard`,
|
|
54
|
+
* `AdminJwtAuthGuard`, `OptionalJwtAuthGuard`) right after authentication.
|
|
55
|
+
*
|
|
56
|
+
* Off unless the app bootstraps with `permissions: { enforce: true }`: with it
|
|
57
|
+
* off, `assert` returns before reading metadata or touching the database.
|
|
58
|
+
*
|
|
59
|
+
* Rules:
|
|
60
|
+
* - A read with no section is allowed (company scoping still applies).
|
|
61
|
+
* - A write with no section is refused (the boot audit makes this unreachable).
|
|
62
|
+
* - Otherwise the caller's effective permission in the token's company decides:
|
|
63
|
+
* `true` or a record path allows, `false` or absent refuses with 403.
|
|
64
|
+
* - No administrator bypass.
|
|
65
|
+
*/
|
|
66
|
+
let ModulePermissionGate = class ModulePermissionGate {
|
|
67
|
+
constructor(reflector, cls, permissions, enforce) {
|
|
68
|
+
this.reflector = reflector;
|
|
69
|
+
this.cls = cls;
|
|
70
|
+
this.permissions = permissions;
|
|
71
|
+
this.enforce = enforce;
|
|
72
|
+
}
|
|
73
|
+
get enabled() {
|
|
74
|
+
return this.enforce === true;
|
|
75
|
+
}
|
|
76
|
+
async assert(params) {
|
|
77
|
+
if (!this.enabled)
|
|
78
|
+
return;
|
|
79
|
+
const userId = params.request?.user?.userId;
|
|
80
|
+
// No authenticated session (optional guard, anonymous caller): nothing to evaluate.
|
|
81
|
+
if (!userId)
|
|
82
|
+
return;
|
|
83
|
+
const { module, action } = resolveRouteAcl({
|
|
84
|
+
classDefinition: this.reflector.get(module_decorator_1.MODULE_ACL_METADATA, params.context.getClass()),
|
|
85
|
+
handlerDefinition: this.reflector.get(module_decorator_1.MODULE_ACL_METADATA, params.context.getHandler()),
|
|
86
|
+
method: params.request?.method,
|
|
87
|
+
});
|
|
88
|
+
if (!module) {
|
|
89
|
+
if (action === "read")
|
|
90
|
+
return;
|
|
91
|
+
throw new common_1.ForbiddenException();
|
|
92
|
+
}
|
|
93
|
+
const companyId = (this.cls.isActive() ? this.cls.get("companyId") : undefined) ?? undefined;
|
|
94
|
+
const allowed = await this.permissions.allows({ userId, companyId, moduleId: module, action });
|
|
95
|
+
if (!allowed)
|
|
96
|
+
throw new common_1.ForbiddenException();
|
|
97
|
+
}
|
|
98
|
+
};
|
|
99
|
+
exports.ModulePermissionGate = ModulePermissionGate;
|
|
100
|
+
exports.ModulePermissionGate = ModulePermissionGate = __decorate([
|
|
101
|
+
(0, common_1.Injectable)(),
|
|
102
|
+
__param(3, (0, common_1.Optional)()),
|
|
103
|
+
__param(3, (0, common_1.Inject)(rbac_tokens_1.PERMISSIONS_ENFORCE)),
|
|
104
|
+
__metadata("design:paramtypes", [core_1.Reflector,
|
|
105
|
+
nestjs_cls_1.ClsService,
|
|
106
|
+
module_permission_service_1.ModulePermissionService, Boolean])
|
|
107
|
+
], ModulePermissionGate);
|
|
108
|
+
//# sourceMappingURL=module-permission.gate.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"module-permission.gate.js","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/module-permission.gate.ts"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
import { ClsService } from "nestjs-cls";
|
|
2
|
+
import { RbacPermissionRepository } from "../repositories/rbac-permission.repository";
|
|
3
|
+
import type { EffectivePermissions } from "../repositories/rbac-permission.repository";
|
|
4
|
+
import type { RbacAction } from "./rbac-permission.service";
|
|
5
|
+
export type { EffectivePermissions } from "../repositories/rbac-permission.repository";
|
|
6
|
+
/**
|
|
7
|
+
* Resolves a caller's effective permissions in the token's company, for the
|
|
8
|
+
* request-level permission gate (`ModulePermissionGate`).
|
|
9
|
+
*
|
|
10
|
+
* Mirrors `RbacPermissionService` (same `featureModuleQuery` resolution) with
|
|
11
|
+
* three differences: it binds the token's company instead of the legacy
|
|
12
|
+
* `BELONGS_TO` edge, it keeps record-path values (a string allows at the
|
|
13
|
+
* section level), and it resolves once per request (cached in CLS).
|
|
14
|
+
*
|
|
15
|
+
* No administrator bypass: the platform Administrator is resolved like any
|
|
16
|
+
* role, so its grants must exist in the app's permission table.
|
|
17
|
+
*/
|
|
18
|
+
export declare class ModulePermissionService {
|
|
19
|
+
private readonly repository;
|
|
20
|
+
private readonly cls;
|
|
21
|
+
constructor(repository: RbacPermissionRepository, cls: ClsService);
|
|
22
|
+
resolve(params: {
|
|
23
|
+
userId: string;
|
|
24
|
+
companyId: string | undefined;
|
|
25
|
+
}): Promise<EffectivePermissions>;
|
|
26
|
+
/** True when the effective value is `true` or a non-empty record path. */
|
|
27
|
+
allows(params: {
|
|
28
|
+
userId: string;
|
|
29
|
+
companyId: string | undefined;
|
|
30
|
+
moduleId: string;
|
|
31
|
+
action: RbacAction;
|
|
32
|
+
}): Promise<boolean>;
|
|
33
|
+
}
|
|
34
|
+
//# sourceMappingURL=module-permission.service.d.ts.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"module-permission.service.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/module-permission.service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AACxC,OAAO,EAAE,wBAAwB,EAAE,MAAM,4CAA4C,CAAC;AACtF,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,4CAA4C,CAAC;AACvF,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,2BAA2B,CAAC;AAE5D,YAAY,EAAE,oBAAoB,EAAE,MAAM,4CAA4C,CAAC;AAUvF;;;;;;;;;;;GAWG;AACH,qBACa,uBAAuB;IAEhC,OAAO,CAAC,QAAQ,CAAC,UAAU;IAC3B,OAAO,CAAC,QAAQ,CAAC,GAAG;gBADH,UAAU,EAAE,wBAAwB,EACpC,GAAG,EAAE,UAAU;IAG5B,OAAO,CAAC,MAAM,EAAE;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,SAAS,EAAE,MAAM,GAAG,SAAS,CAAA;KAAE,GAAG,OAAO,CAAC,oBAAoB,CAAC;IAmBvG,0EAA0E;IACpE,MAAM,CAAC,MAAM,EAAE;QACnB,MAAM,EAAE,MAAM,CAAC;QACf,SAAS,EAAE,MAAM,GAAG,SAAS,CAAC;QAC9B,QAAQ,EAAE,MAAM,CAAC;QACjB,MAAM,EAAE,UAAU,CAAC;KACpB,GAAG,OAAO,CAAC,OAAO,CAAC;CAKrB"}
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __decorate = (this && this.__decorate) || function (decorators, target, key, desc) {
|
|
3
|
+
var c = arguments.length, r = c < 3 ? target : desc === null ? desc = Object.getOwnPropertyDescriptor(target, key) : desc, d;
|
|
4
|
+
if (typeof Reflect === "object" && typeof Reflect.decorate === "function") r = Reflect.decorate(decorators, target, key, desc);
|
|
5
|
+
else for (var i = decorators.length - 1; i >= 0; i--) if (d = decorators[i]) r = (c < 3 ? d(r) : c > 3 ? d(target, key, r) : d(target, key)) || r;
|
|
6
|
+
return c > 3 && r && Object.defineProperty(target, key, r), r;
|
|
7
|
+
};
|
|
8
|
+
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
|
+
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
|
+
};
|
|
11
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
|
+
exports.ModulePermissionService = void 0;
|
|
13
|
+
const common_1 = require("@nestjs/common");
|
|
14
|
+
const nestjs_cls_1 = require("nestjs-cls");
|
|
15
|
+
const rbac_permission_repository_1 = require("../repositories/rbac-permission.repository");
|
|
16
|
+
/** CLS key holding the permissions resolved for the current request. */
|
|
17
|
+
const CLS_KEY = "effectivePermissions";
|
|
18
|
+
/**
|
|
19
|
+
* Resolves a caller's effective permissions in the token's company, for the
|
|
20
|
+
* request-level permission gate (`ModulePermissionGate`).
|
|
21
|
+
*
|
|
22
|
+
* Mirrors `RbacPermissionService` (same `featureModuleQuery` resolution) with
|
|
23
|
+
* three differences: it binds the token's company instead of the legacy
|
|
24
|
+
* `BELONGS_TO` edge, it keeps record-path values (a string allows at the
|
|
25
|
+
* section level), and it resolves once per request (cached in CLS).
|
|
26
|
+
*
|
|
27
|
+
* No administrator bypass: the platform Administrator is resolved like any
|
|
28
|
+
* role, so its grants must exist in the app's permission table.
|
|
29
|
+
*/
|
|
30
|
+
let ModulePermissionService = class ModulePermissionService {
|
|
31
|
+
constructor(repository, cls) {
|
|
32
|
+
this.repository = repository;
|
|
33
|
+
this.cls = cls;
|
|
34
|
+
}
|
|
35
|
+
async resolve(params) {
|
|
36
|
+
const key = `${params.userId}|${params.companyId ?? ""}`;
|
|
37
|
+
const clsActive = this.cls.isActive();
|
|
38
|
+
if (clsActive) {
|
|
39
|
+
const cached = this.cls.get(CLS_KEY);
|
|
40
|
+
if (cached && cached.key === key)
|
|
41
|
+
return cached.permissions;
|
|
42
|
+
}
|
|
43
|
+
const permissions = await this.repository.findEffectivePermissions({
|
|
44
|
+
userId: params.userId,
|
|
45
|
+
companyId: params.companyId || undefined,
|
|
46
|
+
});
|
|
47
|
+
if (clsActive)
|
|
48
|
+
this.cls.set(CLS_KEY, { key, permissions });
|
|
49
|
+
return permissions;
|
|
50
|
+
}
|
|
51
|
+
/** True when the effective value is `true` or a non-empty record path. */
|
|
52
|
+
async allows(params) {
|
|
53
|
+
const permissions = await this.resolve({ userId: params.userId, companyId: params.companyId });
|
|
54
|
+
const value = permissions.get(params.moduleId)?.[params.action];
|
|
55
|
+
return value === true || (typeof value === "string" && value.length > 0);
|
|
56
|
+
}
|
|
57
|
+
};
|
|
58
|
+
exports.ModulePermissionService = ModulePermissionService;
|
|
59
|
+
exports.ModulePermissionService = ModulePermissionService = __decorate([
|
|
60
|
+
(0, common_1.Injectable)(),
|
|
61
|
+
__metadata("design:paramtypes", [rbac_permission_repository_1.RbacPermissionRepository,
|
|
62
|
+
nestjs_cls_1.ClsService])
|
|
63
|
+
], ModulePermissionService);
|
|
64
|
+
//# sourceMappingURL=module-permission.service.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"module-permission.service.js","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/module-permission.service.ts"],"names":[],"mappings":";;;;;;;;;;;;AAAA,2CAA4C;AAC5C,2CAAwC;AACxC,2FAAsF;AAMtF,wEAAwE;AACxE,MAAM,OAAO,GAAG,sBAAsB,CAAC;AAOvC;;;;;;;;;;;GAWG;AAEI,IAAM,uBAAuB,GAA7B,MAAM,uBAAuB;IAClC,YACmB,UAAoC,EACpC,GAAe;QADf,eAAU,GAAV,UAAU,CAA0B;QACpC,QAAG,GAAH,GAAG,CAAY;IAC/B,CAAC;IAEJ,KAAK,CAAC,OAAO,CAAC,MAAyD;QACrE,MAAM,GAAG,GAAG,GAAG,MAAM,CAAC,MAAM,IAAI,MAAM,CAAC,SAAS,IAAI,EAAE,EAAE,CAAC;QACzD,MAAM,SAAS,GAAG,IAAI,CAAC,GAAG,CAAC,QAAQ,EAAE,CAAC;QAEtC,IAAI,SAAS,EAAE,CAAC;YACd,MAAM,MAAM,GAAG,IAAI,CAAC,GAAG,CAAC,GAAG,CAAgC,OAAO,CAAC,CAAC;YACpE,IAAI,MAAM,IAAI,MAAM,CAAC,GAAG,KAAK,GAAG;gBAAE,OAAO,MAAM,CAAC,WAAW,CAAC;QAC9D,CAAC;QAED,MAAM,WAAW,GAAG,MAAM,IAAI,CAAC,UAAU,CAAC,wBAAwB,CAAC;YACjE,MAAM,EAAE,MAAM,CAAC,MAAM;YACrB,SAAS,EAAE,MAAM,CAAC,SAAS,IAAI,SAAS;SACzC,CAAC,CAAC;QAEH,IAAI,SAAS;YAAE,IAAI,CAAC,GAAG,CAAC,GAAG,CAAoB,OAAO,EAAE,EAAE,GAAG,EAAE,WAAW,EAAE,CAAC,CAAC;QAE9E,OAAO,WAAW,CAAC;IACrB,CAAC;IAED,0EAA0E;IAC1E,KAAK,CAAC,MAAM,CAAC,MAKZ;QACC,MAAM,WAAW,GAAG,MAAM,IAAI,CAAC,OAAO,CAAC,EAAE,MAAM,EAAE,MAAM,CAAC,MAAM,EAAE,SAAS,EAAE,MAAM,CAAC,SAAS,EAAE,CAAC,CAAC;QAC/F,MAAM,KAAK,GAAG,WAAW,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;QAChE,OAAO,KAAK,KAAK,IAAI,IAAI,CAAC,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC;IAC3E,CAAC;CACF,CAAA;AApCY,0DAAuB;kCAAvB,uBAAuB;IADnC,IAAA,mBAAU,GAAE;qCAGoB,qDAAwB;QAC/B,uBAAU;GAHvB,uBAAuB,CAoCnC"}
|
|
@@ -1,4 +1,6 @@
|
|
|
1
|
+
import { ClsService } from "nestjs-cls";
|
|
1
2
|
import { RbacPermissionRepository } from "../repositories/rbac-permission.repository";
|
|
3
|
+
import { ModulePermissionService } from "./module-permission.service";
|
|
2
4
|
/**
|
|
3
5
|
* The four permission flags resolved per module by the RBAC permission model.
|
|
4
6
|
*
|
|
@@ -13,10 +15,17 @@ export type RbacAction = "read" | "create" | "update" | "delete";
|
|
|
13
15
|
* UserModulesRepository for the chatbot catalog).
|
|
14
16
|
*
|
|
15
17
|
* Consumed by the MCP layer to gate reads and writes per tool call.
|
|
18
|
+
*
|
|
19
|
+
* With `permissions.enforce` on, it delegates to `ModulePermissionService`
|
|
20
|
+
* (token company from CLS, record paths allow) so tool calls and HTTP routes
|
|
21
|
+
* never disagree. With it off, it behaves exactly as before.
|
|
16
22
|
*/
|
|
17
23
|
export declare class RbacPermissionService {
|
|
18
24
|
private readonly repository;
|
|
19
|
-
|
|
25
|
+
private readonly modulePermissions?;
|
|
26
|
+
private readonly cls?;
|
|
27
|
+
private readonly enforce?;
|
|
28
|
+
constructor(repository: RbacPermissionRepository, modulePermissions?: ModulePermissionService, cls?: ClsService, enforce?: boolean);
|
|
20
29
|
/**
|
|
21
30
|
* True iff the user's effective permission flag for `action` on the module
|
|
22
31
|
* resolves to `true`. Unknown modules (not in the user's effective set)
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rbac-permission.service.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/rbac-permission.service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,wBAAwB,EAAE,MAAM,4CAA4C,CAAC;AAEtF;;;;;;GAMG;AACH,MAAM,MAAM,UAAU,GAAG,MAAM,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,CAAC;AAEjE
|
|
1
|
+
{"version":3,"file":"rbac-permission.service.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/rbac-permission.service.ts"],"names":[],"mappings":"AACA,OAAO,EAAE,UAAU,EAAE,MAAM,YAAY,CAAC;AACxC,OAAO,EAAE,wBAAwB,EAAE,MAAM,4CAA4C,CAAC;AAEtF,OAAO,EAAE,uBAAuB,EAAE,MAAM,6BAA6B,CAAC;AAEtE;;;;;;GAMG;AACH,MAAM,MAAM,UAAU,GAAG,MAAM,GAAG,QAAQ,GAAG,QAAQ,GAAG,QAAQ,CAAC;AAEjE;;;;;;;;;;GAUG;AACH,qBACa,qBAAqB;IAE9B,OAAO,CAAC,QAAQ,CAAC,UAAU;IACkB,OAAO,CAAC,QAAQ,CAAC,iBAAiB,CAAC;IAChD,OAAO,CAAC,QAAQ,CAAC,GAAG,CAAC;IACZ,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAC;gBAHjD,UAAU,EAAE,wBAAwB,EACS,iBAAiB,CAAC,EAAE,uBAAuB,EACxD,GAAG,CAAC,EAAE,UAAU,EACP,OAAO,CAAC,EAAE,OAAO;IAG7E;;;;OAIG;IACG,GAAG,CAAC,MAAM,EAAE;QAAE,MAAM,EAAE,MAAM,CAAC;QAAC,QAAQ,EAAE,MAAM,CAAC;QAAC,MAAM,EAAE,UAAU,CAAA;KAAE,GAAG,OAAO,CAAC,OAAO,CAAC;CAc9F"}
|
|
@@ -8,20 +8,33 @@ var __decorate = (this && this.__decorate) || function (decorators, target, key,
|
|
|
8
8
|
var __metadata = (this && this.__metadata) || function (k, v) {
|
|
9
9
|
if (typeof Reflect === "object" && typeof Reflect.metadata === "function") return Reflect.metadata(k, v);
|
|
10
10
|
};
|
|
11
|
+
var __param = (this && this.__param) || function (paramIndex, decorator) {
|
|
12
|
+
return function (target, key) { decorator(target, key, paramIndex); }
|
|
13
|
+
};
|
|
11
14
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
12
15
|
exports.RbacPermissionService = void 0;
|
|
13
16
|
const common_1 = require("@nestjs/common");
|
|
17
|
+
const nestjs_cls_1 = require("nestjs-cls");
|
|
14
18
|
const rbac_permission_repository_1 = require("../repositories/rbac-permission.repository");
|
|
19
|
+
const rbac_tokens_1 = require("../rbac.tokens");
|
|
20
|
+
const module_permission_service_1 = require("./module-permission.service");
|
|
15
21
|
/**
|
|
16
22
|
* Answers `can(userId, moduleId, action)` using the same `featureModuleQuery`
|
|
17
23
|
* permission resolution as the rest of the app (AuthRepository at login,
|
|
18
24
|
* UserModulesRepository for the chatbot catalog).
|
|
19
25
|
*
|
|
20
26
|
* Consumed by the MCP layer to gate reads and writes per tool call.
|
|
27
|
+
*
|
|
28
|
+
* With `permissions.enforce` on, it delegates to `ModulePermissionService`
|
|
29
|
+
* (token company from CLS, record paths allow) so tool calls and HTTP routes
|
|
30
|
+
* never disagree. With it off, it behaves exactly as before.
|
|
21
31
|
*/
|
|
22
32
|
let RbacPermissionService = class RbacPermissionService {
|
|
23
|
-
constructor(repository) {
|
|
33
|
+
constructor(repository, modulePermissions, cls, enforce) {
|
|
24
34
|
this.repository = repository;
|
|
35
|
+
this.modulePermissions = modulePermissions;
|
|
36
|
+
this.cls = cls;
|
|
37
|
+
this.enforce = enforce;
|
|
25
38
|
}
|
|
26
39
|
/**
|
|
27
40
|
* True iff the user's effective permission flag for `action` on the module
|
|
@@ -29,6 +42,15 @@ let RbacPermissionService = class RbacPermissionService {
|
|
|
29
42
|
* always deny.
|
|
30
43
|
*/
|
|
31
44
|
async can(params) {
|
|
45
|
+
if (this.enforce === true && this.modulePermissions) {
|
|
46
|
+
const companyId = this.cls?.isActive() ? (this.cls.get("companyId") ?? undefined) : undefined;
|
|
47
|
+
return this.modulePermissions.allows({
|
|
48
|
+
userId: params.userId,
|
|
49
|
+
companyId,
|
|
50
|
+
moduleId: params.moduleId,
|
|
51
|
+
action: params.action,
|
|
52
|
+
});
|
|
53
|
+
}
|
|
32
54
|
const perms = await this.repository.findEffectivePermissionsForUser(params.userId);
|
|
33
55
|
return perms.get(params.moduleId)?.[params.action] === true;
|
|
34
56
|
}
|
|
@@ -36,6 +58,14 @@ let RbacPermissionService = class RbacPermissionService {
|
|
|
36
58
|
exports.RbacPermissionService = RbacPermissionService;
|
|
37
59
|
exports.RbacPermissionService = RbacPermissionService = __decorate([
|
|
38
60
|
(0, common_1.Injectable)(),
|
|
39
|
-
|
|
61
|
+
__param(1, (0, common_1.Optional)()),
|
|
62
|
+
__param(1, (0, common_1.Inject)(module_permission_service_1.ModulePermissionService)),
|
|
63
|
+
__param(2, (0, common_1.Optional)()),
|
|
64
|
+
__param(2, (0, common_1.Inject)(nestjs_cls_1.ClsService)),
|
|
65
|
+
__param(3, (0, common_1.Optional)()),
|
|
66
|
+
__param(3, (0, common_1.Inject)(rbac_tokens_1.PERMISSIONS_ENFORCE)),
|
|
67
|
+
__metadata("design:paramtypes", [rbac_permission_repository_1.RbacPermissionRepository,
|
|
68
|
+
module_permission_service_1.ModulePermissionService,
|
|
69
|
+
nestjs_cls_1.ClsService, Boolean])
|
|
40
70
|
], RbacPermissionService);
|
|
41
71
|
//# sourceMappingURL=rbac-permission.service.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rbac-permission.service.js","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/rbac-permission.service.ts"],"names":[],"mappings":"
|
|
1
|
+
{"version":3,"file":"rbac-permission.service.js","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/rbac-permission.service.ts"],"names":[],"mappings":";;;;;;;;;;;;;;;AAAA,2CAA8D;AAC9D,2CAAwC;AACxC,2FAAsF;AACtF,gDAAqD;AACrD,2EAAsE;AAWtE;;;;;;;;;;GAUG;AAEI,IAAM,qBAAqB,GAA3B,MAAM,qBAAqB;IAChC,YACmB,UAAoC,EACS,iBAA2C,EACxD,GAAgB,EACP,OAAiB;QAH1D,eAAU,GAAV,UAAU,CAA0B;QACS,sBAAiB,GAAjB,iBAAiB,CAA0B;QACxD,QAAG,GAAH,GAAG,CAAa;QACP,YAAO,GAAP,OAAO,CAAU;IAC1E,CAAC;IAEJ;;;;OAIG;IACH,KAAK,CAAC,GAAG,CAAC,MAAgE;QACxE,IAAI,IAAI,CAAC,OAAO,KAAK,IAAI,IAAI,IAAI,CAAC,iBAAiB,EAAE,CAAC;YACpD,MAAM,SAAS,GAAuB,IAAI,CAAC,GAAG,EAAE,QAAQ,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,GAAG,CAAC,WAAW,CAAC,IAAI,SAAS,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;YAClH,OAAO,IAAI,CAAC,iBAAiB,CAAC,MAAM,CAAC;gBACnC,MAAM,EAAE,MAAM,CAAC,MAAM;gBACrB,SAAS;gBACT,QAAQ,EAAE,MAAM,CAAC,QAAQ;gBACzB,MAAM,EAAE,MAAM,CAAC,MAAM;aACtB,CAAC,CAAC;QACL,CAAC;QAED,MAAM,KAAK,GAAG,MAAM,IAAI,CAAC,UAAU,CAAC,+BAA+B,CAAC,MAAM,CAAC,MAAM,CAAC,CAAC;QACnF,OAAO,KAAK,CAAC,GAAG,CAAC,MAAM,CAAC,QAAQ,CAAC,EAAE,CAAC,MAAM,CAAC,MAAM,CAAC,KAAK,IAAI,CAAC;IAC9D,CAAC;CACF,CAAA;AA3BY,sDAAqB;gCAArB,qBAAqB;IADjC,IAAA,mBAAU,GAAE;IAIR,WAAA,IAAA,iBAAQ,GAAE,CAAA;IAAE,WAAA,IAAA,eAAM,EAAC,mDAAuB,CAAC,CAAA;IAC3C,WAAA,IAAA,iBAAQ,GAAE,CAAA;IAAE,WAAA,IAAA,eAAM,EAAC,uBAAU,CAAC,CAAA;IAC9B,WAAA,IAAA,iBAAQ,GAAE,CAAA;IAAE,WAAA,IAAA,eAAM,EAAC,iCAAmB,CAAC,CAAA;qCAHX,qDAAwB;QAC6B,mDAAuB;QAClD,uBAAU;GAJxD,qBAAqB,CA2BjC"}
|
|
@@ -7,7 +7,9 @@ import type { RbacMatrix } from "../dsl/types";
|
|
|
7
7
|
*
|
|
8
8
|
* Behaviour (per spec §6.3):
|
|
9
9
|
* - Administrator role is never written as an HAS_PERMISSIONS edge — the
|
|
10
|
-
* security layer short-circuits for it.
|
|
10
|
+
* security layer short-circuits for it. Exception: with
|
|
11
|
+
* `permissions.enforce` on (no administrator bypass in the request gate)
|
|
12
|
+
* its edges are reconciled like any other role's.
|
|
11
13
|
* - Module defaults are stored on `Module.permissions`.
|
|
12
14
|
* - Role-specific permissions are stored on `(Role)-[:HAS_PERMISSIONS]->(Module)`.
|
|
13
15
|
* - Deletions are scoped to modules declared in the matrix: edges for
|
|
@@ -19,7 +21,14 @@ export declare class RbacReconcilerService implements OnApplicationBootstrap {
|
|
|
19
21
|
private readonly neo4j;
|
|
20
22
|
private readonly matrix;
|
|
21
23
|
private readonly logger;
|
|
22
|
-
|
|
24
|
+
private readonly enforce?;
|
|
25
|
+
constructor(neo4j: Neo4jService, matrix: RbacMatrix | null, logger: AppLoggingService, enforce?: boolean);
|
|
26
|
+
/**
|
|
27
|
+
* The Administrator role is skipped (never written, never deleted) unless the
|
|
28
|
+
* request permission gate is on: the gate has no administrator bypass, so the
|
|
29
|
+
* Administrator's grants must then be reconciled like any other role's.
|
|
30
|
+
*/
|
|
31
|
+
private skipsRole;
|
|
23
32
|
onApplicationBootstrap(): Promise<void>;
|
|
24
33
|
private preflight;
|
|
25
34
|
private findMissing;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"rbac-reconciler.service.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/rbac-reconciler.service.ts"],"names":[],"mappings":"AAAA,OAAO,EAAgC,sBAAsB,EAAE,MAAM,gBAAgB,CAAC;AACtF,OAAO,EAAE,YAAY,EAAE,MAAM,4CAA4C,CAAC;AAC1E,OAAO,EAAE,iBAAiB,EAAE,MAAM,gDAAgD,CAAC;AAGnF,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAe/C
|
|
1
|
+
{"version":3,"file":"rbac-reconciler.service.d.ts","sourceRoot":"","sources":["../../../../src/foundations/rbac/services/rbac-reconciler.service.ts"],"names":[],"mappings":"AAAA,OAAO,EAAgC,sBAAsB,EAAE,MAAM,gBAAgB,CAAC;AACtF,OAAO,EAAE,YAAY,EAAE,MAAM,4CAA4C,CAAC;AAC1E,OAAO,EAAE,iBAAiB,EAAE,MAAM,gDAAgD,CAAC;AAGnF,OAAO,KAAK,EAAE,UAAU,EAAE,MAAM,cAAc,CAAC;AAe/C;;;;;;;;;;;;;;GAcG;AACH,qBACa,qBAAsB,YAAW,sBAAsB;IAEhE,OAAO,CAAC,QAAQ,CAAC,KAAK;IACiB,OAAO,CAAC,QAAQ,CAAC,MAAM;IAC9D,OAAO,CAAC,QAAQ,CAAC,MAAM;IACkB,OAAO,CAAC,QAAQ,CAAC,OAAO,CAAC;gBAHjD,KAAK,EAAE,YAAY,EACoB,MAAM,EAAE,UAAU,GAAG,IAAI,EAChE,MAAM,EAAE,iBAAiB,EACgB,OAAO,CAAC,EAAE,OAAO;IAG7E;;;;OAIG;IACH,OAAO,CAAC,SAAS;IAIX,sBAAsB,IAAI,OAAO,CAAC,IAAI,CAAC;YAsB/B,SAAS;YAyBT,WAAW;YAOX,eAAe;IAsB7B,OAAO,CAAC,WAAW;YAkEL,KAAK;CA4BpB"}
|