@venizia/ignis-kernel 0.4.0 → 0.4.2

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.
Files changed (191) hide show
  1. package/dist/cjs/base/applications/abstract.js +2 -2
  2. package/dist/cjs/base/applications/abstract.js.map +1 -1
  3. package/dist/cjs/base/applications/artifact-group.js +1 -1
  4. package/dist/cjs/base/applications/artifact-group.js.map +1 -1
  5. package/dist/cjs/base/applications/artifact-index.js +11 -11
  6. package/dist/cjs/base/applications/artifact-index.js.map +1 -1
  7. package/dist/cjs/base/applications/boot-sequence.js +1 -1
  8. package/dist/cjs/base/applications/boot-sequence.js.map +1 -1
  9. package/dist/cjs/base/applications/cors.d.ts +13 -0
  10. package/dist/cjs/base/applications/cors.d.ts.map +1 -0
  11. package/dist/cjs/base/applications/cors.js +43 -0
  12. package/dist/cjs/base/applications/cors.js.map +1 -0
  13. package/dist/cjs/base/applications/deprecations.d.ts +10 -0
  14. package/dist/cjs/base/applications/deprecations.d.ts.map +1 -0
  15. package/dist/cjs/base/applications/deprecations.js +23 -0
  16. package/dist/cjs/base/applications/deprecations.js.map +1 -0
  17. package/dist/cjs/base/applications/rest.d.ts.map +1 -1
  18. package/dist/cjs/base/applications/rest.js +11 -5
  19. package/dist/cjs/base/applications/rest.js.map +1 -1
  20. package/dist/cjs/base/auth/authenticate/common/codecs.js +2 -2
  21. package/dist/cjs/base/auth/authenticate/common/codecs.js.map +1 -1
  22. package/dist/cjs/base/auth/authenticate/providers/authentication.provider.js +1 -1
  23. package/dist/cjs/base/auth/authenticate/providers/authentication.provider.js.map +1 -1
  24. package/dist/cjs/base/auth/authenticate/strategies/strategy-registry.js +1 -1
  25. package/dist/cjs/base/auth/authenticate/strategies/strategy-registry.js.map +1 -1
  26. package/dist/cjs/base/auth/authorize/builders/grant.builder.js +12 -12
  27. package/dist/cjs/base/auth/authorize/builders/grant.builder.js.map +1 -1
  28. package/dist/cjs/base/auth/authorize/builders/permission.builder.js +1 -1
  29. package/dist/cjs/base/auth/authorize/builders/permission.builder.js.map +1 -1
  30. package/dist/cjs/base/auth/authorize/builders/policy.builder.js +1 -1
  31. package/dist/cjs/base/auth/authorize/builders/policy.builder.js.map +1 -1
  32. package/dist/cjs/base/auth/authorize/common/constants/authorization.d.ts.map +1 -1
  33. package/dist/cjs/base/auth/authorize/common/constants/authorization.js +2 -2
  34. package/dist/cjs/base/auth/authorize/common/constants/authorization.js.map +1 -1
  35. package/dist/cjs/base/auth/authorize/enforcers/enforcer-registry.js +1 -1
  36. package/dist/cjs/base/auth/authorize/enforcers/enforcer-registry.js.map +1 -1
  37. package/dist/cjs/base/auth/authorize/providers/authorization.provider.js +3 -3
  38. package/dist/cjs/base/auth/authorize/providers/authorization.provider.js.map +1 -1
  39. package/dist/cjs/base/controllers/factory/authorize-guard.d.ts +19 -0
  40. package/dist/cjs/base/controllers/factory/authorize-guard.d.ts.map +1 -0
  41. package/dist/cjs/base/controllers/factory/authorize-guard.js +60 -0
  42. package/dist/cjs/base/controllers/factory/authorize-guard.js.map +1 -0
  43. package/dist/cjs/base/controllers/factory/controller.d.ts +2 -2
  44. package/dist/cjs/base/controllers/factory/controller.d.ts.map +1 -1
  45. package/dist/cjs/base/controllers/factory/controller.js +9 -0
  46. package/dist/cjs/base/controllers/factory/controller.js.map +1 -1
  47. package/dist/cjs/base/controllers/factory/crud/abstract.d.ts +1 -1
  48. package/dist/cjs/base/controllers/factory/crud/abstract.d.ts.map +1 -1
  49. package/dist/cjs/base/controllers/factory/crud/abstract.js.map +1 -1
  50. package/dist/cjs/base/controllers/factory/definition.js +1 -1
  51. package/dist/cjs/base/controllers/factory/definition.js.map +1 -1
  52. package/dist/cjs/base/controllers/rest/extras.js +5 -5
  53. package/dist/cjs/base/controllers/rest/extras.js.map +1 -1
  54. package/dist/cjs/base/metadata/injectable.js +1 -1
  55. package/dist/cjs/base/metadata/injectable.js.map +1 -1
  56. package/dist/cjs/base/metadata/model-settings.d.ts +21 -0
  57. package/dist/cjs/base/metadata/model-settings.d.ts.map +1 -0
  58. package/dist/cjs/base/metadata/model-settings.js +77 -0
  59. package/dist/cjs/base/metadata/model-settings.js.map +1 -0
  60. package/dist/cjs/base/metadata/persistents.d.ts +1 -1
  61. package/dist/cjs/base/metadata/persistents.d.ts.map +1 -1
  62. package/dist/cjs/base/metadata/persistents.js +24 -12
  63. package/dist/cjs/base/metadata/persistents.js.map +1 -1
  64. package/dist/cjs/base/metadata/routes/controller.js +1 -1
  65. package/dist/cjs/base/metadata/routes/controller.js.map +1 -1
  66. package/dist/cjs/base/middlewares/app-error/app-error.middleware.js +3 -3
  67. package/dist/cjs/base/middlewares/app-error/app-error.middleware.js.map +1 -1
  68. package/dist/cjs/base/middlewares/app-error/zod.handler.js +2 -2
  69. package/dist/cjs/base/middlewares/app-error/zod.handler.js.map +1 -1
  70. package/dist/cjs/base/middlewares/form-body/form-body.middleware.js +2 -2
  71. package/dist/cjs/base/middlewares/form-body/form-body.middleware.js.map +1 -1
  72. package/dist/cjs/base/middlewares/not-found/not-found.middleware.js.map +1 -1
  73. package/dist/cjs/base/models/common/utilities.js +1 -1
  74. package/dist/cjs/base/models/common/utilities.js.map +1 -1
  75. package/dist/cjs/base/repositories/common/constants.d.ts +18 -1
  76. package/dist/cjs/base/repositories/common/constants.d.ts.map +1 -1
  77. package/dist/cjs/base/repositories/common/constants.js +22 -2
  78. package/dist/cjs/base/repositories/common/constants.js.map +1 -1
  79. package/dist/cjs/base/repositories/common/types/contracts.d.ts +17 -17
  80. package/dist/cjs/base/repositories/common/types/contracts.d.ts.map +1 -1
  81. package/dist/cjs/base/repositories/common/types/contracts.js.map +1 -1
  82. package/dist/cjs/base/repositories/core/abstract.d.ts +18 -18
  83. package/dist/cjs/base/repositories/core/abstract.d.ts.map +1 -1
  84. package/dist/cjs/base/repositories/core/abstract.js +8 -7
  85. package/dist/cjs/base/repositories/core/abstract.js.map +1 -1
  86. package/dist/cjs/helpers/inversion/common/types/model.d.ts +94 -22
  87. package/dist/cjs/helpers/inversion/common/types/model.d.ts.map +1 -1
  88. package/dist/cjs/helpers/inversion/common/types/model.js.map +1 -1
  89. package/dist/cjs/helpers/inversion/mixins/model.mixin.js +1 -1
  90. package/dist/cjs/helpers/inversion/mixins/model.mixin.js.map +1 -1
  91. package/dist/cjs/helpers/inversion/mixins/repository.mixin.js +1 -1
  92. package/dist/cjs/helpers/inversion/mixins/repository.mixin.js.map +1 -1
  93. package/dist/cjs/repository.d.ts +1 -1
  94. package/dist/cjs/repository.d.ts.map +1 -1
  95. package/dist/cjs/repository.js.map +1 -1
  96. package/dist/esm/base/applications/abstract.js +2 -2
  97. package/dist/esm/base/applications/abstract.js.map +1 -1
  98. package/dist/esm/base/applications/artifact-group.js +1 -1
  99. package/dist/esm/base/applications/artifact-group.js.map +1 -1
  100. package/dist/esm/base/applications/artifact-index.js +11 -11
  101. package/dist/esm/base/applications/artifact-index.js.map +1 -1
  102. package/dist/esm/base/applications/boot-sequence.js +1 -1
  103. package/dist/esm/base/applications/boot-sequence.js.map +1 -1
  104. package/dist/esm/base/applications/cors.d.ts +13 -0
  105. package/dist/esm/base/applications/cors.d.ts.map +1 -0
  106. package/dist/esm/base/applications/cors.js +39 -0
  107. package/dist/esm/base/applications/cors.js.map +1 -0
  108. package/dist/esm/base/applications/deprecations.d.ts +10 -0
  109. package/dist/esm/base/applications/deprecations.d.ts.map +1 -0
  110. package/dist/esm/base/applications/deprecations.js +19 -0
  111. package/dist/esm/base/applications/deprecations.js.map +1 -0
  112. package/dist/esm/base/applications/rest.d.ts.map +1 -1
  113. package/dist/esm/base/applications/rest.js +11 -5
  114. package/dist/esm/base/applications/rest.js.map +1 -1
  115. package/dist/esm/base/auth/authenticate/common/codecs.js +2 -2
  116. package/dist/esm/base/auth/authenticate/common/codecs.js.map +1 -1
  117. package/dist/esm/base/auth/authenticate/providers/authentication.provider.js +1 -1
  118. package/dist/esm/base/auth/authenticate/providers/authentication.provider.js.map +1 -1
  119. package/dist/esm/base/auth/authenticate/strategies/strategy-registry.js +1 -1
  120. package/dist/esm/base/auth/authenticate/strategies/strategy-registry.js.map +1 -1
  121. package/dist/esm/base/auth/authorize/builders/grant.builder.js +12 -12
  122. package/dist/esm/base/auth/authorize/builders/grant.builder.js.map +1 -1
  123. package/dist/esm/base/auth/authorize/builders/permission.builder.js +1 -1
  124. package/dist/esm/base/auth/authorize/builders/permission.builder.js.map +1 -1
  125. package/dist/esm/base/auth/authorize/builders/policy.builder.js +1 -1
  126. package/dist/esm/base/auth/authorize/builders/policy.builder.js.map +1 -1
  127. package/dist/esm/base/auth/authorize/common/constants/authorization.d.ts.map +1 -1
  128. package/dist/esm/base/auth/authorize/common/constants/authorization.js +2 -2
  129. package/dist/esm/base/auth/authorize/common/constants/authorization.js.map +1 -1
  130. package/dist/esm/base/auth/authorize/enforcers/enforcer-registry.js +1 -1
  131. package/dist/esm/base/auth/authorize/enforcers/enforcer-registry.js.map +1 -1
  132. package/dist/esm/base/auth/authorize/providers/authorization.provider.js +3 -3
  133. package/dist/esm/base/auth/authorize/providers/authorization.provider.js.map +1 -1
  134. package/dist/esm/base/controllers/factory/authorize-guard.d.ts +19 -0
  135. package/dist/esm/base/controllers/factory/authorize-guard.d.ts.map +1 -0
  136. package/dist/esm/base/controllers/factory/authorize-guard.js +56 -0
  137. package/dist/esm/base/controllers/factory/authorize-guard.js.map +1 -0
  138. package/dist/esm/base/controllers/factory/controller.d.ts +2 -2
  139. package/dist/esm/base/controllers/factory/controller.d.ts.map +1 -1
  140. package/dist/esm/base/controllers/factory/controller.js +9 -0
  141. package/dist/esm/base/controllers/factory/controller.js.map +1 -1
  142. package/dist/esm/base/controllers/factory/crud/abstract.d.ts +1 -1
  143. package/dist/esm/base/controllers/factory/crud/abstract.d.ts.map +1 -1
  144. package/dist/esm/base/controllers/factory/crud/abstract.js.map +1 -1
  145. package/dist/esm/base/controllers/factory/definition.js +1 -1
  146. package/dist/esm/base/controllers/factory/definition.js.map +1 -1
  147. package/dist/esm/base/controllers/rest/extras.js +5 -5
  148. package/dist/esm/base/controllers/rest/extras.js.map +1 -1
  149. package/dist/esm/base/metadata/injectable.js +1 -1
  150. package/dist/esm/base/metadata/injectable.js.map +1 -1
  151. package/dist/esm/base/metadata/model-settings.d.ts +21 -0
  152. package/dist/esm/base/metadata/model-settings.d.ts.map +1 -0
  153. package/dist/esm/base/metadata/model-settings.js +73 -0
  154. package/dist/esm/base/metadata/model-settings.js.map +1 -0
  155. package/dist/esm/base/metadata/persistents.d.ts +1 -1
  156. package/dist/esm/base/metadata/persistents.d.ts.map +1 -1
  157. package/dist/esm/base/metadata/persistents.js +24 -12
  158. package/dist/esm/base/metadata/persistents.js.map +1 -1
  159. package/dist/esm/base/metadata/routes/controller.js +1 -1
  160. package/dist/esm/base/metadata/routes/controller.js.map +1 -1
  161. package/dist/esm/base/middlewares/app-error/app-error.middleware.js +3 -3
  162. package/dist/esm/base/middlewares/app-error/app-error.middleware.js.map +1 -1
  163. package/dist/esm/base/middlewares/app-error/zod.handler.js +2 -2
  164. package/dist/esm/base/middlewares/app-error/zod.handler.js.map +1 -1
  165. package/dist/esm/base/middlewares/form-body/form-body.middleware.js +2 -2
  166. package/dist/esm/base/middlewares/form-body/form-body.middleware.js.map +1 -1
  167. package/dist/esm/base/middlewares/not-found/not-found.middleware.js.map +1 -1
  168. package/dist/esm/base/models/common/utilities.js +1 -1
  169. package/dist/esm/base/models/common/utilities.js.map +1 -1
  170. package/dist/esm/base/repositories/common/constants.d.ts +18 -1
  171. package/dist/esm/base/repositories/common/constants.d.ts.map +1 -1
  172. package/dist/esm/base/repositories/common/constants.js +20 -1
  173. package/dist/esm/base/repositories/common/constants.js.map +1 -1
  174. package/dist/esm/base/repositories/common/types/contracts.d.ts +17 -17
  175. package/dist/esm/base/repositories/common/types/contracts.d.ts.map +1 -1
  176. package/dist/esm/base/repositories/common/types/contracts.js.map +1 -1
  177. package/dist/esm/base/repositories/core/abstract.d.ts +18 -18
  178. package/dist/esm/base/repositories/core/abstract.d.ts.map +1 -1
  179. package/dist/esm/base/repositories/core/abstract.js +8 -7
  180. package/dist/esm/base/repositories/core/abstract.js.map +1 -1
  181. package/dist/esm/helpers/inversion/common/types/model.d.ts +94 -22
  182. package/dist/esm/helpers/inversion/common/types/model.d.ts.map +1 -1
  183. package/dist/esm/helpers/inversion/common/types/model.js.map +1 -1
  184. package/dist/esm/helpers/inversion/mixins/model.mixin.js +1 -1
  185. package/dist/esm/helpers/inversion/mixins/model.mixin.js.map +1 -1
  186. package/dist/esm/helpers/inversion/mixins/repository.mixin.js +1 -1
  187. package/dist/esm/helpers/inversion/mixins/repository.mixin.js.map +1 -1
  188. package/dist/esm/repository.d.ts +1 -1
  189. package/dist/esm/repository.d.ts.map +1 -1
  190. package/dist/esm/repository.js.map +1 -1
  191. package/package.json +6 -6
@@ -94,7 +94,7 @@ class AuthorizationPolicyBuilder {
94
94
  }
95
95
  /** All `action_inherits` rows for the standard {@link AuthorizationActions.LATTICE}. Seed once, idempotently. */
96
96
  static actionLattice() {
97
- return constants_1.AuthorizationActions.LATTICE.map(action => this.actionInherits(action));
97
+ return constants_1.AuthorizationActions.LATTICE.map((action) => this.actionInherits(action));
98
98
  }
99
99
  /** A domain inherits another (casbin `g3`): a grant in the parent domain cascades to the child. e.g. Merchant ⊂ Organizer. */
100
100
  static domainInherits(opts) {
@@ -1 +1 @@
1
- {"version":3,"file":"policy.builder.js","sourceRoot":"","sources":["../../../../../../src/base/auth/authorize/builders/policy.builder.ts"],"names":[],"mappings":"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","sourcesContent":["import type { IdType } from '@/base';\nimport type { TNullable } from '@venizia/ignis-helpers/common';\nimport type { TAuthorizationAction, TAuthorizationDecision } from '../common/constants';\nimport {\n AuthorizationActions,\n AuthorizationDomainScopes,\n AuthorizationPolicyVariants,\n} from '../common/constants';\n\n/** A grant/assignment domain: a scope literal (`SYSTEM_WIDE`/`ANY_MEMBER`) or a typed domain entity. */\nexport type TPolicyDomainInput = string | { type: string; id: IdType };\n\n/**\n * Explicit on purpose: `TAuthorizationDecision` is `Extract<ValueOf<T>, string | number>`, and its\n * literal members widen to `string` when a method's return type is inferred rather than declared.\n * Without this annotation `grant()`'s `effect` stops satisfying `PolicyDefinition`'s narrowed column.\n * Not exported - `TGrantRow`/`TCustomGrantRow` already name unrelated adapter-side row shapes\n * downstream; consumers derive this shape via `ReturnType<typeof AuthorizationPolicyBuilder.grant>`.\n */\ntype TBuilderGrantRow = {\n variant: typeof AuthorizationPolicyVariants.GRANT.action;\n subjectType: string;\n subjectId: IdType;\n targetType: string;\n targetId: IdType;\n action: string;\n effect: TAuthorizationDecision;\n domainType: TNullable<string>;\n domainId: TNullable<IdType>;\n};\n\n/**\n * What IGNIS itself stores in `PolicyDefinition.metadata`: the operations of a subset grant, read\n * back by `ScopedCasbinAdapter` through `parseCustomGrantMetadata`. An application whose own\n * metadata has a different shape points the adapter at a different column\n * (`entities.policyDefinition.metadata.columnName`) rather than widening this one.\n *\n * Declared here, beside the only writer, so the column type and the row type cannot drift.\n */\nexport type TSubsetGrantMetadata = { ops: string[] };\n\ntype TBuilderCustomGrantRow = Omit<TBuilderGrantRow, 'action'> & {\n action: typeof AuthorizationActions.CUSTOM;\n metadata: TSubsetGrantMetadata;\n};\n\nexport class AuthorizationPolicyBuilder {\n static readonly ACTION_PRINCIPAL = 'Action';\n\n /** A domain as the two columns that store it. `ANY_MEMBER` normalises to null - admitting both spellings would leave one state reachable two ways. */\n private static splitDomain(domain?: TNullable<TPolicyDomainInput>): {\n domainType: TNullable<string>;\n domainId: TNullable<IdType>;\n } {\n if (domain == null || domain === AuthorizationDomainScopes.ANY_MEMBER) {\n return { domainType: null, domainId: null };\n }\n\n if (typeof domain === 'string') {\n return { domainType: domain, domainId: null };\n }\n\n return { domainType: domain.type, domainId: domain.id };\n }\n\n /** A grant (casbin `p`): role/user -> permission, carrying action + effect + domain. A null `domain` means `ANY_MEMBER` (adapter default); pass a scope literal or a typed `{ type, id }` domain. */\n static grant(opts: {\n subject: { type: string; id: IdType };\n permission: { type: string; id: IdType };\n action: string;\n domain?: TNullable<TPolicyDomainInput>;\n effect: TAuthorizationDecision;\n }): TBuilderGrantRow {\n return {\n variant: AuthorizationPolicyVariants.GRANT.action,\n subjectType: opts.subject.type,\n subjectId: opts.subject.id,\n targetType: opts.permission.type,\n targetId: opts.permission.id,\n action: opts.action,\n effect: opts.effect,\n ...AuthorizationPolicyBuilder.splitDomain(opts.domain),\n };\n }\n\n /** A subset grant (casbin `p` x N): role/user -> resource node with the granted operations in metadata. `action` is fixed to the CUSTOM sentinel; the adapter expands `ops` at read time. */\n static customGrant(opts: {\n subject: { type: string; id: IdType };\n permission: { type: string; id: IdType };\n ops: string[];\n domain?: TNullable<TPolicyDomainInput>;\n effect: TAuthorizationDecision;\n }): TBuilderCustomGrantRow {\n return {\n variant: AuthorizationPolicyVariants.GRANT.action,\n subjectType: opts.subject.type,\n subjectId: opts.subject.id,\n targetType: opts.permission.type,\n targetId: opts.permission.id,\n action: AuthorizationActions.CUSTOM,\n effect: opts.effect,\n ...AuthorizationPolicyBuilder.splitDomain(opts.domain),\n metadata: { ops: opts.ops },\n };\n }\n\n /** Assign a role to a user (casbin `g`). `domain` null ⇒ `*` (every domain). */\n static assignRole(opts: {\n user: { type: string; id: IdType };\n role: { type: string; id: IdType };\n domain?: TNullable<TPolicyDomainInput>;\n }) {\n return {\n variant: AuthorizationPolicyVariants.ASSIGN_ROLE.action,\n subjectType: opts.user.type,\n subjectId: opts.user.id,\n targetType: opts.role.type,\n targetId: opts.role.id,\n ...AuthorizationPolicyBuilder.splitDomain(opts.domain),\n };\n }\n\n /** A user joins a domain (casbin `g2`) - backs the `ANY_MEMBER` grant scope. */\n static joinDomain(opts: {\n user: { type: string; id: IdType };\n domain: { type: string; id: IdType };\n }) {\n return {\n variant: AuthorizationPolicyVariants.JOIN_DOMAIN.action,\n subjectType: opts.user.type,\n subjectId: opts.user.id,\n targetType: opts.domain.type,\n targetId: opts.domain.id,\n };\n }\n\n /** A role inherits another role (casbin `g`, shared relation with assign_role). */\n static roleInherits(opts: {\n child: { type: string; id: IdType };\n parent: { type: string; id: IdType };\n }) {\n return {\n variant: AuthorizationPolicyVariants.ROLE_INHERITS.action,\n subjectType: opts.child.type,\n subjectId: opts.child.id,\n targetType: opts.parent.type,\n targetId: opts.parent.id,\n };\n }\n\n /** A resource inherits another (casbin `g4`): a grant on the PARENT covers the CHILD. Many-to-many - a subject may inherit several module parents, one edge each. */\n static resourceInherits(opts: {\n child: { type: string; id: IdType }; // Permission\n parent: { type: string; id: IdType }; // Permission\n }) {\n return {\n variant: AuthorizationPolicyVariants.RESOURCE_INHERITS.action,\n subjectType: opts.child.type,\n subjectId: opts.child.id,\n targetType: opts.parent.type,\n targetId: opts.parent.id,\n };\n }\n\n /** An action inherits another (casbin `g5`): the child action is implied by the parent, e.g. read ⊂ manage. */\n static actionInherits(opts: { child: TAuthorizationAction; parent: TAuthorizationAction }) {\n return {\n variant: AuthorizationPolicyVariants.ACTION_INHERITS.action,\n subjectType: this.ACTION_PRINCIPAL,\n subjectId: opts.child,\n targetType: this.ACTION_PRINCIPAL,\n targetId: opts.parent,\n };\n }\n\n /** All `action_inherits` rows for the standard {@link AuthorizationActions.LATTICE}. Seed once, idempotently. */\n static actionLattice() {\n return AuthorizationActions.LATTICE.map(action => this.actionInherits(action));\n }\n\n /** A domain inherits another (casbin `g3`): a grant in the parent domain cascades to the child. e.g. Merchant ⊂ Organizer. */\n static domainInherits(opts: {\n child: { type: string; id: IdType };\n parent: { type: string; id: IdType };\n }) {\n return {\n variant: AuthorizationPolicyVariants.DOMAIN_INHERITS.action,\n subjectType: opts.child.type,\n subjectId: opts.child.id,\n targetType: opts.parent.type,\n targetId: opts.parent.id,\n };\n }\n\n /** Build a role's coarse grant rows from resolved permission ids. The caller resolves each `resourceCode` (subject/module) to a `Permission` and supplies the lookup; unresolved codes are skipped. */\n static roleGrants(opts: {\n role: { type: string; id: IdType };\n permission: {\n type: string;\n idByCode: ReadonlyMap<string, string>;\n };\n\n grants: ReadonlyArray<{\n resourceCode: string;\n action: string;\n domain?: TNullable<TPolicyDomainInput>;\n effect: TAuthorizationDecision;\n }>;\n }) {\n const rows: Array<ReturnType<typeof AuthorizationPolicyBuilder.grant>> = [];\n\n for (const grant of opts.grants) {\n const permissionId = opts.permission.idByCode.get(grant.resourceCode);\n if (!permissionId) {\n continue;\n }\n\n const policy = AuthorizationPolicyBuilder.grant({\n subject: { type: opts.role.type, id: opts.role.id },\n permission: { type: opts.permission.type, id: permissionId },\n action: grant.action,\n domain: grant.domain,\n effect: grant.effect,\n });\n\n rows.push(policy);\n }\n\n return rows;\n }\n}\n"]}
1
+ {"version":3,"file":"policy.builder.js","sourceRoot":"","sources":["../../../../../../src/base/auth/authorize/builders/policy.builder.ts"],"names":[],"mappings":"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","sourcesContent":["import type { IdType } from '@/base';\nimport type { TNullable } from '@venizia/ignis-helpers/common';\nimport type { TAuthorizationAction, TAuthorizationDecision } from '../common/constants';\nimport {\n AuthorizationActions,\n AuthorizationDomainScopes,\n AuthorizationPolicyVariants,\n} from '../common/constants';\n\n/** A grant/assignment domain: a scope literal (`SYSTEM_WIDE`/`ANY_MEMBER`) or a typed domain entity. */\nexport type TPolicyDomainInput = string | { type: string; id: IdType };\n\n/**\n * Explicit on purpose: `TAuthorizationDecision` is `Extract<ValueOf<T>, string | number>`, and its\n * literal members widen to `string` when a method's return type is inferred rather than declared.\n * Without this annotation `grant()`'s `effect` stops satisfying `PolicyDefinition`'s narrowed column.\n * Not exported - `TGrantRow`/`TCustomGrantRow` already name unrelated adapter-side row shapes\n * downstream; consumers derive this shape via `ReturnType<typeof AuthorizationPolicyBuilder.grant>`.\n */\ntype TBuilderGrantRow = {\n variant: typeof AuthorizationPolicyVariants.GRANT.action;\n subjectType: string;\n subjectId: IdType;\n targetType: string;\n targetId: IdType;\n action: string;\n effect: TAuthorizationDecision;\n domainType: TNullable<string>;\n domainId: TNullable<IdType>;\n};\n\n/**\n * What IGNIS itself stores in `PolicyDefinition.metadata`: the operations of a subset grant, read\n * back by `ScopedCasbinAdapter` through `parseCustomGrantMetadata`. An application whose own\n * metadata has a different shape points the adapter at a different column\n * (`entities.policyDefinition.metadata.columnName`) rather than widening this one.\n *\n * Declared here, beside the only writer, so the column type and the row type cannot drift.\n */\nexport type TSubsetGrantMetadata = { ops: string[] };\n\ntype TBuilderCustomGrantRow = Omit<TBuilderGrantRow, 'action'> & {\n action: typeof AuthorizationActions.CUSTOM;\n metadata: TSubsetGrantMetadata;\n};\n\nexport class AuthorizationPolicyBuilder {\n static readonly ACTION_PRINCIPAL = 'Action';\n\n /** A domain as the two columns that store it. `ANY_MEMBER` normalises to null - admitting both spellings would leave one state reachable two ways. */\n private static splitDomain(domain?: TNullable<TPolicyDomainInput>): {\n domainType: TNullable<string>;\n domainId: TNullable<IdType>;\n } {\n if (domain == null || domain === AuthorizationDomainScopes.ANY_MEMBER) {\n return { domainType: null, domainId: null };\n }\n\n if (typeof domain === 'string') {\n return { domainType: domain, domainId: null };\n }\n\n return { domainType: domain.type, domainId: domain.id };\n }\n\n /** A grant (casbin `p`): role/user -> permission, carrying action + effect + domain. A null `domain` means `ANY_MEMBER` (adapter default); pass a scope literal or a typed `{ type, id }` domain. */\n static grant(opts: {\n subject: { type: string; id: IdType };\n permission: { type: string; id: IdType };\n action: string;\n domain?: TNullable<TPolicyDomainInput>;\n effect: TAuthorizationDecision;\n }): TBuilderGrantRow {\n return {\n variant: AuthorizationPolicyVariants.GRANT.action,\n subjectType: opts.subject.type,\n subjectId: opts.subject.id,\n targetType: opts.permission.type,\n targetId: opts.permission.id,\n action: opts.action,\n effect: opts.effect,\n ...AuthorizationPolicyBuilder.splitDomain(opts.domain),\n };\n }\n\n /** A subset grant (casbin `p` x N): role/user -> resource node with the granted operations in metadata. `action` is fixed to the CUSTOM sentinel; the adapter expands `ops` at read time. */\n static customGrant(opts: {\n subject: { type: string; id: IdType };\n permission: { type: string; id: IdType };\n ops: string[];\n domain?: TNullable<TPolicyDomainInput>;\n effect: TAuthorizationDecision;\n }): TBuilderCustomGrantRow {\n return {\n variant: AuthorizationPolicyVariants.GRANT.action,\n subjectType: opts.subject.type,\n subjectId: opts.subject.id,\n targetType: opts.permission.type,\n targetId: opts.permission.id,\n action: AuthorizationActions.CUSTOM,\n effect: opts.effect,\n ...AuthorizationPolicyBuilder.splitDomain(opts.domain),\n metadata: { ops: opts.ops },\n };\n }\n\n /** Assign a role to a user (casbin `g`). `domain` null ⇒ `*` (every domain). */\n static assignRole(opts: {\n user: { type: string; id: IdType };\n role: { type: string; id: IdType };\n domain?: TNullable<TPolicyDomainInput>;\n }) {\n return {\n variant: AuthorizationPolicyVariants.ASSIGN_ROLE.action,\n subjectType: opts.user.type,\n subjectId: opts.user.id,\n targetType: opts.role.type,\n targetId: opts.role.id,\n ...AuthorizationPolicyBuilder.splitDomain(opts.domain),\n };\n }\n\n /** A user joins a domain (casbin `g2`) - backs the `ANY_MEMBER` grant scope. */\n static joinDomain(opts: {\n user: { type: string; id: IdType };\n domain: { type: string; id: IdType };\n }) {\n return {\n variant: AuthorizationPolicyVariants.JOIN_DOMAIN.action,\n subjectType: opts.user.type,\n subjectId: opts.user.id,\n targetType: opts.domain.type,\n targetId: opts.domain.id,\n };\n }\n\n /** A role inherits another role (casbin `g`, shared relation with assign_role). */\n static roleInherits(opts: {\n child: { type: string; id: IdType };\n parent: { type: string; id: IdType };\n }) {\n return {\n variant: AuthorizationPolicyVariants.ROLE_INHERITS.action,\n subjectType: opts.child.type,\n subjectId: opts.child.id,\n targetType: opts.parent.type,\n targetId: opts.parent.id,\n };\n }\n\n /** A resource inherits another (casbin `g4`): a grant on the PARENT covers the CHILD. Many-to-many - a subject may inherit several module parents, one edge each. */\n static resourceInherits(opts: {\n child: { type: string; id: IdType }; // Permission\n parent: { type: string; id: IdType }; // Permission\n }) {\n return {\n variant: AuthorizationPolicyVariants.RESOURCE_INHERITS.action,\n subjectType: opts.child.type,\n subjectId: opts.child.id,\n targetType: opts.parent.type,\n targetId: opts.parent.id,\n };\n }\n\n /** An action inherits another (casbin `g5`): the child action is implied by the parent, e.g. read ⊂ manage. */\n static actionInherits(opts: { child: TAuthorizationAction; parent: TAuthorizationAction }) {\n return {\n variant: AuthorizationPolicyVariants.ACTION_INHERITS.action,\n subjectType: this.ACTION_PRINCIPAL,\n subjectId: opts.child,\n targetType: this.ACTION_PRINCIPAL,\n targetId: opts.parent,\n };\n }\n\n /** All `action_inherits` rows for the standard {@link AuthorizationActions.LATTICE}. Seed once, idempotently. */\n static actionLattice() {\n return AuthorizationActions.LATTICE.map((action) => this.actionInherits(action));\n }\n\n /** A domain inherits another (casbin `g3`): a grant in the parent domain cascades to the child. e.g. Merchant ⊂ Organizer. */\n static domainInherits(opts: {\n child: { type: string; id: IdType };\n parent: { type: string; id: IdType };\n }) {\n return {\n variant: AuthorizationPolicyVariants.DOMAIN_INHERITS.action,\n subjectType: opts.child.type,\n subjectId: opts.child.id,\n targetType: opts.parent.type,\n targetId: opts.parent.id,\n };\n }\n\n /** Build a role's coarse grant rows from resolved permission ids. The caller resolves each `resourceCode` (subject/module) to a `Permission` and supplies the lookup; unresolved codes are skipped. */\n static roleGrants(opts: {\n role: { type: string; id: IdType };\n permission: {\n type: string;\n idByCode: ReadonlyMap<string, string>;\n };\n\n grants: ReadonlyArray<{\n resourceCode: string;\n action: string;\n domain?: TNullable<TPolicyDomainInput>;\n effect: TAuthorizationDecision;\n }>;\n }) {\n const rows: Array<ReturnType<typeof AuthorizationPolicyBuilder.grant>> = [];\n\n for (const grant of opts.grants) {\n const permissionId = opts.permission.idByCode.get(grant.resourceCode);\n if (!permissionId) {\n continue;\n }\n\n const policy = AuthorizationPolicyBuilder.grant({\n subject: { type: opts.role.type, id: opts.role.id },\n permission: { type: opts.permission.type, id: permissionId },\n action: grant.action,\n domain: grant.domain,\n effect: grant.effect,\n });\n\n rows.push(policy);\n }\n\n return rows;\n }\n}\n"]}
@@ -1 +1 @@
1
- {"version":3,"file":"authorization.d.ts","sourceRoot":"","sources":["../../../../../../../src/base/auth/authorize/common/constants/authorization.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"authorization.d.ts","sourceRoot":"","sources":["../../../../../../../src/base/auth/authorize/common/constants/authorization.ts"],"names":[],"mappings":"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"}
@@ -150,8 +150,8 @@ class AuthorizationPolicyVariants {
150
150
  this.RESOURCE_INHERITS,
151
151
  this.ACTION_INHERITS,
152
152
  ]; }
153
- static { this.ACTION_SCHEME_SET = new Set(this.ALL.map(variant => variant.action.toString())); }
154
- static { this.RULE_SCHEME_SET = new Set(this.ALL.map(variant => variant.rule.toString())); }
153
+ static { this.ACTION_SCHEME_SET = new Set(this.ALL.map((variant) => variant.action.toString())); }
154
+ static { this.RULE_SCHEME_SET = new Set(this.ALL.map((variant) => variant.rule.toString())); }
155
155
  static isValidAction(input) {
156
156
  return this.ACTION_SCHEME_SET.has(input);
157
157
  }
@@ -1 +1 @@
1
- {"version":3,"file":"authorization.js","sourceRoot":"","sources":["../../../../../../../src/base/auth/authorize/common/constants/authorization.ts"],"names":[],"mappings":"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","sourcesContent":["import type { TConstValue } from '@venizia/ignis-helpers/common';\nimport { AuthorizationRole } from '../../models/authorization-role.model';\nimport { CasbinRuleVariants } from './enforcer';\n\nexport class Authorization {\n static readonly RULES = 'authorization.rules';\n static readonly SKIP_AUTHORIZATION = 'authorization.skip';\n static readonly ENFORCER = 'authorization.enforcer';\n static readonly DOMAIN = 'authorization.domain';\n}\n\nexport class AuthorizationActions {\n static readonly CREATE = 'create';\n static readonly UPDATE = 'update';\n static readonly DELETE = 'delete';\n static readonly EXECUTE = 'execute';\n\n static readonly READ = 'read';\n static readonly WRITE = 'write';\n static readonly MANAGE = 'manage';\n\n /** Grant-mode marker for a subset grant carrying `metadata.ops`; never a member of LATTICE. */\n static readonly CUSTOM = 'custom';\n\n static readonly SCHEME_SET = new Set([\n this.CREATE,\n this.UPDATE,\n this.DELETE,\n this.EXECUTE,\n\n this.READ,\n this.WRITE,\n this.MANAGE,\n\n this.CUSTOM,\n ]);\n\n static readonly LATTICE: ReadonlyArray<{\n child: TAuthorizationAction;\n parent: TAuthorizationAction;\n }> = [\n { child: this.READ, parent: this.MANAGE },\n { child: this.WRITE, parent: this.MANAGE },\n { child: this.EXECUTE, parent: this.MANAGE },\n { child: this.CREATE, parent: this.WRITE },\n { child: this.UPDATE, parent: this.WRITE },\n { child: this.DELETE, parent: this.WRITE },\n ];\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n}\nexport type TAuthorizationAction = TConstValue<typeof AuthorizationActions>;\n\nexport class AuthorizationDecisions {\n static readonly ALLOW = 'allow';\n static readonly DENY = 'deny';\n static readonly ABSTAIN = 'abstain';\n\n static readonly SCHEME_SET = new Set([this.ALLOW, this.DENY, this.ABSTAIN]);\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n\n static isAllow(input: string | number): boolean {\n if (typeof input === 'number') {\n return input > 0;\n }\n return input.toLowerCase() === this.ALLOW;\n }\n\n static isDeny(input: string | number): boolean {\n if (typeof input === 'number') {\n return input < 0;\n }\n return input.toLowerCase() === this.DENY;\n }\n\n static isAbstain(input: string | number): boolean {\n if (typeof input === 'number') {\n return input === 0;\n }\n return input.toLowerCase() === this.ABSTAIN;\n }\n}\nexport type TAuthorizationDecision = TConstValue<typeof AuthorizationDecisions>;\n\nexport class AuthorizationRoles {\n static readonly SUPER_ADMIN = AuthorizationRole.build({\n name: 'super-admin',\n priority: 999,\n });\n static readonly ADMIN = AuthorizationRole.build({\n name: 'admin',\n priority: 900,\n });\n static readonly USER = AuthorizationRole.build({\n name: 'user',\n priority: 10,\n });\n static readonly GUEST = AuthorizationRole.build({\n name: 'guest',\n priority: 1,\n });\n static readonly UNKNOWN_USER = AuthorizationRole.build({\n name: 'unknown-user',\n priority: 0,\n });\n\n static readonly SCHEME_SET = new Set<string>([\n this.SUPER_ADMIN.identifier,\n this.ADMIN.identifier,\n this.USER.identifier,\n this.GUEST.identifier,\n this.UNKNOWN_USER.identifier,\n ]);\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n}\n\nexport class AuthorizationDomainScopes {\n /** Grant applies in EVERY domain the subject is a member of (checked via join_domain / g2). */\n static readonly ANY_MEMBER = 'ANY_MEMBER';\n\n /** Grant applies system-wide, bypassing membership - super-admin only. */\n static readonly SYSTEM_WIDE = 'SYSTEM_WIDE';\n\n static readonly SCHEME_SET = new Set([this.ANY_MEMBER, this.SYSTEM_WIDE]);\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n}\nexport type TAuthorizationDomainScope = TConstValue<typeof AuthorizationDomainScopes>;\n\n/** Edge kinds in the `PolicyDefinition` table (each row: subject -> target, `variant` = kind), carrying `action` (DB `variant` value) + `rule` (casbin prefix emitted per edge). Per-USER edges: GRANT, ASSIGN_ROLE, JOIN_DOMAIN; shared org-structure edges: the *_INHERITS ones. */\nexport class AuthorizationPolicyVariants {\n /** Give a Permission to a User/Role (row also carries action / effect / domain). casbin `p`: `p, <Role|User>_<id>, <domain>, <permissionCode>, <action>, <allow|deny>` */\n static readonly GRANT = { action: 'grant', rule: CasbinRuleVariants.P } as const;\n\n /** Give a User a Role (optionally domain-scoped; no domain -> `*` = every domain). casbin `g`: `g, User_<id>, Role_<id>, <domain|*>` */\n static readonly ASSIGN_ROLE = { action: 'assign_role', rule: CasbinRuleVariants.G } as const;\n\n /** A Role inherits another Role (DAG). Shares `g` with ASSIGN_ROLE so user -> role -> parent-role resolves in one lookup. Emitted with domain `*`: `g, Role_<child>, Role_<parent>, *` */\n static readonly ROLE_INHERITS = { action: 'role_inherits', rule: CasbinRuleVariants.G } as const;\n\n /** User is a member of a Domain; powers the `ANY_MEMBER` grant scope via `g2(r.sub, r.dom)`. casbin `g2`: `g2, User_<id>, <Type>_<domainId>` */\n static readonly JOIN_DOMAIN = { action: 'join_domain', rule: CasbinRuleVariants.G2 } as const;\n\n /** DOMAIN axis (`dom`): domain nesting. Matcher: `g3(r.dom, p.dom)` + self-link so an exact domain always matches itself. casbin `g3`: `g3, <Type>_<childId>, <Type>_<parentId>` */\n static readonly DOMAIN_INHERITS = {\n action: 'domain_inherits',\n rule: CasbinRuleVariants.G3,\n } as const;\n\n /** RESOURCE axis (`obj`), NON-standard nesting only - dotted nesting (`Order.findById ⊂ Order`) is handled by `objectMatch` WITHOUT an edge. Matcher: `objectMatch(r.obj, p.obj) || g4(r.obj, p.obj)`, casbin `g4`: `g4, <childCode>, <parentCode>` */\n static readonly RESOURCE_INHERITS = {\n action: 'resource_inherits',\n rule: CasbinRuleVariants.G4,\n } as const;\n\n /** ACTION axis (`act`): a narrow action covered by a broader one; no dotted shortcut, so it needs an explicit edge. Matcher: `g5(r.act, p.act)`, casbin `g5`: `g5, <childAction>, <parentAction>`. g4 + g5 combine multiplicatively: `manage Order` covers a `read OrderItem` request. */\n static readonly ACTION_INHERITS = {\n action: 'action_inherits',\n rule: CasbinRuleVariants.G5,\n } as const;\n\n /** Every edge kind, in declaration order - the one place the scheme sets and the `variant` column's literal type both derive from. */\n static readonly ALL = [\n this.GRANT,\n this.ASSIGN_ROLE,\n this.ROLE_INHERITS,\n this.JOIN_DOMAIN,\n this.DOMAIN_INHERITS,\n this.RESOURCE_INHERITS,\n this.ACTION_INHERITS,\n ] as const;\n\n static readonly ACTION_SCHEME_SET = new Set(this.ALL.map(variant => variant.action.toString()));\n\n static readonly RULE_SCHEME_SET = new Set(this.ALL.map(variant => variant.rule.toString()));\n\n static isValidAction(input: string): boolean {\n return this.ACTION_SCHEME_SET.has(input);\n }\n\n static isValidRule(input: string): boolean {\n return this.RULE_SCHEME_SET.has(input);\n }\n}\n\n/** The `variant` column's full value set, derived from {@link AuthorizationPolicyVariants.ALL} - never hand-list the seven strings again. */\nexport type TAuthorizationPolicyVariant =\n (typeof AuthorizationPolicyVariants.ALL)[number]['action'];\n"]}
1
+ {"version":3,"file":"authorization.js","sourceRoot":"","sources":["../../../../../../../src/base/auth/authorize/common/constants/authorization.ts"],"names":[],"mappings":"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","sourcesContent":["import type { TConstValue } from '@venizia/ignis-helpers/common';\nimport { AuthorizationRole } from '../../models/authorization-role.model';\nimport { CasbinRuleVariants } from './enforcer';\n\nexport class Authorization {\n static readonly RULES = 'authorization.rules';\n static readonly SKIP_AUTHORIZATION = 'authorization.skip';\n static readonly ENFORCER = 'authorization.enforcer';\n static readonly DOMAIN = 'authorization.domain';\n}\n\nexport class AuthorizationActions {\n static readonly CREATE = 'create';\n static readonly UPDATE = 'update';\n static readonly DELETE = 'delete';\n static readonly EXECUTE = 'execute';\n\n static readonly READ = 'read';\n static readonly WRITE = 'write';\n static readonly MANAGE = 'manage';\n\n /** Grant-mode marker for a subset grant carrying `metadata.ops`; never a member of LATTICE. */\n static readonly CUSTOM = 'custom';\n\n static readonly SCHEME_SET = new Set([\n this.CREATE,\n this.UPDATE,\n this.DELETE,\n this.EXECUTE,\n\n this.READ,\n this.WRITE,\n this.MANAGE,\n\n this.CUSTOM,\n ]);\n\n static readonly LATTICE: ReadonlyArray<{\n child: TAuthorizationAction;\n parent: TAuthorizationAction;\n }> = [\n { child: this.READ, parent: this.MANAGE },\n { child: this.WRITE, parent: this.MANAGE },\n { child: this.EXECUTE, parent: this.MANAGE },\n { child: this.CREATE, parent: this.WRITE },\n { child: this.UPDATE, parent: this.WRITE },\n { child: this.DELETE, parent: this.WRITE },\n ];\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n}\nexport type TAuthorizationAction = TConstValue<typeof AuthorizationActions>;\n\nexport class AuthorizationDecisions {\n static readonly ALLOW = 'allow';\n static readonly DENY = 'deny';\n static readonly ABSTAIN = 'abstain';\n\n static readonly SCHEME_SET = new Set([this.ALLOW, this.DENY, this.ABSTAIN]);\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n\n static isAllow(input: string | number): boolean {\n if (typeof input === 'number') {\n return input > 0;\n }\n return input.toLowerCase() === this.ALLOW;\n }\n\n static isDeny(input: string | number): boolean {\n if (typeof input === 'number') {\n return input < 0;\n }\n return input.toLowerCase() === this.DENY;\n }\n\n static isAbstain(input: string | number): boolean {\n if (typeof input === 'number') {\n return input === 0;\n }\n return input.toLowerCase() === this.ABSTAIN;\n }\n}\nexport type TAuthorizationDecision = TConstValue<typeof AuthorizationDecisions>;\n\nexport class AuthorizationRoles {\n static readonly SUPER_ADMIN = AuthorizationRole.build({\n name: 'super-admin',\n priority: 999,\n });\n static readonly ADMIN = AuthorizationRole.build({\n name: 'admin',\n priority: 900,\n });\n static readonly USER = AuthorizationRole.build({\n name: 'user',\n priority: 10,\n });\n static readonly GUEST = AuthorizationRole.build({\n name: 'guest',\n priority: 1,\n });\n static readonly UNKNOWN_USER = AuthorizationRole.build({\n name: 'unknown-user',\n priority: 0,\n });\n\n static readonly SCHEME_SET = new Set<string>([\n this.SUPER_ADMIN.identifier,\n this.ADMIN.identifier,\n this.USER.identifier,\n this.GUEST.identifier,\n this.UNKNOWN_USER.identifier,\n ]);\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n}\n\nexport class AuthorizationDomainScopes {\n /** Grant applies in EVERY domain the subject is a member of (checked via join_domain / g2). */\n static readonly ANY_MEMBER = 'ANY_MEMBER';\n\n /** Grant applies system-wide, bypassing membership - super-admin only. */\n static readonly SYSTEM_WIDE = 'SYSTEM_WIDE';\n\n static readonly SCHEME_SET = new Set([this.ANY_MEMBER, this.SYSTEM_WIDE]);\n\n static isValid(input: string): boolean {\n return this.SCHEME_SET.has(input);\n }\n}\nexport type TAuthorizationDomainScope = TConstValue<typeof AuthorizationDomainScopes>;\n\n/** Edge kinds in the `PolicyDefinition` table (each row: subject -> target, `variant` = kind), carrying `action` (DB `variant` value) + `rule` (casbin prefix emitted per edge). Per-USER edges: GRANT, ASSIGN_ROLE, JOIN_DOMAIN; shared org-structure edges: the *_INHERITS ones. */\nexport class AuthorizationPolicyVariants {\n /** Give a Permission to a User/Role (row also carries action / effect / domain). casbin `p`: `p, <Role|User>_<id>, <domain>, <permissionCode>, <action>, <allow|deny>` */\n static readonly GRANT = { action: 'grant', rule: CasbinRuleVariants.P } as const;\n\n /** Give a User a Role (optionally domain-scoped; no domain -> `*` = every domain). casbin `g`: `g, User_<id>, Role_<id>, <domain|*>` */\n static readonly ASSIGN_ROLE = { action: 'assign_role', rule: CasbinRuleVariants.G } as const;\n\n /** A Role inherits another Role (DAG). Shares `g` with ASSIGN_ROLE so user -> role -> parent-role resolves in one lookup. Emitted with domain `*`: `g, Role_<child>, Role_<parent>, *` */\n static readonly ROLE_INHERITS = { action: 'role_inherits', rule: CasbinRuleVariants.G } as const;\n\n /** User is a member of a Domain; powers the `ANY_MEMBER` grant scope via `g2(r.sub, r.dom)`. casbin `g2`: `g2, User_<id>, <Type>_<domainId>` */\n static readonly JOIN_DOMAIN = { action: 'join_domain', rule: CasbinRuleVariants.G2 } as const;\n\n /** DOMAIN axis (`dom`): domain nesting. Matcher: `g3(r.dom, p.dom)` + self-link so an exact domain always matches itself. casbin `g3`: `g3, <Type>_<childId>, <Type>_<parentId>` */\n static readonly DOMAIN_INHERITS = {\n action: 'domain_inherits',\n rule: CasbinRuleVariants.G3,\n } as const;\n\n /** RESOURCE axis (`obj`), NON-standard nesting only - dotted nesting (`Order.findById ⊂ Order`) is handled by `objectMatch` WITHOUT an edge. Matcher: `objectMatch(r.obj, p.obj) || g4(r.obj, p.obj)`, casbin `g4`: `g4, <childCode>, <parentCode>` */\n static readonly RESOURCE_INHERITS = {\n action: 'resource_inherits',\n rule: CasbinRuleVariants.G4,\n } as const;\n\n /** ACTION axis (`act`): a narrow action covered by a broader one; no dotted shortcut, so it needs an explicit edge. Matcher: `g5(r.act, p.act)`, casbin `g5`: `g5, <childAction>, <parentAction>`. g4 + g5 combine multiplicatively: `manage Order` covers a `read OrderItem` request. */\n static readonly ACTION_INHERITS = {\n action: 'action_inherits',\n rule: CasbinRuleVariants.G5,\n } as const;\n\n /** Every edge kind, in declaration order - the one place the scheme sets and the `variant` column's literal type both derive from. */\n static readonly ALL = [\n this.GRANT,\n this.ASSIGN_ROLE,\n this.ROLE_INHERITS,\n this.JOIN_DOMAIN,\n this.DOMAIN_INHERITS,\n this.RESOURCE_INHERITS,\n this.ACTION_INHERITS,\n ] as const;\n\n static readonly ACTION_SCHEME_SET = new Set(this.ALL.map((variant) => variant.action.toString()));\n\n static readonly RULE_SCHEME_SET = new Set(this.ALL.map((variant) => variant.rule.toString()));\n\n static isValidAction(input: string): boolean {\n return this.ACTION_SCHEME_SET.has(input);\n }\n\n static isValidRule(input: string): boolean {\n return this.RULE_SCHEME_SET.has(input);\n }\n}\n\n/** The `variant` column's full value set, derived from {@link AuthorizationPolicyVariants.ALL} - never hand-list the seven strings again. */\nexport type TAuthorizationPolicyVariant =\n (typeof AuthorizationPolicyVariants.ALL)[number]['action'];\n"]}
@@ -32,7 +32,7 @@ class AuthorizationEnforcerRegistry extends base_1.AbstractAuthRegistry {
32
32
  }
33
33
  register(opts) {
34
34
  const { container, enforcers } = opts;
35
- const names = enforcers.map(e => e.name);
35
+ const names = enforcers.map((e) => e.name);
36
36
  const duplicateNames = names.filter((n, i) => names.indexOf(n) !== i);
37
37
  if (duplicateNames.length) {
38
38
  throw (0, core_1.getError)({
@@ -1 +1 @@
1
- {"version":3,"file":"enforcer-registry.js","sourceRoot":"","sources":["../../../../../../src/base/auth/authorize/enforcers/enforcer-registry.ts"],"names":[],"mappings":"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","sourcesContent":["import { SingletonRealm } from '@/helpers/singleton-realm';\nimport type { Container } from '@/helpers/inversion/container';\nimport type { TClass, TNullable } from '@venizia/ignis-helpers/common';\nimport { getError } from '@venizia/ignis-helpers/core';\nimport type { IAuthUser } from '../../authenticate/common/types';\nimport { AbstractAuthRegistry } from '../../base';\nimport type {\n AuthorizationEnforcerTypes,\n IAuthorizationEnforcer,\n IAuthorizationUser,\n IAuthorizeOptions,\n ICasbinEnforcerOptions,\n} from '../common';\nimport { Authorization, AuthorizeBindingKeys } from '../common';\n\nexport class AuthorizationEnforcerRegistry extends AbstractAuthRegistry<IAuthorizationEnforcer> {\n static readonly SINGLETON_REAL_KEY = 'authorization-enforcer-registry';\n\n private configuredEnforcers: Set<string>;\n\n /** In-flight `configure()` calls, so concurrent first requests share one warmup instead of racing. */\n private pendingConfigurations: Map<string, Promise<void>>;\n\n /** Set by AuthorizeComponent from the application container. Held here because the descriptor scan\n * below sees only registered enforcers, and `defaultDecision` has to be readable when there are none. */\n private applicationOptions: TNullable<IAuthorizeOptions> = null;\n\n constructor() {\n super({ scope: AuthorizationEnforcerRegistry.name });\n this.configuredEnforcers = new Set();\n this.pendingConfigurations = new Map();\n }\n\n static getInstance() {\n return SingletonRealm.resolve({\n key: AuthorizationEnforcerRegistry.SINGLETON_REAL_KEY,\n create: () => new AuthorizationEnforcerRegistry(),\n });\n }\n\n override reset(): void {\n super.reset();\n this.configuredEnforcers.clear();\n this.pendingConfigurations.clear();\n this.applicationOptions = null;\n }\n\n protected getBindingPrefix(): string {\n return Authorization.ENFORCER;\n }\n\n register(opts: {\n container: Container;\n enforcers: Array<\n | {\n enforcer: TClass<IAuthorizationEnforcer>;\n name: string;\n type: typeof AuthorizationEnforcerTypes.CASBIN;\n options?: ICasbinEnforcerOptions;\n }\n | {\n enforcer: TClass<IAuthorizationEnforcer>;\n name: string;\n type: typeof AuthorizationEnforcerTypes.CUSTOM;\n options?: unknown;\n }\n >;\n }) {\n const { container, enforcers } = opts;\n\n const names = enforcers.map(e => e.name);\n const duplicateNames = names.filter((n, i) => names.indexOf(n) !== i);\n if (duplicateNames.length) {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Duplicate enforcer name(s): ${[...new Set(duplicateNames)].join(', ')}`,\n });\n }\n\n for (const { enforcer, name, options } of enforcers) {\n if (this.descriptors.has(name)) {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Enforcer already registered: ${name}`,\n });\n }\n\n this.registerDescriptor({ container, target: enforcer, name });\n\n if (options) {\n container.bind({ key: AuthorizeBindingKeys.enforcerOptions(name) }).toValue(options);\n }\n }\n\n return this;\n }\n\n hasEnforcers(): boolean {\n return this.descriptors.size > 0;\n }\n\n getDefaultEnforcerName(): string {\n return this.getDefaultName();\n }\n\n /**\n * The PROMISE is memoised, not just the completed flag.\n *\n * `configure()` yields (it dynamic-imports casbin), and the flag was only set after the await -\n * so a burst of first requests each saw an unconfigured enforcer and each built a full pool.\n * Measured: 40 concurrent first requests produced 40 configure() calls and 640 enforcers.\n * The entry is dropped on rejection so a failed warmup does not poison every later request.\n */\n async resolveEnforcer(opts: { name: string }): Promise<IAuthorizationEnforcer> {\n const enforcer = this.resolveDescriptor(opts);\n\n if (this.configuredEnforcers.has(opts.name)) {\n return enforcer;\n }\n\n const inFlight = this.pendingConfigurations.get(opts.name);\n if (inFlight) {\n await inFlight;\n return enforcer;\n }\n\n // `Promise.resolve` because `configure()` is declared `ValueOrPromise<void>` - a synchronous\n // implementation returns plain `void`, which has no `.then`.\n const pending = Promise.resolve(enforcer.configure())\n .then(() => {\n this.configuredEnforcers.add(opts.name);\n })\n .finally(() => {\n this.pendingConfigurations.delete(opts.name);\n });\n\n this.pendingConfigurations.set(opts.name, pending);\n\n await pending;\n return enforcer;\n }\n\n /** Drop a user's cached policies on the resolved enforcer. Lazy - next request rebuilds. */\n async invalidateUserCache(opts: {\n user: IAuthorizationUser;\n enforcerName?: string;\n }): Promise<{ invalidatedKeys: number }> {\n const name = opts.enforcerName ?? this.getDefaultEnforcerName();\n const enforcer = await this.resolveEnforcer({ name });\n\n // Cache management is an optional IAuthorizationEnforcer capability - feature-detect it.\n if (typeof enforcer.invalidateUserCache !== 'function') {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Enforcer \"${name}\" does not support cache invalidation`,\n });\n }\n\n return enforcer.invalidateUserCache({ user: opts.user });\n }\n\n /** Drop then immediately rebuild + re-cache a user's policies on the resolved enforcer. */\n async rebuildUserCache(opts: {\n user: { principalType: string } & IAuthUser;\n enforcerName?: string;\n }): Promise<{ cacheKey: string; lineCount: number }> {\n const name = opts.enforcerName ?? this.getDefaultEnforcerName();\n const enforcer = await this.resolveEnforcer({ name });\n\n if (typeof enforcer.rebuildUserCache !== 'function') {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Enforcer \"${name}\" does not support cache invalidation`,\n });\n }\n\n return enforcer.rebuildUserCache({ user: opts.user });\n }\n\n /** Options bound on the application, independent of any enforcer. */\n setOptions(opts: { options: IAuthorizeOptions }): void {\n this.applicationOptions = opts.options;\n }\n\n resolveOptions(): IAuthorizeOptions | undefined {\n if (this.applicationOptions) {\n return this.applicationOptions;\n }\n\n for (const [, metadata] of this.descriptors) {\n const { container } = metadata;\n const options = container.get<IAuthorizeOptions>({\n key: AuthorizeBindingKeys.OPTIONS,\n isOptional: true,\n });\n if (options) {\n return options;\n }\n }\n return undefined;\n }\n}\n"]}
1
+ {"version":3,"file":"enforcer-registry.js","sourceRoot":"","sources":["../../../../../../src/base/auth/authorize/enforcers/enforcer-registry.ts"],"names":[],"mappings":"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","sourcesContent":["import { SingletonRealm } from '@/helpers/singleton-realm';\nimport type { Container } from '@/helpers/inversion/container';\nimport type { TClass, TNullable } from '@venizia/ignis-helpers/common';\nimport { getError } from '@venizia/ignis-helpers/core';\nimport type { IAuthUser } from '../../authenticate/common/types';\nimport { AbstractAuthRegistry } from '../../base';\nimport type {\n AuthorizationEnforcerTypes,\n IAuthorizationEnforcer,\n IAuthorizationUser,\n IAuthorizeOptions,\n ICasbinEnforcerOptions,\n} from '../common';\nimport { Authorization, AuthorizeBindingKeys } from '../common';\n\nexport class AuthorizationEnforcerRegistry extends AbstractAuthRegistry<IAuthorizationEnforcer> {\n static readonly SINGLETON_REAL_KEY = 'authorization-enforcer-registry';\n\n private configuredEnforcers: Set<string>;\n\n /** In-flight `configure()` calls, so concurrent first requests share one warmup instead of racing. */\n private pendingConfigurations: Map<string, Promise<void>>;\n\n /** Set by AuthorizeComponent from the application container. Held here because the descriptor scan\n * below sees only registered enforcers, and `defaultDecision` has to be readable when there are none. */\n private applicationOptions: TNullable<IAuthorizeOptions> = null;\n\n constructor() {\n super({ scope: AuthorizationEnforcerRegistry.name });\n this.configuredEnforcers = new Set();\n this.pendingConfigurations = new Map();\n }\n\n static getInstance() {\n return SingletonRealm.resolve({\n key: AuthorizationEnforcerRegistry.SINGLETON_REAL_KEY,\n create: () => new AuthorizationEnforcerRegistry(),\n });\n }\n\n override reset(): void {\n super.reset();\n this.configuredEnforcers.clear();\n this.pendingConfigurations.clear();\n this.applicationOptions = null;\n }\n\n protected getBindingPrefix(): string {\n return Authorization.ENFORCER;\n }\n\n register(opts: {\n container: Container;\n enforcers: Array<\n | {\n enforcer: TClass<IAuthorizationEnforcer>;\n name: string;\n type: typeof AuthorizationEnforcerTypes.CASBIN;\n options?: ICasbinEnforcerOptions;\n }\n | {\n enforcer: TClass<IAuthorizationEnforcer>;\n name: string;\n type: typeof AuthorizationEnforcerTypes.CUSTOM;\n options?: unknown;\n }\n >;\n }) {\n const { container, enforcers } = opts;\n\n const names = enforcers.map((e) => e.name);\n const duplicateNames = names.filter((n, i) => names.indexOf(n) !== i);\n if (duplicateNames.length) {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Duplicate enforcer name(s): ${[...new Set(duplicateNames)].join(', ')}`,\n });\n }\n\n for (const { enforcer, name, options } of enforcers) {\n if (this.descriptors.has(name)) {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Enforcer already registered: ${name}`,\n });\n }\n\n this.registerDescriptor({ container, target: enforcer, name });\n\n if (options) {\n container.bind({ key: AuthorizeBindingKeys.enforcerOptions(name) }).toValue(options);\n }\n }\n\n return this;\n }\n\n hasEnforcers(): boolean {\n return this.descriptors.size > 0;\n }\n\n getDefaultEnforcerName(): string {\n return this.getDefaultName();\n }\n\n /**\n * The PROMISE is memoised, not just the completed flag.\n *\n * `configure()` yields (it dynamic-imports casbin), and the flag was only set after the await -\n * so a burst of first requests each saw an unconfigured enforcer and each built a full pool.\n * Measured: 40 concurrent first requests produced 40 configure() calls and 640 enforcers.\n * The entry is dropped on rejection so a failed warmup does not poison every later request.\n */\n async resolveEnforcer(opts: { name: string }): Promise<IAuthorizationEnforcer> {\n const enforcer = this.resolveDescriptor(opts);\n\n if (this.configuredEnforcers.has(opts.name)) {\n return enforcer;\n }\n\n const inFlight = this.pendingConfigurations.get(opts.name);\n if (inFlight) {\n await inFlight;\n return enforcer;\n }\n\n // `Promise.resolve` because `configure()` is declared `ValueOrPromise<void>` - a synchronous\n // implementation returns plain `void`, which has no `.then`.\n const pending = Promise.resolve(enforcer.configure())\n .then(() => {\n this.configuredEnforcers.add(opts.name);\n })\n .finally(() => {\n this.pendingConfigurations.delete(opts.name);\n });\n\n this.pendingConfigurations.set(opts.name, pending);\n\n await pending;\n return enforcer;\n }\n\n /** Drop a user's cached policies on the resolved enforcer. Lazy - next request rebuilds. */\n async invalidateUserCache(opts: {\n user: IAuthorizationUser;\n enforcerName?: string;\n }): Promise<{ invalidatedKeys: number }> {\n const name = opts.enforcerName ?? this.getDefaultEnforcerName();\n const enforcer = await this.resolveEnforcer({ name });\n\n // Cache management is an optional IAuthorizationEnforcer capability - feature-detect it.\n if (typeof enforcer.invalidateUserCache !== 'function') {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Enforcer \"${name}\" does not support cache invalidation`,\n });\n }\n\n return enforcer.invalidateUserCache({ user: opts.user });\n }\n\n /** Drop then immediately rebuild + re-cache a user's policies on the resolved enforcer. */\n async rebuildUserCache(opts: {\n user: { principalType: string } & IAuthUser;\n enforcerName?: string;\n }): Promise<{ cacheKey: string; lineCount: number }> {\n const name = opts.enforcerName ?? this.getDefaultEnforcerName();\n const enforcer = await this.resolveEnforcer({ name });\n\n if (typeof enforcer.rebuildUserCache !== 'function') {\n throw getError({\n message: `[AuthorizationEnforcerRegistry] Enforcer \"${name}\" does not support cache invalidation`,\n });\n }\n\n return enforcer.rebuildUserCache({ user: opts.user });\n }\n\n /** Options bound on the application, independent of any enforcer. */\n setOptions(opts: { options: IAuthorizeOptions }): void {\n this.applicationOptions = opts.options;\n }\n\n resolveOptions(): IAuthorizeOptions | undefined {\n if (this.applicationOptions) {\n return this.applicationOptions;\n }\n\n for (const [, metadata] of this.descriptors) {\n const { container } = metadata;\n const options = container.get<IAuthorizeOptions>({\n key: AuthorizeBindingKeys.OPTIONS,\n isOptional: true,\n });\n if (options) {\n return options;\n }\n }\n return undefined;\n }\n}\n"]}
@@ -14,7 +14,7 @@ class AuthorizationProvider extends core_1.BaseHelper {
14
14
  super({ scope: AuthorizationProvider.name });
15
15
  }
16
16
  value() {
17
- return opts => {
17
+ return (opts) => {
18
18
  return this.createAuthorizeMiddleware(opts);
19
19
  };
20
20
  }
@@ -40,11 +40,11 @@ class AuthorizationProvider extends core_1.BaseHelper {
40
40
  if (needsRoleCheck) {
41
41
  const userRoles = this.extractUserRoles({ user });
42
42
  if (options?.alwaysAllowRoles?.length &&
43
- userRoles.some(r => options.alwaysAllowRoles.includes(r))) {
43
+ userRoles.some((r) => options.alwaysAllowRoles.includes(r))) {
44
44
  logger.warn('SKIP checking authorization | User has always-allow role | userRoles: %s', userRoles);
45
45
  return next();
46
46
  }
47
- if (spec.allowedRoles?.length && userRoles.some(r => spec.allowedRoles.includes(r))) {
47
+ if (spec.allowedRoles?.length && userRoles.some((r) => spec.allowedRoles.includes(r))) {
48
48
  logger.warn('GRANT access | User has allowed role for route | userRoles: %s', userRoles);
49
49
  return next();
50
50
  }
@@ -1 +1 @@
1
- {"version":3,"file":"authorization.provider.js","sourceRoot":"","sources":["../../../../../../src/base/auth/authorize/providers/authorization.provider.ts"],"names":[],"mappings":"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","sourcesContent":["import { asTypedContext } from '@/base/controllers/context';\nimport { BaseHelper, getError } from '@venizia/ignis-helpers/core';\nimport type { IProvider } from '@venizia/ignis-inversion';\nimport { createMiddleware } from 'hono/factory';\nimport type { IAuthUser } from '../../authenticate/common/types';\n// Deep import (not the authenticate barrel): the barrel re-exports ./controllers, whose factory extends BaseRestController - a value import here forms the base/controllers <-> auth init cycle.\nimport { Authentication } from '../../authenticate/common/constants';\nimport type { IAuthorizationSpec, TAuthorizeFn } from '../common';\nimport { Authorization, AuthorizationDecisions, AuthorizationErrors } from '../common';\nimport { AuthorizationEnforcerRegistry } from '../enforcers/enforcer-registry';\nimport { resolveRequestDomain } from './request-domain';\n\nexport class AuthorizationProvider extends BaseHelper implements IProvider<TAuthorizeFn> {\n constructor() {\n super({ scope: AuthorizationProvider.name });\n }\n\n value(): TAuthorizeFn {\n return opts => {\n return this.createAuthorizeMiddleware(opts);\n };\n }\n\n private createAuthorizeMiddleware(opts: { spec: IAuthorizationSpec; enforcerName?: string }) {\n const { spec, enforcerName } = opts;\n const logger = this.logger.for(this.createAuthorizeMiddleware.name);\n\n return createMiddleware(async (context, next) => {\n const registry = AuthorizationEnforcerRegistry.getInstance();\n const options = registry.resolveOptions();\n\n const isSkipAuthorize = context.get(Authorization.SKIP_AUTHORIZATION);\n if (isSkipAuthorize) {\n logger.warn('SKIP checking authorization | path: %s', context.req.path);\n return next();\n }\n\n const user = context.get(Authentication.CURRENT_USER) as IAuthUser | undefined;\n if (!user) {\n throw getError({\n error: AuthorizationErrors.UNAUTHENTICATED,\n message: 'Authorization failed: No authenticated user found',\n });\n }\n\n const needsRoleCheck =\n Boolean(options?.alwaysAllowRoles?.length) || Boolean(spec.allowedRoles?.length);\n if (needsRoleCheck) {\n const userRoles = this.extractUserRoles({ user });\n\n if (\n options?.alwaysAllowRoles?.length &&\n userRoles.some(r => options.alwaysAllowRoles!.includes(r))\n ) {\n logger.warn(\n 'SKIP checking authorization | User has always-allow role | userRoles: %s',\n userRoles,\n );\n return next();\n }\n\n if (spec.allowedRoles?.length && userRoles.some(r => spec.allowedRoles!.includes(r))) {\n logger.warn('GRANT access | User has allowed role for route | userRoles: %s', userRoles);\n return next();\n }\n }\n\n const votersList = spec.voters ?? [];\n for (const voter of votersList) {\n const decision = await voter({\n user,\n action: spec.action,\n resource: spec.resource,\n context: asTypedContext(context),\n });\n\n if (decision === AuthorizationDecisions.DENY) {\n throw getError({\n error: AuthorizationErrors.DENIED_BY_VOTER,\n message: `Authorization denied by voter | action: ${spec.action} | resource: ${spec.resource}`,\n messageArgs: { action: spec.action, resource: spec.resource },\n });\n }\n\n if (decision === AuthorizationDecisions.ALLOW) {\n await next();\n return;\n }\n\n // ABSTAIN → continue to enforcer\n }\n\n if (!registry.hasEnforcers()) {\n const noEnforcerDecision = options?.defaultDecision ?? AuthorizationDecisions.DENY;\n\n if (noEnforcerDecision === AuthorizationDecisions.ALLOW) {\n logger.warn(\n 'ALLOW checking authorization | No enforcers registered | path: %s',\n context.req.path,\n );\n return next();\n }\n\n throw getError({\n error: AuthorizationErrors.ENFORCER_NOT_REGISTERED,\n message: `Authorization failed: authorize() was declared for this route but no enforcer is registered | path: ${context.req.path}`,\n });\n }\n\n const resolvedName = enforcerName ?? registry.getDefaultEnforcerName();\n const enforcer = await registry.resolveEnforcer({ name: resolvedName });\n\n // Only resolve domain scope when it is actually in play (per-route domain OR a configured global resolver) - avoids a resolver call (possible DB hit) for legacy enforcers.\n //\n // Held in a LOCAL, not read back out of the context. One middleware is pushed per spec onto\n // the same Hono context, so reading `Authorization.DOMAIN` at decision time meant a\n // domain-less spec inherited the tenant domain a PREVIOUS spec had written - silently\n // widening a check that should have run at SYSTEM_WIDE. The context is still set, for\n // observability, but nothing decides on it.\n const domainScope =\n spec.domain || options?.domainResolver\n ? await resolveRequestDomain({\n spec,\n context: asTypedContext(context),\n options,\n })\n : undefined;\n context.set(Authorization.DOMAIN, domainScope);\n\n // Keyed by enforcer. The slot used to hold one rule set for the whole request, so a second\n // `authorize()` naming a DIFFERENT enforcer evaluated against the first enforcer's rules -\n // granting where its own policy set denies.\n //\n // `instanceof Map`, not a truthiness test: the slot previously held a bare rule set, so\n // anything that pre-populates it with the old shape would otherwise reach `.get` on a value\n // that has no such method and take the request down with a TypeError.\n const existingRules = context.get(Authorization.RULES);\n const rulesByEnforcer =\n existingRules instanceof Map ? existingRules : new Map<string, unknown>();\n let rules = rulesByEnforcer.get(resolvedName);\n\n if (!rules) {\n if (!user.principalType) {\n throw getError({\n error: AuthorizationErrors.PRINCIPAL_TYPE_MISSING,\n message:\n 'Authorization failed: user.principalType is required for enforcer-based authorization',\n });\n }\n\n rules = await enforcer.buildRules({\n user: user as { principalType: string } & IAuthUser,\n context: asTypedContext(context),\n });\n rulesByEnforcer.set(resolvedName, rules);\n context.set(Authorization.RULES, rulesByEnforcer);\n }\n\n let decision = await enforcer.evaluate({\n rules,\n request: {\n action: spec.action,\n resource: spec.resource,\n conditions: spec.conditions,\n domain: domainScope,\n },\n context: asTypedContext(context),\n });\n\n if (decision === AuthorizationDecisions.ABSTAIN) {\n decision = options?.defaultDecision ?? AuthorizationDecisions.DENY;\n }\n\n if (decision !== AuthorizationDecisions.ALLOW) {\n throw getError({\n error: AuthorizationErrors.DENIED,\n message: `Authorization denied | action: ${spec.action} | resource: ${spec.resource}`,\n messageArgs: { action: spec.action, resource: spec.resource },\n });\n }\n\n await next();\n });\n }\n\n private extractUserRoles(opts: { user: IAuthUser }): string[] {\n const { user } = opts;\n const roles = user.roles;\n\n if (!Array.isArray(roles)) {\n return [];\n }\n\n return roles.map((r: string | { identifier?: string; name?: string; id?: unknown }) => {\n if (typeof r === 'string') {\n return r;\n }\n return r.identifier ?? r.name ?? String(r.id ?? '');\n });\n }\n}\n"]}
1
+ {"version":3,"file":"authorization.provider.js","sourceRoot":"","sources":["../../../../../../src/base/auth/authorize/providers/authorization.provider.ts"],"names":[],"mappings":"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","sourcesContent":["import { asTypedContext } from '@/base/controllers/context';\nimport { BaseHelper, getError } from '@venizia/ignis-helpers/core';\nimport type { IProvider } from '@venizia/ignis-inversion';\nimport { createMiddleware } from 'hono/factory';\nimport type { IAuthUser } from '../../authenticate/common/types';\n// Deep import (not the authenticate barrel): the barrel re-exports ./controllers, whose factory extends BaseRestController - a value import here forms the base/controllers <-> auth init cycle.\nimport { Authentication } from '../../authenticate/common/constants';\nimport type { IAuthorizationSpec, TAuthorizeFn } from '../common';\nimport { Authorization, AuthorizationDecisions, AuthorizationErrors } from '../common';\nimport { AuthorizationEnforcerRegistry } from '../enforcers/enforcer-registry';\nimport { resolveRequestDomain } from './request-domain';\n\nexport class AuthorizationProvider extends BaseHelper implements IProvider<TAuthorizeFn> {\n constructor() {\n super({ scope: AuthorizationProvider.name });\n }\n\n value(): TAuthorizeFn {\n return (opts) => {\n return this.createAuthorizeMiddleware(opts);\n };\n }\n\n private createAuthorizeMiddleware(opts: { spec: IAuthorizationSpec; enforcerName?: string }) {\n const { spec, enforcerName } = opts;\n const logger = this.logger.for(this.createAuthorizeMiddleware.name);\n\n return createMiddleware(async (context, next) => {\n const registry = AuthorizationEnforcerRegistry.getInstance();\n const options = registry.resolveOptions();\n\n const isSkipAuthorize = context.get(Authorization.SKIP_AUTHORIZATION);\n if (isSkipAuthorize) {\n logger.warn('SKIP checking authorization | path: %s', context.req.path);\n return next();\n }\n\n const user = context.get(Authentication.CURRENT_USER) as IAuthUser | undefined;\n if (!user) {\n throw getError({\n error: AuthorizationErrors.UNAUTHENTICATED,\n message: 'Authorization failed: No authenticated user found',\n });\n }\n\n const needsRoleCheck =\n Boolean(options?.alwaysAllowRoles?.length) || Boolean(spec.allowedRoles?.length);\n if (needsRoleCheck) {\n const userRoles = this.extractUserRoles({ user });\n\n if (\n options?.alwaysAllowRoles?.length &&\n userRoles.some((r) => options.alwaysAllowRoles!.includes(r))\n ) {\n logger.warn(\n 'SKIP checking authorization | User has always-allow role | userRoles: %s',\n userRoles,\n );\n return next();\n }\n\n if (spec.allowedRoles?.length && userRoles.some((r) => spec.allowedRoles!.includes(r))) {\n logger.warn('GRANT access | User has allowed role for route | userRoles: %s', userRoles);\n return next();\n }\n }\n\n const votersList = spec.voters ?? [];\n for (const voter of votersList) {\n const decision = await voter({\n user,\n action: spec.action,\n resource: spec.resource,\n context: asTypedContext(context),\n });\n\n if (decision === AuthorizationDecisions.DENY) {\n throw getError({\n error: AuthorizationErrors.DENIED_BY_VOTER,\n message: `Authorization denied by voter | action: ${spec.action} | resource: ${spec.resource}`,\n messageArgs: { action: spec.action, resource: spec.resource },\n });\n }\n\n if (decision === AuthorizationDecisions.ALLOW) {\n await next();\n return;\n }\n\n // ABSTAIN → continue to enforcer\n }\n\n if (!registry.hasEnforcers()) {\n const noEnforcerDecision = options?.defaultDecision ?? AuthorizationDecisions.DENY;\n\n if (noEnforcerDecision === AuthorizationDecisions.ALLOW) {\n logger.warn(\n 'ALLOW checking authorization | No enforcers registered | path: %s',\n context.req.path,\n );\n return next();\n }\n\n throw getError({\n error: AuthorizationErrors.ENFORCER_NOT_REGISTERED,\n message: `Authorization failed: authorize() was declared for this route but no enforcer is registered | path: ${context.req.path}`,\n });\n }\n\n const resolvedName = enforcerName ?? registry.getDefaultEnforcerName();\n const enforcer = await registry.resolveEnforcer({ name: resolvedName });\n\n // Only resolve domain scope when it is actually in play (per-route domain OR a configured global resolver) - avoids a resolver call (possible DB hit) for legacy enforcers.\n //\n // Held in a LOCAL, not read back out of the context. One middleware is pushed per spec onto\n // the same Hono context, so reading `Authorization.DOMAIN` at decision time meant a\n // domain-less spec inherited the tenant domain a PREVIOUS spec had written - silently\n // widening a check that should have run at SYSTEM_WIDE. The context is still set, for\n // observability, but nothing decides on it.\n const domainScope =\n spec.domain || options?.domainResolver\n ? await resolveRequestDomain({\n spec,\n context: asTypedContext(context),\n options,\n })\n : undefined;\n context.set(Authorization.DOMAIN, domainScope);\n\n // Keyed by enforcer. The slot used to hold one rule set for the whole request, so a second\n // `authorize()` naming a DIFFERENT enforcer evaluated against the first enforcer's rules -\n // granting where its own policy set denies.\n //\n // `instanceof Map`, not a truthiness test: the slot previously held a bare rule set, so\n // anything that pre-populates it with the old shape would otherwise reach `.get` on a value\n // that has no such method and take the request down with a TypeError.\n const existingRules = context.get(Authorization.RULES);\n const rulesByEnforcer =\n existingRules instanceof Map ? existingRules : new Map<string, unknown>();\n let rules = rulesByEnforcer.get(resolvedName);\n\n if (!rules) {\n if (!user.principalType) {\n throw getError({\n error: AuthorizationErrors.PRINCIPAL_TYPE_MISSING,\n message:\n 'Authorization failed: user.principalType is required for enforcer-based authorization',\n });\n }\n\n rules = await enforcer.buildRules({\n user: user as { principalType: string } & IAuthUser,\n context: asTypedContext(context),\n });\n rulesByEnforcer.set(resolvedName, rules);\n context.set(Authorization.RULES, rulesByEnforcer);\n }\n\n let decision = await enforcer.evaluate({\n rules,\n request: {\n action: spec.action,\n resource: spec.resource,\n conditions: spec.conditions,\n domain: domainScope,\n },\n context: asTypedContext(context),\n });\n\n if (decision === AuthorizationDecisions.ABSTAIN) {\n decision = options?.defaultDecision ?? AuthorizationDecisions.DENY;\n }\n\n if (decision !== AuthorizationDecisions.ALLOW) {\n throw getError({\n error: AuthorizationErrors.DENIED,\n message: `Authorization denied | action: ${spec.action} | resource: ${spec.resource}`,\n messageArgs: { action: spec.action, resource: spec.resource },\n });\n }\n\n await next();\n });\n }\n\n private extractUserRoles(opts: { user: IAuthUser }): string[] {\n const { user } = opts;\n const roles = user.roles;\n\n if (!Array.isArray(roles)) {\n return [];\n }\n\n return roles.map((r: string | { identifier?: string; name?: string; id?: unknown }) => {\n if (typeof r === 'string') {\n return r;\n }\n return r.identifier ?? r.name ?? String(r.id ?? '');\n });\n }\n}\n"]}
@@ -0,0 +1,19 @@
1
+ import type { IAuthorizationSpec } from '../../auth/authorize/common/types';
2
+ import type { ICustomizableRoutes } from '../common';
3
+ /**
4
+ * Refuses a CRUD controller whose enabled write verb would inherit a controller-level `authorize`
5
+ * that is only a `read` permission: the verb would then answer to anyone who may read.
6
+ *
7
+ * A write verb is fine when it declares its own `authorize` (a spec, an array, or `{ skip: true }`),
8
+ * skips authentication, is not enabled, or the controller is `readonly`. Only the literal action
9
+ * `read` is detected; a custom action name is the application's own vocabulary. An array counts when
10
+ * every spec in it is `read`, since the specs of one route must all pass.
11
+ */
12
+ export declare const assertWriteVerbsDeclareAuthorize: (opts: {
13
+ controllerName: string;
14
+ authorize: IAuthorizationSpec | IAuthorizationSpec[] | undefined;
15
+ routes: ICustomizableRoutes | undefined;
16
+ readonly: boolean | undefined;
17
+ enabledRoutes: Array<keyof ICustomizableRoutes> | undefined;
18
+ }) => void;
19
+ //# sourceMappingURL=authorize-guard.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"authorize-guard.d.ts","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/authorize-guard.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,oCAAoC,CAAC;AAE7E,OAAO,KAAK,EAAE,mBAAmB,EAAE,MAAM,WAAW,CAAC;AASrD;;;;;;;;GAQG;AACH,eAAO,MAAM,gCAAgC,GAAI,MAAM;IACrD,cAAc,EAAE,MAAM,CAAC;IACvB,SAAS,EAAE,kBAAkB,GAAG,kBAAkB,EAAE,GAAG,SAAS,CAAC;IACjE,MAAM,EAAE,mBAAmB,GAAG,SAAS,CAAC;IACxC,QAAQ,EAAE,OAAO,GAAG,SAAS,CAAC;IAC9B,aAAa,EAAE,KAAK,CAAC,MAAM,mBAAmB,CAAC,GAAG,SAAS,CAAC;CAC7D,KAAG,IA+CH,CAAC"}
@@ -0,0 +1,60 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.assertWriteVerbsDeclareAuthorize = void 0;
4
+ const constants_1 = require("../../auth/authorize/common/constants");
5
+ const core_1 = require("@venizia/ignis-helpers/core");
6
+ /** The generated routes that change data: the ones that must never be answered by a `read` permission. */
7
+ const WRITE_VERBS = ['create', 'updateById', 'updateBy', 'deleteById', 'deleteBy'];
8
+ const describeSpec = (spec) => {
9
+ return `{ action: ${String(spec.action)}, resource: ${String(spec.resource)} }`;
10
+ };
11
+ /**
12
+ * Refuses a CRUD controller whose enabled write verb would inherit a controller-level `authorize`
13
+ * that is only a `read` permission: the verb would then answer to anyone who may read.
14
+ *
15
+ * A write verb is fine when it declares its own `authorize` (a spec, an array, or `{ skip: true }`),
16
+ * skips authentication, is not enabled, or the controller is `readonly`. Only the literal action
17
+ * `read` is detected; a custom action name is the application's own vocabulary. An array counts when
18
+ * every spec in it is `read`, since the specs of one route must all pass.
19
+ */
20
+ const assertWriteVerbsDeclareAuthorize = (opts) => {
21
+ const { controllerName, authorize, routes, readonly, enabledRoutes } = opts;
22
+ if (readonly || authorize == null) {
23
+ return;
24
+ }
25
+ const specs = Array.isArray(authorize) ? authorize : [authorize];
26
+ const isReadOnlyPermission = specs.length > 0 && specs.every((spec) => spec.action === constants_1.AuthorizationActions.READ);
27
+ if (!isReadOnlyPermission) {
28
+ return;
29
+ }
30
+ const offending = WRITE_VERBS.filter((verb) => {
31
+ const isEnabled = enabledRoutes
32
+ ? enabledRoutes.includes(verb)
33
+ : routes?.[verb]?.enabled !== false;
34
+ if (!isEnabled) {
35
+ return false;
36
+ }
37
+ const route = routes?.[verb];
38
+ return route?.authenticate?.skip !== true && route?.authorize == null;
39
+ });
40
+ if (offending.length === 0) {
41
+ return;
42
+ }
43
+ const inherited = specs.map(describeSpec).join(', ');
44
+ const verbs = offending.map((verb) => `${controllerName}.${verb}`).join(', ');
45
+ const hasBulkVerb = offending.some((verb) => verb === 'updateBy' || verb === 'deleteBy');
46
+ throw (0, core_1.getError)({
47
+ message: [
48
+ `[defineCrudController] Write routes would inherit a read-only authorize | controller: ${controllerName} | routes: ${verbs} | inherited: ${inherited}`,
49
+ 'Anyone allowed to read could then create, update or delete.',
50
+ `Fix: declare routes.<verb>.authorize for each of them (a spec, an array or { skip: true }), or set controller.readonly, or leave them out of controller.enabledRoutes.`,
51
+ ...(hasBulkVerb
52
+ ? [
53
+ 'updateBy and deleteBy are bulk routes on the collection and are generated unless controller.enabledRoutes lists the routes you want, so dropping them there closes this too.',
54
+ ]
55
+ : []),
56
+ ].join(' | '),
57
+ });
58
+ };
59
+ exports.assertWriteVerbsDeclareAuthorize = assertWriteVerbsDeclareAuthorize;
60
+ //# sourceMappingURL=authorize-guard.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"authorize-guard.js","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/authorize-guard.ts"],"names":[],"mappings":";;;AAAA,sEAA8E;AAE9E,sDAAuD;AAGvD,0GAA0G;AAC1G,MAAM,WAAW,GAAG,CAAC,QAAQ,EAAE,YAAY,EAAE,UAAU,EAAE,YAAY,EAAE,UAAU,CAAU,CAAC;AAE5F,MAAM,YAAY,GAAG,CAAC,IAAwB,EAAU,EAAE;IACxD,OAAO,aAAa,MAAM,CAAC,IAAI,CAAC,MAAM,CAAC,eAAe,MAAM,CAAC,IAAI,CAAC,QAAQ,CAAC,IAAI,CAAC;AAClF,CAAC,CAAC;AAEF;;;;;;;;GAQG;AACI,MAAM,gCAAgC,GAAG,CAAC,IAMhD,EAAQ,EAAE;IACT,MAAM,EAAE,cAAc,EAAE,SAAS,EAAE,MAAM,EAAE,QAAQ,EAAE,aAAa,EAAE,GAAG,IAAI,CAAC;IAE5E,IAAI,QAAQ,IAAI,SAAS,IAAI,IAAI,EAAE,CAAC;QAClC,OAAO;IACT,CAAC;IAED,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC;IACjE,MAAM,oBAAoB,GACxB,KAAK,CAAC,MAAM,GAAG,CAAC,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,CAAC,MAAM,KAAK,gCAAoB,CAAC,IAAI,CAAC,CAAC;IAEvF,IAAI,CAAC,oBAAoB,EAAE,CAAC;QAC1B,OAAO;IACT,CAAC;IAED,MAAM,SAAS,GAAG,WAAW,CAAC,MAAM,CAAC,CAAC,IAAI,EAAE,EAAE;QAC5C,MAAM,SAAS,GAAG,aAAa;YAC7B,CAAC,CAAC,aAAa,CAAC,QAAQ,CAAC,IAAI,CAAC;YAC9B,CAAC,CAAC,MAAM,EAAE,CAAC,IAAI,CAAC,EAAE,OAAO,KAAK,KAAK,CAAC;QACtC,IAAI,CAAC,SAAS,EAAE,CAAC;YACf,OAAO,KAAK,CAAC;QACf,CAAC;QAED,MAAM,KAAK,GAAG,MAAM,EAAE,CAAC,IAAI,CAAC,CAAC;QAC7B,OAAO,KAAK,EAAE,YAAY,EAAE,IAAI,KAAK,IAAI,IAAI,KAAK,EAAE,SAAS,IAAI,IAAI,CAAC;IACxE,CAAC,CAAC,CAAC;IAEH,IAAI,SAAS,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QAC3B,OAAO;IACT,CAAC;IAED,MAAM,SAAS,GAAG,KAAK,CAAC,GAAG,CAAC,YAAY,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IACrD,MAAM,KAAK,GAAG,SAAS,CAAC,GAAG,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,GAAG,cAAc,IAAI,IAAI,EAAE,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC9E,MAAM,WAAW,GAAG,SAAS,CAAC,IAAI,CAAC,CAAC,IAAI,EAAE,EAAE,CAAC,IAAI,KAAK,UAAU,IAAI,IAAI,KAAK,UAAU,CAAC,CAAC;IAEzF,MAAM,IAAA,eAAQ,EAAC;QACb,OAAO,EAAE;YACP,yFAAyF,cAAc,cAAc,KAAK,iBAAiB,SAAS,EAAE;YACtJ,6DAA6D;YAC7D,wKAAwK;YACxK,GAAG,CAAC,WAAW;gBACb,CAAC,CAAC;oBACE,8KAA8K;iBAC/K;gBACH,CAAC,CAAC,EAAE,CAAC;SACR,CAAC,IAAI,CAAC,KAAK,CAAC;KACd,CAAC,CAAC;AACL,CAAC,CAAC;AArDW,QAAA,gCAAgC,oCAqD3C","sourcesContent":["import { AuthorizationActions } from '@/base/auth/authorize/common/constants';\nimport type { IAuthorizationSpec } from '@/base/auth/authorize/common/types';\nimport { getError } from '@venizia/ignis-helpers/core';\nimport type { ICustomizableRoutes } from '../common';\n\n/** The generated routes that change data: the ones that must never be answered by a `read` permission. */\nconst WRITE_VERBS = ['create', 'updateById', 'updateBy', 'deleteById', 'deleteBy'] as const;\n\nconst describeSpec = (spec: IAuthorizationSpec): string => {\n return `{ action: ${String(spec.action)}, resource: ${String(spec.resource)} }`;\n};\n\n/**\n * Refuses a CRUD controller whose enabled write verb would inherit a controller-level `authorize`\n * that is only a `read` permission: the verb would then answer to anyone who may read.\n *\n * A write verb is fine when it declares its own `authorize` (a spec, an array, or `{ skip: true }`),\n * skips authentication, is not enabled, or the controller is `readonly`. Only the literal action\n * `read` is detected; a custom action name is the application's own vocabulary. An array counts when\n * every spec in it is `read`, since the specs of one route must all pass.\n */\nexport const assertWriteVerbsDeclareAuthorize = (opts: {\n controllerName: string;\n authorize: IAuthorizationSpec | IAuthorizationSpec[] | undefined;\n routes: ICustomizableRoutes | undefined;\n readonly: boolean | undefined;\n enabledRoutes: Array<keyof ICustomizableRoutes> | undefined;\n}): void => {\n const { controllerName, authorize, routes, readonly, enabledRoutes } = opts;\n\n if (readonly || authorize == null) {\n return;\n }\n\n const specs = Array.isArray(authorize) ? authorize : [authorize];\n const isReadOnlyPermission =\n specs.length > 0 && specs.every((spec) => spec.action === AuthorizationActions.READ);\n\n if (!isReadOnlyPermission) {\n return;\n }\n\n const offending = WRITE_VERBS.filter((verb) => {\n const isEnabled = enabledRoutes\n ? enabledRoutes.includes(verb)\n : routes?.[verb]?.enabled !== false;\n if (!isEnabled) {\n return false;\n }\n\n const route = routes?.[verb];\n return route?.authenticate?.skip !== true && route?.authorize == null;\n });\n\n if (offending.length === 0) {\n return;\n }\n\n const inherited = specs.map(describeSpec).join(', ');\n const verbs = offending.map((verb) => `${controllerName}.${verb}`).join(', ');\n const hasBulkVerb = offending.some((verb) => verb === 'updateBy' || verb === 'deleteBy');\n\n throw getError({\n message: [\n `[defineCrudController] Write routes would inherit a read-only authorize | controller: ${controllerName} | routes: ${verbs} | inherited: ${inherited}`,\n 'Anyone allowed to read could then create, update or delete.',\n `Fix: declare routes.<verb>.authorize for each of them (a spec, an array or { skip: true }), or set controller.readonly, or leave them out of controller.enabledRoutes.`,\n ...(hasBulkVerb\n ? [\n 'updateBy and deleteBy are bulk routes on the collection and are generated unless controller.enabledRoutes lists the routes you want, so dropping them there closes this too.',\n ]\n : []),\n ].join(' | '),\n });\n};\n"]}
@@ -1,7 +1,7 @@
1
1
  import type { AbstractEntity } from '../../models';
2
2
  import type { AbstractRepository } from '../../repositories';
3
3
  import type { TAnyObjectSchema } from '../common/schema-builders';
4
- import type { ValueOrPromise } from '@venizia/ignis-helpers/common';
4
+ import type { AnyType, ValueOrPromise } from '@venizia/ignis-helpers/common';
5
5
  import { BaseHelper } from '@venizia/ignis-helpers/core';
6
6
  import type { Env, Schema } from 'hono';
7
7
  import type { ICrudControllerOptions, ICustomizableRoutes, TEntityDataObject, TEntityPersistObject } from '../common';
@@ -9,7 +9,7 @@ import type { ICrudControllerOptions, ICustomizableRoutes, TEntityDataObject, TE
9
9
  export declare class ControllerFactory extends BaseHelper {
10
10
  constructor();
11
11
  static defineCrudController<TEntity extends AbstractEntity<TAnyObjectSchema> = AbstractEntity<TAnyObjectSchema>, Routes extends ICustomizableRoutes = ICustomizableRoutes, RouteEnv extends Env = Env, RouteSchema extends Schema = {}, BasePath extends string = '/', ConfigurableOptions extends object = {}, TDataObject extends object = TEntityDataObject<TEntity>, TPersistObject extends object = TEntityPersistObject<TEntity>>(defOpts: ICrudControllerOptions<TEntity, Routes>): {
12
- new (repository: AbstractRepository<TDataObject, TPersistObject>): {
12
+ new (repository: AbstractRepository<TDataObject, TPersistObject, AnyType>): {
13
13
  /** Registers each CRUD route whose handler tier supplies it, honoring enabledRoutes/readonly. */
14
14
  binding(): ValueOrPromise<void>;
15
15
  create(opts: {
@@ -1 +1 @@
1
- {"version":3,"file":"controller.d.ts","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/controller.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAEpD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,2CAA2C,CAAC;AAClF,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,+BAA+B,CAAC;AACpE,OAAO,EAAE,UAAU,EAAY,MAAM,6BAA6B,CAAC;AAEnE,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,MAAM,CAAC;AACxC,OAAO,KAAK,EACV,sBAAsB,EACtB,mBAAmB,EACnB,iBAAiB,EACjB,oBAAoB,EACrB,MAAM,WAAW,CAAC;AAKnB,6EAA6E;AAC7E,qBAAa,iBAAkB,SAAQ,UAAU;;IAK/C,MAAM,CAAC,oBAAoB,CACzB,OAAO,SAAS,cAAc,CAAC,gBAAgB,CAAC,GAAG,cAAc,CAAC,gBAAgB,CAAC,EACnF,MAAM,SAAS,mBAAmB,GAAG,mBAAmB,EACxD,QAAQ,SAAS,GAAG,GAAG,GAAG,EAC1B,WAAW,SAAS,MAAM,GAAG,EAAE,EAC/B,QAAQ,SAAS,MAAM,GAAG,GAAG,EAC7B,mBAAmB,SAAS,MAAM,GAAG,EAAE,EACvC,WAAW,SAAS,MAAM,GAAG,iBAAiB,CAAC,OAAO,CAAC,EACvD,cAAc,SAAS,MAAM,GAAG,oBAAoB,CAAC,OAAO,CAAC,EAC7D,OAAO,EAAE,sBAAsB,CAAC,OAAO,EAAE,MAAM,CAAC;yBAwCtB,kBAAkB,CAAC,WAAW,EAAE,cAAc,CAAC;YAUvE,iGAAiG;uBAC7E,cAAc,CAAC,IAAI,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;qBADkB,CAAA;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAyF/D"}
1
+ {"version":3,"file":"controller.d.ts","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/controller.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,eAAe,CAAC;AAEpD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,2CAA2C,CAAC;AAClF,OAAO,KAAK,EAAE,OAAO,EAAE,cAAc,EAAE,MAAM,+BAA+B,CAAC;AAC7E,OAAO,EAAE,UAAU,EAAY,MAAM,6BAA6B,CAAC;AAEnE,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,MAAM,CAAC;AACxC,OAAO,KAAK,EACV,sBAAsB,EACtB,mBAAmB,EACnB,iBAAiB,EACjB,oBAAoB,EACrB,MAAM,WAAW,CAAC;AAMnB,6EAA6E;AAC7E,qBAAa,iBAAkB,SAAQ,UAAU;;IAK/C,MAAM,CAAC,oBAAoB,CACzB,OAAO,SAAS,cAAc,CAAC,gBAAgB,CAAC,GAAG,cAAc,CAAC,gBAAgB,CAAC,EACnF,MAAM,SAAS,mBAAmB,GAAG,mBAAmB,EACxD,QAAQ,SAAS,GAAG,GAAG,GAAG,EAC1B,WAAW,SAAS,MAAM,GAAG,EAAE,EAC/B,QAAQ,SAAS,MAAM,GAAG,GAAG,EAC7B,mBAAmB,SAAS,MAAM,GAAG,EAAE,EACvC,WAAW,SAAS,MAAM,GAAG,iBAAiB,CAAC,OAAO,CAAC,EACvD,cAAc,SAAS,MAAM,GAAG,oBAAoB,CAAC,OAAO,CAAC,EAC7D,OAAO,EAAE,sBAAsB,CAAC,OAAO,EAAE,MAAM,CAAC;yBAiDtB,kBAAkB,CAAC,WAAW,EAAE,cAAc,EAAE,OAAO,CAAC;YAUhF,iGAAiG;uBAC7E,cAAc,CAAC,IAAI,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;qBAZoB,CAAC;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;CAoGlE"}
@@ -5,6 +5,7 @@ const constants_1 = require("../../models/common/constants");
5
5
  const core_1 = require("@venizia/ignis-helpers/core");
6
6
  const ignis_inversion_1 = require("@venizia/ignis-inversion");
7
7
  const crud_1 = require("./crud");
8
+ const authorize_guard_1 = require("./authorize-guard");
8
9
  const definition_1 = require("./definition");
9
10
  const repository_injection_1 = require("./repository-injection");
10
11
  /** Factory for generating typed CRUD controllers from entity definitions. */
@@ -20,6 +21,13 @@ class ControllerFactory extends core_1.BaseHelper {
20
21
  message: `[defineCrudController] Invalid controller basePath | name: ${name} | basePath: ${basePath}`,
21
22
  });
22
23
  }
24
+ (0, authorize_guard_1.assertWriteVerbsDeclareAuthorize)({
25
+ controllerName: name,
26
+ authorize,
27
+ routes,
28
+ readonly: controller.readonly,
29
+ enabledRoutes: controller.enabledRoutes,
30
+ });
23
31
  const entityClass = (0, ignis_inversion_1.isClass)(entity) ? entity : entity();
24
32
  const entityInstance = new entityClass();
25
33
  const routeDefinitions = (0, definition_1.defineControllerRouteConfigs)({
@@ -36,6 +44,7 @@ class ControllerFactory extends core_1.BaseHelper {
36
44
  serverStampedKeys: entityInstance.getServerStampedKeys(),
37
45
  });
38
46
  const controllerClass = class extends crud_1.PersistableCrudController {
47
+ // Any extra options: a repository whose options narrow `IExtraOptions` (a typed transaction) must fit.
39
48
  constructor(repository) {
40
49
  super({
41
50
  scope: name,
@@ -1 +1 @@
1
- {"version":3,"file":"controller.js","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AbstractEntity } from '@/base/models';\nimport { SchemaTypes } from '@/base/models/common/constants';\nimport type { AbstractRepository } from '@/base/repositories';\nimport type { TAnyObjectSchema } from '@/base/controllers/common/schema-builders';\nimport type { ValueOrPromise } from '@venizia/ignis-helpers/common';\nimport { BaseHelper, getError } from '@venizia/ignis-helpers/core';\nimport { isClass } from '@venizia/ignis-inversion';\nimport type { Env, Schema } from 'hono';\nimport type {\n ICrudControllerOptions,\n ICustomizableRoutes,\n TEntityDataObject,\n TEntityPersistObject,\n} from '../common';\nimport { PersistableCrudController } from './crud';\nimport { defineControllerRouteConfigs } from './definition';\nimport { registerFactoryRepositoryInjection } from './repository-injection';\n\n/** Factory for generating typed CRUD controllers from entity definitions. */\nexport class ControllerFactory extends BaseHelper {\n constructor() {\n super({ scope: ControllerFactory.name });\n }\n\n static defineCrudController<\n TEntity extends AbstractEntity<TAnyObjectSchema> = AbstractEntity<TAnyObjectSchema>,\n Routes extends ICustomizableRoutes = ICustomizableRoutes,\n RouteEnv extends Env = Env,\n RouteSchema extends Schema = {},\n BasePath extends string = '/',\n ConfigurableOptions extends object = {},\n TDataObject extends object = TEntityDataObject<TEntity>,\n TPersistObject extends object = TEntityPersistObject<TEntity>,\n >(defOpts: ICrudControllerOptions<TEntity, Routes>) {\n const { controller, entity, authenticate, authorize, routes } = defOpts;\n\n const {\n name,\n basePath = 'unknown_path',\n isStrict = { path: true, requestSchema: true },\n } = controller;\n if (!basePath || basePath === 'unknown_path') {\n throw getError({\n message: `[defineCrudController] Invalid controller basePath | name: ${name} | basePath: ${basePath}`,\n });\n }\n\n const entityClass = isClass(entity) ? entity : entity();\n const entityInstance = new entityClass();\n\n const routeDefinitions = defineControllerRouteConfigs({\n isStrict: isStrict.requestSchema ?? true,\n idType: entityInstance.getIdType(),\n authenticate,\n authorize,\n routes,\n schema: {\n select: entityInstance.getSchema({ type: SchemaTypes.SELECT }),\n create: entityInstance.getSchema({ type: SchemaTypes.CREATE }),\n update: entityInstance.getSchema({ type: SchemaTypes.UPDATE }),\n },\n serverStampedKeys: entityInstance.getServerStampedKeys(),\n });\n\n const controllerClass = class extends PersistableCrudController<\n TEntity,\n RouteEnv,\n RouteSchema,\n BasePath,\n ConfigurableOptions,\n TDataObject,\n TPersistObject\n > {\n constructor(repository: AbstractRepository<TDataObject, TPersistObject>) {\n super({\n scope: name,\n path: basePath,\n isStrict: isStrict.path ?? true,\n repository,\n definitions: routeDefinitions,\n });\n }\n\n /** Registers each CRUD route whose handler tier supplies it, honoring enabledRoutes/readonly. */\n override binding(): ValueOrPromise<void> {\n const isEnabled = (routeKey: keyof ICustomizableRoutes) => {\n if (controller.enabledRoutes) {\n return controller.enabledRoutes.includes(routeKey);\n }\n return routes?.[routeKey]?.enabled !== false;\n };\n\n // Read routes - always registered (unless explicitly disabled)\n if (isEnabled('count')) {\n this.defineRoute({\n configs: routeDefinitions.COUNT,\n handler: async context => this.count({ context }),\n });\n }\n\n if (isEnabled('find')) {\n this.defineRoute({\n configs: routeDefinitions.FIND,\n handler: async context => this.find({ context }),\n });\n }\n\n if (isEnabled('findOne')) {\n this.defineRoute({\n configs: routeDefinitions.FIND_ONE,\n handler: async context => this.findOne({ context }),\n });\n }\n\n if (isEnabled('findById')) {\n this.defineRoute({\n configs: routeDefinitions.FIND_BY_ID,\n handler: async context => this.findById({ context }),\n });\n }\n\n // Write routes - skipped when readonly\n if (controller.readonly) {\n return;\n }\n\n if (isEnabled('create')) {\n this.defineRoute({\n configs: routeDefinitions.CREATE,\n handler: async context => this.create({ context }),\n });\n }\n\n if (isEnabled('updateById')) {\n this.defineRoute({\n configs: routeDefinitions.UPDATE_BY_ID,\n handler: async context => this.updateById({ context }),\n });\n }\n\n if (isEnabled('updateBy')) {\n this.defineRoute({\n configs: routeDefinitions.UPDATE_BY,\n handler: async context => this.updateBy({ context }),\n });\n }\n\n if (isEnabled('deleteById')) {\n this.defineRoute({\n configs: routeDefinitions.DELETE_BY_ID,\n handler: async context => this.deleteById({ context }),\n });\n }\n\n if (isEnabled('deleteBy')) {\n this.defineRoute({\n configs: routeDefinitions.DELETE_BY,\n handler: async context => this.deleteBy({ context }),\n });\n }\n }\n };\n\n Object.defineProperty(controllerClass, 'name', { value: name, configurable: true });\n registerFactoryRepositoryInjection({\n target: controllerClass,\n factoryName: 'defineCrudController',\n controllerName: name,\n repositoryName: defOpts.repository.name,\n });\n return controllerClass;\n }\n}\n"]}
1
+ {"version":3,"file":"controller.js","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/controller.ts"],"names":[],"mappings":"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","sourcesContent":["import type { AbstractEntity } from '@/base/models';\nimport { SchemaTypes } from '@/base/models/common/constants';\nimport type { AbstractRepository } from '@/base/repositories';\nimport type { TAnyObjectSchema } from '@/base/controllers/common/schema-builders';\nimport type { AnyType, ValueOrPromise } from '@venizia/ignis-helpers/common';\nimport { BaseHelper, getError } from '@venizia/ignis-helpers/core';\nimport { isClass } from '@venizia/ignis-inversion';\nimport type { Env, Schema } from 'hono';\nimport type {\n ICrudControllerOptions,\n ICustomizableRoutes,\n TEntityDataObject,\n TEntityPersistObject,\n} from '../common';\nimport { PersistableCrudController } from './crud';\nimport { assertWriteVerbsDeclareAuthorize } from './authorize-guard';\nimport { defineControllerRouteConfigs } from './definition';\nimport { registerFactoryRepositoryInjection } from './repository-injection';\n\n/** Factory for generating typed CRUD controllers from entity definitions. */\nexport class ControllerFactory extends BaseHelper {\n constructor() {\n super({ scope: ControllerFactory.name });\n }\n\n static defineCrudController<\n TEntity extends AbstractEntity<TAnyObjectSchema> = AbstractEntity<TAnyObjectSchema>,\n Routes extends ICustomizableRoutes = ICustomizableRoutes,\n RouteEnv extends Env = Env,\n RouteSchema extends Schema = {},\n BasePath extends string = '/',\n ConfigurableOptions extends object = {},\n TDataObject extends object = TEntityDataObject<TEntity>,\n TPersistObject extends object = TEntityPersistObject<TEntity>,\n >(defOpts: ICrudControllerOptions<TEntity, Routes>) {\n const { controller, entity, authenticate, authorize, routes } = defOpts;\n\n const {\n name,\n basePath = 'unknown_path',\n isStrict = { path: true, requestSchema: true },\n } = controller;\n if (!basePath || basePath === 'unknown_path') {\n throw getError({\n message: `[defineCrudController] Invalid controller basePath | name: ${name} | basePath: ${basePath}`,\n });\n }\n\n assertWriteVerbsDeclareAuthorize({\n controllerName: name,\n authorize,\n routes,\n readonly: controller.readonly,\n enabledRoutes: controller.enabledRoutes,\n });\n\n const entityClass = isClass(entity) ? entity : entity();\n const entityInstance = new entityClass();\n\n const routeDefinitions = defineControllerRouteConfigs({\n isStrict: isStrict.requestSchema ?? true,\n idType: entityInstance.getIdType(),\n authenticate,\n authorize,\n routes,\n schema: {\n select: entityInstance.getSchema({ type: SchemaTypes.SELECT }),\n create: entityInstance.getSchema({ type: SchemaTypes.CREATE }),\n update: entityInstance.getSchema({ type: SchemaTypes.UPDATE }),\n },\n serverStampedKeys: entityInstance.getServerStampedKeys(),\n });\n\n const controllerClass = class extends PersistableCrudController<\n TEntity,\n RouteEnv,\n RouteSchema,\n BasePath,\n ConfigurableOptions,\n TDataObject,\n TPersistObject\n > {\n // Any extra options: a repository whose options narrow `IExtraOptions` (a typed transaction) must fit.\n constructor(repository: AbstractRepository<TDataObject, TPersistObject, AnyType>) {\n super({\n scope: name,\n path: basePath,\n isStrict: isStrict.path ?? true,\n repository,\n definitions: routeDefinitions,\n });\n }\n\n /** Registers each CRUD route whose handler tier supplies it, honoring enabledRoutes/readonly. */\n override binding(): ValueOrPromise<void> {\n const isEnabled = (routeKey: keyof ICustomizableRoutes) => {\n if (controller.enabledRoutes) {\n return controller.enabledRoutes.includes(routeKey);\n }\n return routes?.[routeKey]?.enabled !== false;\n };\n\n // Read routes - always registered (unless explicitly disabled)\n if (isEnabled('count')) {\n this.defineRoute({\n configs: routeDefinitions.COUNT,\n handler: async (context) => this.count({ context }),\n });\n }\n\n if (isEnabled('find')) {\n this.defineRoute({\n configs: routeDefinitions.FIND,\n handler: async (context) => this.find({ context }),\n });\n }\n\n if (isEnabled('findOne')) {\n this.defineRoute({\n configs: routeDefinitions.FIND_ONE,\n handler: async (context) => this.findOne({ context }),\n });\n }\n\n if (isEnabled('findById')) {\n this.defineRoute({\n configs: routeDefinitions.FIND_BY_ID,\n handler: async (context) => this.findById({ context }),\n });\n }\n\n // Write routes - skipped when readonly\n if (controller.readonly) {\n return;\n }\n\n if (isEnabled('create')) {\n this.defineRoute({\n configs: routeDefinitions.CREATE,\n handler: async (context) => this.create({ context }),\n });\n }\n\n if (isEnabled('updateById')) {\n this.defineRoute({\n configs: routeDefinitions.UPDATE_BY_ID,\n handler: async (context) => this.updateById({ context }),\n });\n }\n\n if (isEnabled('updateBy')) {\n this.defineRoute({\n configs: routeDefinitions.UPDATE_BY,\n handler: async (context) => this.updateBy({ context }),\n });\n }\n\n if (isEnabled('deleteById')) {\n this.defineRoute({\n configs: routeDefinitions.DELETE_BY_ID,\n handler: async (context) => this.deleteById({ context }),\n });\n }\n\n if (isEnabled('deleteBy')) {\n this.defineRoute({\n configs: routeDefinitions.DELETE_BY,\n handler: async (context) => this.deleteBy({ context }),\n });\n }\n }\n };\n\n Object.defineProperty(controllerClass, 'name', { value: name, configurable: true });\n registerFactoryRepositoryInjection({\n target: controllerClass,\n factoryName: 'defineCrudController',\n controllerName: name,\n repositoryName: defOpts.repository.name,\n });\n return controllerClass;\n }\n}\n"]}
@@ -19,7 +19,7 @@ export declare abstract class AbstractCrudController<TEntity extends AbstractEnt
19
19
  scope: string;
20
20
  path: string;
21
21
  isStrict?: boolean;
22
- repository: AbstractRepository<TDataObject, TPersistObject>;
22
+ repository: AbstractRepository<TDataObject, TPersistObject, AnyType>;
23
23
  definitions: AnyType;
24
24
  });
25
25
  /** 400 when a bulk operation is missing its `where` filter; undefined when it is present. */
@@ -1 +1 @@
1
- {"version":3,"file":"abstract.d.ts","sourceRoot":"","sources":["../../../../../../src/base/controllers/factory/crud/abstract.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,2CAA2C,CAAC;AAClF,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,+BAA+B,CAAC;AAE7D,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,MAAM,CAAC;AACxC,OAAO,KAAK,EAAE,iBAAiB,EAAE,oBAAoB,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC3F,OAAO,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAErD,KAAK,oBAAoB,CAAC,SAAS,IAC/B;IAAE,KAAK,EAAE,SAAS,CAAC;IAAC,KAAK,CAAC,EAAE,SAAS,CAAA;CAAE,GACvC;IAAE,KAAK,CAAC,EAAE,SAAS,CAAC;IAAC,KAAK,EAAE,QAAQ,CAAA;CAAE,CAAC;AAE3C,yRAAyR;AACzR,8BAAsB,sBAAsB,CAC1C,OAAO,SAAS,cAAc,CAAC,gBAAgB,CAAC,GAAG,cAAc,CAAC,gBAAgB,CAAC,EACnF,QAAQ,SAAS,GAAG,GAAG,GAAG,EAC1B,WAAW,SAAS,MAAM,GAAG,EAAE,EAC/B,QAAQ,SAAS,MAAM,GAAG,GAAG,EAC7B,mBAAmB,SAAS,MAAM,GAAG,EAAE,EACvC,WAAW,SAAS,MAAM,GAAG,iBAAiB,CAAC,OAAO,CAAC,EACvD,cAAc,SAAS,MAAM,GAAG,oBAAoB,CAAC,OAAO,CAAC,CAC7D,SAAQ,kBAAkB,CAAC,QAAQ,EAAE,WAAW,EAAE,QAAQ,EAAE,mBAAmB,CAAC;IAChF,UAAU,EAAE,kBAAkB,CAAC,WAAW,EAAE,cAAc,CAAC,CAAC;gBAEhD,IAAI,EAAE;QAChB,KAAK,EAAE,MAAM,CAAC;QACd,IAAI,EAAE,MAAM,CAAC;QACb,QAAQ,CAAC,EAAE,OAAO,CAAC;QACnB,UAAU,EAAE,kBAAkB,CAAC,WAAW,EAAE,cAAc,CAAC,CAAC;QAC5D,WAAW,EAAE,OAAO,CAAC;KACtB;IAMD,6FAA6F;IAC7F,cAAc,CAAC,IAAI,EAAE;QAAE,OAAO,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE;IAWzE,2GAA2G;IAC3G,gBAAgB,CAAC,SAAS,SAAS,MAAM,EAAE,IAAI,EAAE;QAC/C,OAAO,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;QACjC,KAAK,CAAC,EAAE;YACN,SAAS,CAAC,EAAE,SAAS,CAAC;YACtB,QAAQ,CAAC,EAAE,SAAS,CAAC;SACtB,CAAC;KACH,GAAG,oBAAoB,CAAC,SAAS,CAAC;CAyBpC"}
1
+ {"version":3,"file":"abstract.d.ts","sourceRoot":"","sources":["../../../../../../src/base/controllers/factory/crud/abstract.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,oBAAoB,CAAC;AACzD,OAAO,KAAK,EAAE,kBAAkB,EAAE,MAAM,qBAAqB,CAAC;AAC9D,OAAO,KAAK,EAAE,gBAAgB,EAAE,MAAM,2CAA2C,CAAC;AAClF,OAAO,KAAK,EAAE,OAAO,EAAE,MAAM,+BAA+B,CAAC;AAE7D,OAAO,KAAK,EAAE,GAAG,EAAE,MAAM,EAAE,MAAM,MAAM,CAAC;AACxC,OAAO,KAAK,EAAE,iBAAiB,EAAE,oBAAoB,EAAE,aAAa,EAAE,MAAM,cAAc,CAAC;AAC3F,OAAO,EAAE,kBAAkB,EAAE,MAAM,iBAAiB,CAAC;AAErD,KAAK,oBAAoB,CAAC,SAAS,IAC/B;IAAE,KAAK,EAAE,SAAS,CAAC;IAAC,KAAK,CAAC,EAAE,SAAS,CAAA;CAAE,GACvC;IAAE,KAAK,CAAC,EAAE,SAAS,CAAC;IAAC,KAAK,EAAE,QAAQ,CAAA;CAAE,CAAC;AAE3C,yRAAyR;AACzR,8BAAsB,sBAAsB,CAC1C,OAAO,SAAS,cAAc,CAAC,gBAAgB,CAAC,GAAG,cAAc,CAAC,gBAAgB,CAAC,EACnF,QAAQ,SAAS,GAAG,GAAG,GAAG,EAC1B,WAAW,SAAS,MAAM,GAAG,EAAE,EAC/B,QAAQ,SAAS,MAAM,GAAG,GAAG,EAC7B,mBAAmB,SAAS,MAAM,GAAG,EAAE,EACvC,WAAW,SAAS,MAAM,GAAG,iBAAiB,CAAC,OAAO,CAAC,EACvD,cAAc,SAAS,MAAM,GAAG,oBAAoB,CAAC,OAAO,CAAC,CAC7D,SAAQ,kBAAkB,CAAC,QAAQ,EAAE,WAAW,EAAE,QAAQ,EAAE,mBAAmB,CAAC;IAChF,UAAU,EAAE,kBAAkB,CAAC,WAAW,EAAE,cAAc,CAAC,CAAC;gBAEhD,IAAI,EAAE;QAChB,KAAK,EAAE,MAAM,CAAC;QACd,IAAI,EAAE,MAAM,CAAC;QACb,QAAQ,CAAC,EAAE,OAAO,CAAC;QACnB,UAAU,EAAE,kBAAkB,CAAC,WAAW,EAAE,cAAc,EAAE,OAAO,CAAC,CAAC;QACrE,WAAW,EAAE,OAAO,CAAC;KACtB;IAMD,6FAA6F;IAC7F,cAAc,CAAC,IAAI,EAAE;QAAE,OAAO,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;QAAC,KAAK,CAAC,EAAE,MAAM,CAAA;KAAE;IAWzE,2GAA2G;IAC3G,gBAAgB,CAAC,SAAS,SAAS,MAAM,EAAE,IAAI,EAAE;QAC/C,OAAO,EAAE,aAAa,CAAC,QAAQ,CAAC,CAAC;QACjC,KAAK,CAAC,EAAE;YACN,SAAS,CAAC,EAAE,SAAS,CAAC;YACtB,QAAQ,CAAC,EAAE,SAAS,CAAC;SACtB,CAAC;KACH,GAAG,oBAAoB,CAAC,SAAS,CAAC;CAyBpC"}
@@ -1 +1 @@
1
- {"version":3,"file":"abstract.js","sourceRoot":"","sources":["../../../../../../src/base/controllers/factory/crud/abstract.ts"],"names":[],"mappings":";;;AAIA,0DAAqD;AAGrD,0CAAqD;AAMrD,yRAAyR;AACzR,MAAsB,sBAQpB,SAAQ,yBAAwE;IAGhF,YAAY,IAMX;QACC,KAAK,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE,QAAQ,EAAE,IAAI,CAAC,QAAQ,EAAE,CAAC,CAAC;QACvE,IAAI,CAAC,UAAU,GAAG,IAAI,CAAC,UAAU,CAAC;QAClC,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,WAAW,CAAC;IACtC,CAAC;IAED,6FAA6F;IAC7F,cAAc,CAAC,IAA0D;QACvE,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,GAAG,IAAI,CAAC;QAChC,IAAI,CAAC,KAAK,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC9C,OAAO,OAAO,CAAC,IAAI,CACjB,EAAE,OAAO,EAAE,8CAA8C,EAAE,EAC3D,aAAI,CAAC,WAAW,CAAC,IAAI,CAAC,UAAU,CACjC,CAAC;QACJ,CAAC;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;IAED,2GAA2G;IAC3G,gBAAgB,CAA2B,IAM1C;QACC,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;QAC9C,MAAM,EAAE,SAAS,EAAE,QAAQ,EAAE,GAAG,YAAY,IAAI,EAAE,CAAC;QAEnD,IAAI,SAAS,KAAK,SAAS,IAAI,QAAQ,KAAK,SAAS,EAAE,CAAC;YACtD,OAAO;gBACL,KAAK,EAAE,OAAO,CAAC,IAAI,CACjB,EAAE,OAAO,EAAE,6DAA6D,EAAE,EAC1E,aAAI,CAAC,WAAW,CAAC,IAAI,CAAC,UAAU,CACjC;aACF,CAAC;QACJ,CAAC;QAED,MAAM,KAAK,GAAG,SAAS,IAAI,QAAQ,CAAC;QACpC,IAAI,CAAC,KAAK,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC9C,OAAO;gBACL,KAAK,EAAE,OAAO,CAAC,IAAI,CACjB,EAAE,OAAO,EAAE,8CAA8C,EAAE,EAC3D,aAAI,CAAC,WAAW,CAAC,IAAI,CAAC,UAAU,CACjC;aACF,CAAC;QACJ,CAAC;QAED,OAAO,EAAE,KAAK,EAAE,CAAC;IACnB,CAAC;CACF;AAnED,wDAmEC","sourcesContent":["import type { AbstractEntity } from '@/base/models/base';\nimport type { AbstractRepository } from '@/base/repositories';\nimport type { TAnyObjectSchema } from '@/base/controllers/common/schema-builders';\nimport type { AnyType } from '@venizia/ignis-helpers/common';\nimport { HTTP } from '@venizia/ignis-helpers/common';\nimport type { Env, Schema } from 'hono';\nimport type { TEntityDataObject, TEntityPersistObject, TRouteContext } from '../../common';\nimport { BaseRestController } from '../../rest/base';\n\ntype TBulkWhereResolution<WhereType> =\n | { where: WhereType; error?: undefined }\n | { where?: undefined; error: Response };\n\n/** Base tier of a generated CRUD controller - the repository handle; the response helpers (`respond`, `setListHeaders`) live on BaseRestController so hand-written controllers share them. Read and write verbs are layered on by ReadableCrudController / PersistableCrudController. */\nexport abstract class AbstractCrudController<\n TEntity extends AbstractEntity<TAnyObjectSchema> = AbstractEntity<TAnyObjectSchema>,\n RouteEnv extends Env = Env,\n RouteSchema extends Schema = {},\n BasePath extends string = '/',\n ConfigurableOptions extends object = {},\n TDataObject extends object = TEntityDataObject<TEntity>,\n TPersistObject extends object = TEntityPersistObject<TEntity>,\n> extends BaseRestController<RouteEnv, RouteSchema, BasePath, ConfigurableOptions> {\n repository: AbstractRepository<TDataObject, TPersistObject>;\n\n constructor(opts: {\n scope: string;\n path: string;\n isStrict?: boolean;\n repository: AbstractRepository<TDataObject, TPersistObject>;\n definitions: AnyType;\n }) {\n super({ scope: opts.scope, path: opts.path, isStrict: opts.isStrict });\n this.repository = opts.repository;\n this.definitions = opts.definitions;\n }\n\n /** 400 when a bulk operation is missing its `where` filter; undefined when it is present. */\n bulkWhereError(opts: { context: TRouteContext<RouteEnv>; where?: object }) {\n const { context, where } = opts;\n if (!where || Object.keys(where).length === 0) {\n return context.json(\n { message: 'where filter is required for bulk operations' },\n HTTP.ResultCodes.RS_4.BadRequest,\n );\n }\n return undefined;\n }\n\n /** Bulk `where` from the query or the JSON body (long id lists outgrow a URL). Both, or none, is a 400. */\n resolveBulkWhere<WhereType extends object>(opts: {\n context: TRouteContext<RouteEnv>;\n where?: {\n fromQuery?: WhereType;\n fromBody?: WhereType;\n };\n }): TBulkWhereResolution<WhereType> {\n const { context, where: whereSources } = opts;\n const { fromQuery, fromBody } = whereSources ?? {};\n\n if (fromQuery !== undefined && fromBody !== undefined) {\n return {\n error: context.json(\n { message: 'where given in both the query and the body - send it in one' },\n HTTP.ResultCodes.RS_4.BadRequest,\n ),\n };\n }\n\n const where = fromQuery ?? fromBody;\n if (!where || Object.keys(where).length === 0) {\n return {\n error: context.json(\n { message: 'where filter is required for bulk operations' },\n HTTP.ResultCodes.RS_4.BadRequest,\n ),\n };\n }\n\n return { where };\n }\n}\n"]}
1
+ {"version":3,"file":"abstract.js","sourceRoot":"","sources":["../../../../../../src/base/controllers/factory/crud/abstract.ts"],"names":[],"mappings":";;;AAIA,0DAAqD;AAGrD,0CAAqD;AAMrD,yRAAyR;AACzR,MAAsB,sBAQpB,SAAQ,yBAAwE;IAGhF,YAAY,IAMX;QACC,KAAK,CAAC,EAAE,KAAK,EAAE,IAAI,CAAC,KAAK,EAAE,IAAI,EAAE,IAAI,CAAC,IAAI,EAAE,QAAQ,EAAE,IAAI,CAAC,QAAQ,EAAE,CAAC,CAAC;QACvE,IAAI,CAAC,UAAU,GAAG,IAAI,CAAC,UAAU,CAAC;QAClC,IAAI,CAAC,WAAW,GAAG,IAAI,CAAC,WAAW,CAAC;IACtC,CAAC;IAED,6FAA6F;IAC7F,cAAc,CAAC,IAA0D;QACvE,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,GAAG,IAAI,CAAC;QAChC,IAAI,CAAC,KAAK,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC9C,OAAO,OAAO,CAAC,IAAI,CACjB,EAAE,OAAO,EAAE,8CAA8C,EAAE,EAC3D,aAAI,CAAC,WAAW,CAAC,IAAI,CAAC,UAAU,CACjC,CAAC;QACJ,CAAC;QACD,OAAO,SAAS,CAAC;IACnB,CAAC;IAED,2GAA2G;IAC3G,gBAAgB,CAA2B,IAM1C;QACC,MAAM,EAAE,OAAO,EAAE,KAAK,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;QAC9C,MAAM,EAAE,SAAS,EAAE,QAAQ,EAAE,GAAG,YAAY,IAAI,EAAE,CAAC;QAEnD,IAAI,SAAS,KAAK,SAAS,IAAI,QAAQ,KAAK,SAAS,EAAE,CAAC;YACtD,OAAO;gBACL,KAAK,EAAE,OAAO,CAAC,IAAI,CACjB,EAAE,OAAO,EAAE,6DAA6D,EAAE,EAC1E,aAAI,CAAC,WAAW,CAAC,IAAI,CAAC,UAAU,CACjC;aACF,CAAC;QACJ,CAAC;QAED,MAAM,KAAK,GAAG,SAAS,IAAI,QAAQ,CAAC;QACpC,IAAI,CAAC,KAAK,IAAI,MAAM,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC9C,OAAO;gBACL,KAAK,EAAE,OAAO,CAAC,IAAI,CACjB,EAAE,OAAO,EAAE,8CAA8C,EAAE,EAC3D,aAAI,CAAC,WAAW,CAAC,IAAI,CAAC,UAAU,CACjC;aACF,CAAC;QACJ,CAAC;QAED,OAAO,EAAE,KAAK,EAAE,CAAC;IACnB,CAAC;CACF;AAnED,wDAmEC","sourcesContent":["import type { AbstractEntity } from '@/base/models/base';\nimport type { AbstractRepository } from '@/base/repositories';\nimport type { TAnyObjectSchema } from '@/base/controllers/common/schema-builders';\nimport type { AnyType } from '@venizia/ignis-helpers/common';\nimport { HTTP } from '@venizia/ignis-helpers/common';\nimport type { Env, Schema } from 'hono';\nimport type { TEntityDataObject, TEntityPersistObject, TRouteContext } from '../../common';\nimport { BaseRestController } from '../../rest/base';\n\ntype TBulkWhereResolution<WhereType> =\n | { where: WhereType; error?: undefined }\n | { where?: undefined; error: Response };\n\n/** Base tier of a generated CRUD controller - the repository handle; the response helpers (`respond`, `setListHeaders`) live on BaseRestController so hand-written controllers share them. Read and write verbs are layered on by ReadableCrudController / PersistableCrudController. */\nexport abstract class AbstractCrudController<\n TEntity extends AbstractEntity<TAnyObjectSchema> = AbstractEntity<TAnyObjectSchema>,\n RouteEnv extends Env = Env,\n RouteSchema extends Schema = {},\n BasePath extends string = '/',\n ConfigurableOptions extends object = {},\n TDataObject extends object = TEntityDataObject<TEntity>,\n TPersistObject extends object = TEntityPersistObject<TEntity>,\n> extends BaseRestController<RouteEnv, RouteSchema, BasePath, ConfigurableOptions> {\n repository: AbstractRepository<TDataObject, TPersistObject>;\n\n constructor(opts: {\n scope: string;\n path: string;\n isStrict?: boolean;\n repository: AbstractRepository<TDataObject, TPersistObject, AnyType>;\n definitions: AnyType;\n }) {\n super({ scope: opts.scope, path: opts.path, isStrict: opts.isStrict });\n this.repository = opts.repository;\n this.definitions = opts.definitions;\n }\n\n /** 400 when a bulk operation is missing its `where` filter; undefined when it is present. */\n bulkWhereError(opts: { context: TRouteContext<RouteEnv>; where?: object }) {\n const { context, where } = opts;\n if (!where || Object.keys(where).length === 0) {\n return context.json(\n { message: 'where filter is required for bulk operations' },\n HTTP.ResultCodes.RS_4.BadRequest,\n );\n }\n return undefined;\n }\n\n /** Bulk `where` from the query or the JSON body (long id lists outgrow a URL). Both, or none, is a 400. */\n resolveBulkWhere<WhereType extends object>(opts: {\n context: TRouteContext<RouteEnv>;\n where?: {\n fromQuery?: WhereType;\n fromBody?: WhereType;\n };\n }): TBulkWhereResolution<WhereType> {\n const { context, where: whereSources } = opts;\n const { fromQuery, fromBody } = whereSources ?? {};\n\n if (fromQuery !== undefined && fromBody !== undefined) {\n return {\n error: context.json(\n { message: 'where given in both the query and the body - send it in one' },\n HTTP.ResultCodes.RS_4.BadRequest,\n ),\n };\n }\n\n const where = fromQuery ?? fromBody;\n if (!where || Object.keys(where).length === 0) {\n return {\n error: context.json(\n { message: 'where filter is required for bulk operations' },\n HTTP.ResultCodes.RS_4.BadRequest,\n ),\n };\n }\n\n return { where };\n }\n}\n"]}