@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
@@ -38,7 +38,7 @@ class RouteConfigResolver {
38
38
  // A `.transform()` pipe has no shape to read, so every key it might hold counts.
39
39
  const isObjectSchema = schema instanceof zod_openapi_1.z.ZodObject;
40
40
  const omittedKeys = isObjectSchema
41
- ? droppedKeys.filter(key => Object.hasOwn(schema.shape, key))
41
+ ? droppedKeys.filter((key) => Object.hasOwn(schema.shape, key))
42
42
  : droppedKeys;
43
43
  if (omittedKeys.length === 0) {
44
44
  return schema;
@@ -1 +1 @@
1
- {"version":3,"file":"definition.js","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/definition.ts"],"names":[],"mappings":";;;AAGA,iDAAiF;AACjF,uDAAyD;AACzD,qEAAmF;AAEnF,mDAAsC;AACtC,0DAAqD;AACrD,sDAAuD;AAEvD,sCAMmB;AAWnB;;;;GAIG;AACH,MAAa,mBAAmB;IAC9B,0KAA0K;IAClK,MAAM,CAAC,kBAAkB,CAAC,IAA+B;QAC/D,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QAExB,IAAI,MAAM,KAAK,QAAQ,EAAE,CAAC;YACxB,OAAO,IAAA,uBAAc,EAAC,EAAE,MAAM,EAAE,CAAC,CAAC;QACpC,CAAC;QAED,OAAO,eAAC,CAAC,MAAM,CAAC;YACd,EAAE,EAAE,eAAC,CAAC,MAAM,CAAC,MAAM,EAAE,CAAC,OAAO,CAAC;gBAC5B,KAAK,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,EAAE,EAAE,MAAM,EAAE,WAAW,EAAE,+BAA+B,EAAE;gBAC/E,QAAQ,EAAE,CAAC,CAAC,EAAE,CAAC,EAAE,CAAC,CAAC;aACpB,CAAC;SACH,CAAC,CAAC;IACL,CAAC;IAED;;;;OAIG;IACK,MAAM,CAAC,iBAAiB,CAAC,IAIhC;QACC,MAAM,EAAE,MAAM,EAAE,KAAK,EAAE,iBAAiB,EAAE,GAAG,IAAI,CAAC;QAClD,MAAM,WAAW,GAAG,KAAK,KAAK,QAAQ,CAAC,CAAC,CAAC,iBAAiB,CAAC,CAAC,CAAC,CAAC,GAAG,iBAAiB,EAAE,IAAI,CAAC,CAAC;QAC1F,iFAAiF;QACjF,MAAM,cAAc,GAAG,MAAM,YAAY,eAAC,CAAC,SAAS,CAAC;QACrD,MAAM,WAAW,GAAG,cAAc;YAChC,CAAC,CAAC,WAAW,CAAC,MAAM,CAAC,GAAG,CAAC,EAAE,CAAC,MAAM,CAAC,MAAM,CAAC,MAAM,CAAC,KAAK,EAAE,GAAG,CAAC,CAAC;YAC7D,CAAC,CAAC,WAAW,CAAC;QAEhB,IAAI,WAAW,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;YAC7B,OAAO,MAAM,CAAC;QAChB,CAAC;QAED,IAAI,CAAC,cAAc,IAAI,MAAM,CAAC,GAAG,CAAC,MAAM,EAAE,MAAM,EAAE,CAAC;YACjD,MAAM,IAAA,eAAQ,EAAC;gBACb,OAAO,EAAE,2DAA2D,KAAK,8BAA8B,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,oFAAoF,KAAK,eAAe;aACtO,CAAC,CAAC;QACL,CAAC;QAED,MAAM,IAAI,GAAyB,EAAE,CAAC;QACtC,KAAK,MAAM,GAAG,IAAI,WAAW,EAAE,CAAC;YAC9B,IAAI,CAAC,GAAG,CAAC,GAAG,IAAI,CAAC;QACnB,CAAC;QAED,OAAO,MAAM,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAC3B,CAAC;IAED,sGAAsG;IAC9F,MAAM,CAAC,eAAe,CAE5B,IAA0C;QAC1C,MAAM,EAAE,MAAM,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QAChC,OAAO,MAAM,EAAE,OAAO,EAAE,MAAM,IAAI,mBAAmB,CAAC,kBAAkB,CAAC,EAAE,MAAM,EAAE,CAAC,CAAC;IACvF,CAAC;IAED,iDAAiD;IACjD,MAAM,CAAC,wBAAwB,CAAsB,UAAa;QAChE,OAAO,eAAC,CAAC,KAAK,CAAC;YACb,oBAAW,CAAC,MAAM,CAAC,EAAE,IAAI,EAAE,UAAU,EAAE,CAAC,CAAC,OAAO,CAAC;gBAC/C,WAAW,EAAE,wEAAwE;aACtF,CAAC;YACF,UAAU,CAAC,OAAO,CAAC;gBACjB,WAAW,EAAE,6DAA6D;aAC3E,CAAC;SACH,CAAC,CAAC;IACL,CAAC;IAED,wQAAwQ;IAChQ,MAAM,CAAC,qBAAqB,CAGlC,IAAqC;QACrC,MAAM,EAAE,MAAM,EAAE,aAAa,EAAE,GAAG,IAAI,CAAC;QACvC,OAAO,CAAC,MAAM,EAAE,QAAQ,EAAE,MAAM,IAAI,aAAa,CAAkC,CAAC;IACtF,CAAC;IAED,MAAM,CAAC,kBAAkB,CAAyC,IAGjE;QACC,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,GAAG,IAAI,CAAC;QAClC,MAAM,YAAY,GAAG,eAAC;aACnB,MAAM,CAAC;YACN,KAAK,EAAE,QAAQ;gBACb,CAAC,CAAC,2BAAW;gBACb,CAAC,CAAC,eAAC,CAAC,QAAQ,CAAC,2BAAW,CAAC,CAAC,OAAO,CAAC,EAAE,WAAW,EAAE,mBAAmB,EAAE,CAAC;SAC1E,CAAC;aACD,OAAO,CAAC,EAAE,WAAW,EAAE,oBAAoB,EAAE,CAAC,CAAC;QAElD,OAAO;YACL,OAAO,EAAE;gBACP,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,IAAI,YAAY;gBAC7C,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,yBAAgB;aACtD;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,iCAAiC;gBAC9C,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,oBAAW,EAAE,CAAC;gBACzF,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,iBAAiB,CAGtB,IAA6C;QAC7C,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;QACtC,MAAM,YAAY,GAAG,iCAAiB,CAAC;QACvC,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,eAAC,CAAC,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC;QAE1F,OAAO;YACL,OAAO,EAAE;gBACP,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,IAAI,YAAY;gBAC7C,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,iDAAiD;gBAC9D,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,4BAAmB;aAC1D;SACF,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,qBAAqB,CAG1B,IAAwE;QACxE,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QAC9C,MAAM,YAAY,GAAG,iCAAiB,CAAC,OAAO,CAAC;YAC7C,WAAW,EAAE,oDAAoD;SAClE,CAAC,CAAC;QACH,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,YAAY,CAAC,CAAC;QAEjF,OAAO;YACL,OAAO,EAAE;gBACP,MAAM,EAAE,mBAAmB,CAAC,eAAe,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC;gBAC/D,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,IAAI,YAAY;gBAC7C,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,mCAAmC;gBAChD,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAED,MAAM,CAAC,oBAAoB,CAGzB,IAAgD;QAChD,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;QACtC,MAAM,YAAY,GAAG,iCAAiB,CAAC,OAAO,CAAC;YAC7C,WAAW,EAAE,2CAA2C;SACzD,CAAC,CAAC;QACH,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,YAAY,CAAC,CAAC;QAEjF,OAAO;YACL,OAAO,EAAE;gBACP,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,IAAI,YAAY;gBAC7C,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,+BAA+B;gBAC5C,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAED,qHAAqH;IACrH,MAAM,CAAC,mBAAmB,CAIxB,IAKD;QACC,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,YAAY,EAAE,iBAAiB,GAAG,EAAE,EAAE,GAAG,IAAI,CAAC;QAC5E,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,YAAY,CAAC,CAAC;QAEjF,OAAO;YACL,OAAO,EAAE;gBACP,IAAI,EACF,MAAM,EAAE,OAAO,EAAE,IAAI;oBACrB,mBAAmB,CAAC,iBAAiB,CAAC;wBACpC,MAAM,EAAE,YAAY;wBACpB,KAAK,EAAE,QAAQ;wBACf,iBAAiB;qBAClB,CAAC;gBACJ,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,4DAA4D;gBACzE,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAEO,MAAM,CAAC,uBAAuB,CAIpC,IAMD;QACC,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,YAAY,EAAE,MAAM,EAAE,iBAAiB,EAAE,GAAG,IAAI,CAAC;QAC/E,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,YAAY,CAAC,CAAC;QACjF,OAAO;YACL,OAAO,EAAE;gBACP,MAAM,EAAE,mBAAmB,CAAC,eAAe,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC;gBAC/D,IAAI,EACF,MAAM,EAAE,OAAO,EAAE,IAAI;oBACrB,mBAAmB,CAAC,iBAAiB,CAAC;wBACpC,MAAM,EAAE,YAAY;wBACpB,KAAK,EAAE,YAAY;wBACnB,iBAAiB;qBAClB,CAAC;gBACJ,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,wCAAwC;gBACrD,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAEO,MAAM,CAAC,qBAAqB,CAIlC,IAKD;QACC,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,YAAY,EAAE,iBAAiB,EAAE,GAAG,IAAI,CAAC;QACvE,MAAM,YAAY,GAAG,eAAC,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,2BAAW,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,OAAO,CAAC;YACvE,WAAW,EACT,iFAAiF;SACpF,CAAC,CAAC;QACH,4FAA4F;QAC5F,MAAM,gBAAgB,GAAG,GAAG,EAAE;YAC5B,MAAM,cAAc,GAAG,mBAAmB,CAAC,iBAAiB,CAAC;gBAC3D,MAAM,EAAE,YAAY;gBACpB,KAAK,EAAE,UAAU;gBACjB,iBAAiB;aAClB,CAAC,CAAC;YACH,0FAA0F;YAC1F,4DAA4D;YAC5D,OAAO,OAAO,IAAI,cAAc,CAAC,KAAK;gBACpC,CAAC,CAAC,cAAc;gBAChB,CAAC,CAAC,cAAc,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,2BAAW,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC;QAC/D,CAAC,CAAC;QACF,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,eAAC,CAAC,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC;QAC1F,OAAO;YACL,OAAO,EAAE;gBACP,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,IAAI,YAAY;gBAC7C,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,IAAI,IAAI,gBAAgB,EAAE;gBACjD,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,0BAA0B;gBACvC,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAEO,MAAM,CAAC,uBAAuB,CAGpC,IAAsE;QACtE,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,GAAG,IAAI,CAAC;QAC9C,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,YAAY,CAAC,CAAC;QACjF,OAAO;YACL,OAAO,EAAE;gBACP,MAAM,EAAE,mBAAmB,CAAC,eAAe,CAAC,EAAE,MAAM,EAAE,MAAM,EAAE,CAAC;gBAC/D,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,qBAAqB;gBAClC,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAEO,MAAM,CAAC,qBAAqB,CAGlC,IAA+C;QAC/C,MAAM,EAAE,MAAM,EAAE,YAAY,EAAE,GAAG,IAAI,CAAC;QACtC,MAAM,YAAY,GAAG,eAAC,CAAC,MAAM,CAAC,EAAE,KAAK,EAAE,2BAAW,CAAC,QAAQ,EAAE,EAAE,CAAC,CAAC,OAAO,CAAC;YACvE,WAAW,EACT,iFAAiF;SACpF,CAAC,CAAC;QACH,MAAM,aAAa,GAAG,mBAAmB,CAAC,wBAAwB,CAAC,eAAC,CAAC,KAAK,CAAC,YAAY,CAAC,CAAC,CAAC;QAC1F,OAAO;YACL,OAAO,EAAE;gBACP,KAAK,EAAE,MAAM,EAAE,OAAO,EAAE,KAAK,IAAI,YAAY;gBAC7C,6FAA6F;gBAC7F,8FAA8F;gBAC9F,0FAA0F;gBAC1F,IAAI,EAAE,MAAM,EAAE,OAAO,EAAE,IAAI;gBAC3B,OAAO,EAAE,MAAM,EAAE,OAAO,EAAE,OAAO,IAAI,8BAAqB;aAC3D;YACD,QAAQ,EAAE;gBACR,WAAW,EAAE,0BAA0B;gBACvC,MAAM,EAAE,mBAAmB,CAAC,qBAAqB,CAAC,EAAE,MAAM,EAAE,aAAa,EAAE,CAAC;gBAC5E,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,OAAO,IAAI,8BAAqB;aAC5D;SACF,CAAC;IACJ,CAAC;IAED;;;OAGG;IACH,MAAM,CAAC,4BAA4B,CAKjC,IAQD;QACC,MAAM,EACJ,QAAQ,EACR,MAAM,EACN,YAAY,EAAE,cAAc,GAAG,EAAE,EACjC,SAAS,EAAE,mBAAmB,EAC9B,MAAM,EAAE,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,YAAY,EAAE,MAAM,EAAE,YAAY,EAAE,EAC5E,iBAAiB,GAAG,EAAE,EACtB,MAAM,GACP,GAAG,IAAI,CAAC;QACT,MAAM,EAAE,UAAU,EAAE,iBAAiB,GAAG,EAAE,EAAE,IAAI,EAAE,WAAW,EAAE,GAAG,cAAc,CAAC;QAEjF,mLAAmL;QACnL,MAAM,YAAY,GAAG,CAAC,MAAM,IAAI,EAAE,CAAW,CAAC;QAI9C,iEAAiE;QACjE,MAAM,gBAAgB,GAAG,CAAC,QAAmC,EAAuB,EAAE;YACpF,MAAM,cAAc,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;YAC9C,MAAM,UAAU,GAAG,cAAc,EAAE,YAAY,CAAC;YAEhD,IAAI,UAAU,IAAI,IAAI,EAAE,CAAC;gBACvB,OAAO,EAAE,UAAU,EAAE,iBAAiB,EAAE,IAAI,EAAE,WAAW,EAAE,CAAC;YAC9D,CAAC;YAED,IAAI,UAAU,CAAC,IAAI,KAAK,IAAI,EAAE,CAAC;gBAC7B,OAAO,EAAE,UAAU,EAAE,EAAE,EAAE,CAAC;YAC5B,CAAC;YAED,OAAO;gBACL,UAAU,EAAE,UAAU,CAAC,UAAU,IAAI,iBAAiB;gBACtD,IAAI,EAAE,UAAU,CAAC,IAAI,IAAI,WAAW;aACrC,CAAC;QACJ,CAAC,CAAC;QAIF,kHAAkH;QAClH,MAAM,qBAAqB,GAAG,CAAC,QAAmC,EAAoB,EAAE;YACtF,MAAM,cAAc,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;YAE9C,IAAI,cAAc,EAAE,YAAY,EAAE,IAAI,KAAK,IAAI,EAAE,CAAC;gBAChD,OAAO,SAAS,CAAC;YACnB,CAAC;YAED,MAAM,SAAS,GAAG,cAAc,EAAE,SAAS,CAAC;YAE5C,IAAI,SAAS,IAAI,IAAI,EAAE,CAAC;gBACtB,OAAO,mBAAmB,CAAC;YAC7B,CAAC;YAED,IAAI,KAAK,CAAC,OAAO,CAAC,SAAS,CAAC,EAAE,CAAC;gBAC7B,OAAO,SAAS,CAAC;YACnB,CAAC;YAED,IAAI,MAAM,IAAI,SAAS,EAAE,CAAC;gBACxB,OAAO,SAAS,CAAC;YACnB,CAAC;YAED,OAAO,SAAS,CAAC;QACnB,CAAC,CAAC;QAEF,MAAM,KAAK,GAAG,mBAAmB,CAAC,kBAAkB,CAAC,EAAE,MAAM,EAAE,YAAY,CAAC,KAAK,EAAE,QAAQ,EAAE,CAAC,CAAC;QAC/F,MAAM,IAAI,GAAG,mBAAmB,CAAC,iBAAiB,CAAC,EAAE,MAAM,EAAE,YAAY,CAAC,IAAI,EAAE,YAAY,EAAE,CAAC,CAAC;QAChG,MAAM,QAAQ,GAAG,mBAAmB,CAAC,qBAAqB,CAAC;YACzD,MAAM,EAAE,YAAY,CAAC,QAAQ;YAC7B,YAAY;YACZ,MAAM;SACP,CAAC,CAAC;QACH,MAAM,OAAO,GAAG,mBAAmB,CAAC,oBAAoB,CAAC;YACvD,MAAM,EAAE,YAAY,CAAC,OAAO;YAC5B,YAAY;SACb,CAAC,CAAC;QACH,MAAM,MAAM,GAAG,mBAAmB,CAAC,mBAAmB,CAAC;YACrD,MAAM,EAAE,YAAY,CAAC,MAAM;YAC3B,YAAY;YACZ,YAAY;YACZ,iBAAiB;SAClB,CAAC,CAAC;QACH,MAAM,UAAU,GAAG,mBAAmB,CAAC,uBAAuB,CAAC;YAC7D,MAAM,EAAE,YAAY,CAAC,UAAU;YAC/B,YAAY;YACZ,YAAY;YACZ,MAAM;YACN,iBAAiB;SAClB,CAAC,CAAC;QACH,MAAM,QAAQ,GAAG,mBAAmB,CAAC,qBAAqB,CAAC;YACzD,MAAM,EAAE,YAAY,CAAC,QAAQ;YAC7B,YAAY;YACZ,YAAY;YACZ,iBAAiB;SAClB,CAAC,CAAC;QACH,MAAM,UAAU,GAAG,mBAAmB,CAAC,uBAAuB,CAAC;YAC7D,MAAM,EAAE,YAAY,CAAC,UAAU;YAC/B,YAAY;YACZ,MAAM;SACP,CAAC,CAAC;QACH,MAAM,QAAQ,GAAG,mBAAmB,CAAC,qBAAqB,CAAC;YACzD,MAAM,EAAE,YAAY,CAAC,QAAQ;YAC7B,YAAY;SACb,CAAC,CAAC;QAEH,MAAM,EAAE,GAAG;YACT,KAAK,EAAE;gBACL,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,GAAG;gBACxB,IAAI,EAAE,kBAAS,CAAC,KAAK;gBACrB,WAAW,EAAE,wCAAwC;gBACrD,YAAY,EAAE,gBAAgB,CAAC,OAAO,CAAC;gBACvC,SAAS,EAAE,qBAAqB,CAAC,OAAO,CAAC;gBACzC,OAAO,EAAE,KAAK,CAAC,OAAO;gBACtB,SAAS,EAAE,IAAA,qBAAY,EAAC,KAAK,CAAC,QAAQ,CAAC;aACxC;YAED,IAAI,EAAE;gBACJ,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,GAAG;gBACxB,IAAI,EAAE,kBAAS,CAAC,IAAI;gBACpB,WAAW,EAAE,8DAA8D;gBAC3E,YAAY,EAAE,gBAAgB,CAAC,MAAM,CAAC;gBACtC,SAAS,EAAE,qBAAqB,CAAC,MAAM,CAAC;gBACxC,OAAO,EAAE,IAAI,CAAC,OAAO;gBACrB,SAAS,EAAE,IAAA,qBAAY,EAAC,IAAI,CAAC,QAAQ,CAAC;aACvC;YAED,UAAU,EAAE;gBACV,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,GAAG;gBACxB,IAAI,EAAE,OAAO;gBACb,WAAW,EAAE,0BAA0B;gBACvC,YAAY,EAAE,gBAAgB,CAAC,UAAU,CAAC;gBAC1C,SAAS,EAAE,qBAAqB,CAAC,UAAU,CAAC;gBAC5C,OAAO,EAAE,QAAQ,CAAC,OAAO;gBACzB,SAAS,EAAE,IAAA,qBAAY,EAAC,QAAQ,CAAC,QAAQ,CAAC;aAC3C;YAED,QAAQ,EAAE;gBACR,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,GAAG;gBACxB,IAAI,EAAE,kBAAS,CAAC,QAAQ;gBACxB,WAAW,EAAE,mCAAmC;gBAChD,YAAY,EAAE,gBAAgB,CAAC,SAAS,CAAC;gBACzC,SAAS,EAAE,qBAAqB,CAAC,SAAS,CAAC;gBAC3C,OAAO,EAAE,OAAO,CAAC,OAAO;gBACxB,SAAS,EAAE,IAAA,qBAAY,EAAC,OAAO,CAAC,QAAQ,CAAC;aAC1C;YAED,MAAM,EAAE;gBACN,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,IAAI;gBACzB,IAAI,EAAE,kBAAS,CAAC,IAAI;gBACpB,WAAW,EAAE,mBAAmB;gBAChC,YAAY,EAAE,gBAAgB,CAAC,QAAQ,CAAC;gBACxC,SAAS,EAAE,qBAAqB,CAAC,QAAQ,CAAC;gBAC1C,OAAO,EAAE;oBACP,IAAI,EAAE,IAAA,oBAAW,EAAC;wBAChB,WAAW,EAAE,gDAAgD;wBAC7D,MAAM,EAAE,MAAM,CAAC,OAAO,CAAC,IAAI;qBAC5B,CAAC;oBACF,OAAO,EAAE,MAAM,CAAC,OAAO,CAAC,OAAO;iBAChC;gBACD,SAAS,EAAE,IAAA,qBAAY,EAAC,MAAM,CAAC,QAAQ,CAAC;aACzC;YAED,YAAY,EAAE;gBACZ,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,KAAK;gBAC1B,IAAI,EAAE,OAAO;gBACb,WAAW,EAAE,6BAA6B;gBAC1C,YAAY,EAAE,gBAAgB,CAAC,YAAY,CAAC;gBAC5C,SAAS,EAAE,qBAAqB,CAAC,YAAY,CAAC;gBAC9C,OAAO,EAAE;oBACP,MAAM,EAAE,UAAU,CAAC,OAAO,CAAC,MAAM;oBACjC,IAAI,EAAE,IAAA,oBAAW,EAAC;wBAChB,WAAW,EAAE,oCAAoC;wBACjD,MAAM,EAAE,UAAU,CAAC,OAAO,CAAC,IAAI;qBAChC,CAAC;oBACF,OAAO,EAAE,UAAU,CAAC,OAAO,CAAC,OAAO;iBACpC;gBACD,SAAS,EAAE,IAAA,qBAAY,EAAC,UAAU,CAAC,QAAQ,CAAC;aAC7C;YAED,SAAS,EAAE;gBACT,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,KAAK;gBAC1B,IAAI,EAAE,kBAAS,CAAC,IAAI;gBACpB,WAAW,EAAE,8CAA8C;gBAC3D,YAAY,EAAE,gBAAgB,CAAC,UAAU,CAAC;gBAC1C,SAAS,EAAE,qBAAqB,CAAC,UAAU,CAAC;gBAC5C,OAAO,EAAE;oBACP,KAAK,EAAE,QAAQ,CAAC,OAAO,CAAC,KAAK;oBAC7B,IAAI,EAAE,IAAA,oBAAW,EAAC;wBAChB,WAAW,EAAE,sCAAsC;wBACnD,MAAM,EAAE,QAAQ,CAAC,OAAO,CAAC,IAAI;qBAC9B,CAAC;oBACF,OAAO,EAAE,QAAQ,CAAC,OAAO,CAAC,OAAO;iBAClC;gBACD,SAAS,EAAE,IAAA,qBAAY,EAAC,QAAQ,CAAC,QAAQ,CAAC;aAC3C;YAED,YAAY,EAAE;gBACZ,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,MAAM;gBAC3B,IAAI,EAAE,OAAO;gBACb,WAAW,EAAE,oCAAoC;gBACjD,YAAY,EAAE,gBAAgB,CAAC,YAAY,CAAC;gBAC5C,SAAS,EAAE,qBAAqB,CAAC,YAAY,CAAC;gBAC9C,OAAO,EAAE,UAAU,CAAC,OAAO;gBAC3B,SAAS,EAAE,IAAA,qBAAY,EAAC,UAAU,CAAC,QAAQ,CAAC;aAC7C;YAED,SAAS,EAAE;gBACT,MAAM,EAAE,aAAI,CAAC,OAAO,CAAC,MAAM;gBAC3B,IAAI,EAAE,kBAAS,CAAC,IAAI;gBACpB,WAAW,EAAE,6DAA6D;gBAC1E,YAAY,EAAE,gBAAgB,CAAC,UAAU,CAAC;gBAC1C,SAAS,EAAE,qBAAqB,CAAC,UAAU,CAAC;gBAC5C,OAAO,EAAE;oBACP,KAAK,EAAE,QAAQ,CAAC,OAAO,CAAC,KAAK;oBAC7B,GAAG,CAAC,QAAQ,CAAC,OAAO,CAAC,IAAI;wBACvB,CAAC,CAAC;4BACE,IAAI,EAAE,IAAA,oBAAW,EAAC;gCAChB,WAAW,EAAE,oDAAoD;gCACjE,MAAM,EAAE,QAAQ,CAAC,OAAO,CAAC,IAAI;gCAC7B,QAAQ,EAAE,KAAK;6BAChB,CAAC;yBACH;wBACH,CAAC,CAAC,EAAE,CAAC;oBACP,OAAO,EAAE,QAAQ,CAAC,OAAO,CAAC,OAAO;iBAClC;gBACD,SAAS,EAAE,IAAA,qBAAY,EAAC,QAAQ,CAAC,QAAQ,CAAC;aAC3C;SACO,CAAC;QAEX,OAAO,EAAE,CAAC;IACZ,CAAC;CACF;AAjkBD,kDAikBC;AAEY,QAAA,wBAAwB,GAAG,mBAAmB,CAAC,wBAAwB,CAAC;AACxE,QAAA,kBAAkB,GAAG,mBAAmB,CAAC,kBAAkB,CAAC;AAC5D,QAAA,iBAAiB,GAAG,mBAAmB,CAAC,iBAAiB,CAAC;AAC1D,QAAA,qBAAqB,GAAG,mBAAmB,CAAC,qBAAqB,CAAC;AAClE,QAAA,oBAAoB,GAAG,mBAAmB,CAAC,oBAAoB,CAAC;AAChE,QAAA,mBAAmB,GAAG,mBAAmB,CAAC,mBAAmB,CAAC;AAC9D,QAAA,4BAA4B,GAAG,mBAAmB,CAAC,4BAA4B,CAAC","sourcesContent":["import type { TAuthMode, TAuthStrategy } from '@/base/auth/authenticate/common/constants';\nimport type { IAuthorizationSpec } from '@/base/auth/authorize/common/types';\nimport type { TIdSchemaType } from '@/base/models/common';\nimport { idParamsSchema, jsonContent, jsonResponse } from '@/base/models/common';\nimport { CountSchema } from '@/base/repositories/common';\nimport { FilterQuerySchema, WhereSchema } from '@/base/repositories/query-schemas';\nimport type { TAnyObjectSchema } from '@/base/controllers/common/schema-builders';\nimport { z } from '@hono/zod-openapi';\nimport { HTTP } from '@venizia/ignis-helpers/common';\nimport { getError } from '@venizia/ignis-helpers/core';\nimport type { ICustomizableRoutes } from '../common';\nimport {\n commonResponseHeaders,\n defaultRequestHeaders,\n findResponseHeaders,\n RestPaths,\n trackableHeaders,\n} from '../common';\n\n/** Picks user-overridden response schema if present (and non-undefined), else the default. */\ntype TResolvedResponseSchema<C, D extends z.ZodType> = C extends {\n response: {\n schema: infer S extends z.ZodType;\n };\n}\n ? S\n : D;\n\n/**\n * Every method here is an unbound static, called from the exported aliases below without a\n * receiver - a method must call another via `RouteConfigResolver.other(...)`, never\n * `this.other(...)`, or `this` is `undefined` at the call site.\n */\nexport class RouteConfigResolver {\n /** Path params always reach the validator as strings, so a number-typed id must be coerced before `z.number()` sees it - `idParamsSchema` alone rejects `/accounts/7`. */\n private static idPathParamsSchema(opts: { idType: TIdSchemaType }) {\n const { idType } = opts;\n\n if (idType !== 'number') {\n return idParamsSchema({ idType });\n }\n\n return z.object({\n id: z.coerce.number().openapi({\n param: { name: 'id', in: 'path', description: 'The unique id of the resource' },\n examples: [1, 2, 3],\n }),\n });\n }\n\n /**\n * The default body of a write route: the entity schema without the keys the entity stamps, and on\n * an update without `id` - the path or `where` names the rows. Zod strips a left-out key a client\n * sends. With nothing to leave out the schema itself is the body, refinements and OpenAPI name kept.\n */\n private static toWriteBodySchema(opts: {\n schema: TAnyObjectSchema;\n route: keyof ICustomizableRoutes;\n serverStampedKeys: string[];\n }): TAnyObjectSchema {\n const { schema, route, serverStampedKeys } = opts;\n const droppedKeys = route === 'create' ? serverStampedKeys : [...serverStampedKeys, 'id'];\n // A `.transform()` pipe has no shape to read, so every key it might hold counts.\n const isObjectSchema = schema instanceof z.ZodObject;\n const omittedKeys = isObjectSchema\n ? droppedKeys.filter(key => Object.hasOwn(schema.shape, key))\n : droppedKeys;\n\n if (omittedKeys.length === 0) {\n return schema;\n }\n\n if (!isObjectSchema || schema.def.checks?.length) {\n throw getError({\n message: `[defineControllerRouteConfigs] Cannot build the default ${route} body | keys to leave out: ${omittedKeys.join(', ')} | The schema is refined or transformed, so zod cannot remove them | Pass routes.${route}.request.body`,\n });\n }\n\n const mask: Record<string, true> = {};\n for (const key of omittedKeys) {\n mask[key] = true;\n }\n\n return schema.omit(mask);\n }\n\n /** Picks the caller's per-route `request.params` override, else the entity's id path-param schema. */\n private static resolveIdParams<\n C extends { request?: { params?: TAnyObjectSchema } } | undefined,\n >(opts: { config: C; idType: TIdSchemaType }) {\n const { config, idType } = opts;\n return config?.request?.params ?? RouteConfigResolver.idPathParamsSchema({ idType });\n }\n\n /** Creates conditional count response schema. */\n static conditionalCountResponse<T extends z.ZodType>(dataSchema: T) {\n return z.union([\n CountSchema.extend({ data: dataSchema }).openapi({\n description: 'Response with count (when x-request-count header is \"true\" or omitted)',\n }),\n dataSchema.openapi({\n description: 'Data only response (when x-request-count header is \"false\")',\n }),\n ]);\n }\n\n /** Resolves a route's response schema - user override or default. Holds the one cast every `resolve*Config` needs: generic `C` is only known by its wider structural constraint, so it cannot be proven at the value level to collapse to `TResolvedResponseSchema`. */\n private static resolveResponseSchema<\n C extends { response?: { schema?: z.ZodType } } | undefined,\n D extends z.ZodType,\n >(opts: { config: C; defaultSchema: D }): TResolvedResponseSchema<C, D> {\n const { config, defaultSchema } = opts;\n return (config?.response?.schema ?? defaultSchema) as TResolvedResponseSchema<C, D>;\n }\n\n static resolveCountConfig<C extends ICustomizableRoutes['count']>(opts: {\n config: C;\n isStrict: boolean;\n }) {\n const { config, isStrict } = opts;\n const defaultQuery = z\n .object({\n where: isStrict\n ? WhereSchema\n : z.optional(WhereSchema).openapi({ description: 'Filter conditions' }),\n })\n .openapi({ description: 'Count query params' });\n\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? trackableHeaders,\n },\n response: {\n description: 'Total count of matching records',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema: CountSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n static resolveFindConfig<\n C extends ICustomizableRoutes['find'],\n FindSchema extends TAnyObjectSchema,\n >(opts: { config: C; selectSchema: FindSchema }) {\n const { config, selectSchema } = opts;\n const defaultQuery = FilterQuerySchema;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(z.array(selectSchema));\n\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Array of matching records (with optional count)',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? findResponseHeaders,\n },\n };\n }\n\n static resolveFindByIdConfig<\n C extends ICustomizableRoutes['findById'],\n FindByIdSchema extends TAnyObjectSchema,\n >(opts: { idType: TIdSchemaType; config: C; selectSchema: FindByIdSchema }) {\n const { config, selectSchema, idType } = opts;\n const defaultQuery = FilterQuerySchema.openapi({\n description: 'Filter with fields, order, include (where ignored)',\n });\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n\n return {\n request: {\n params: RouteConfigResolver.resolveIdParams({ config, idType }),\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Single record matching ID or null',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n static resolveFindOneConfig<\n C extends ICustomizableRoutes['findOne'],\n FindOneSchema extends TAnyObjectSchema,\n >(opts: { config: C; selectSchema: FindOneSchema }) {\n const { config, selectSchema } = opts;\n const defaultQuery = FilterQuerySchema.openapi({\n description: 'Filter with where, fields, order, include',\n });\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'First matching record or null',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n /** `serverStampedKeys` - what the entity reports from `getServerStampedKeys()`; the default body leaves them out. */\n static resolveCreateConfig<\n C extends ICustomizableRoutes['create'],\n SelectSchema extends TAnyObjectSchema,\n CreateSchema extends TAnyObjectSchema,\n >(opts: {\n config: C;\n selectSchema: SelectSchema;\n createSchema: CreateSchema;\n serverStampedKeys?: string[];\n }) {\n const { config, selectSchema, createSchema, serverStampedKeys = [] } = opts;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n\n return {\n request: {\n body:\n config?.request?.body ??\n RouteConfigResolver.toWriteBodySchema({\n schema: createSchema,\n route: 'create',\n serverStampedKeys,\n }),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Created record with generated fields (id, createdAt, etc.)',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveUpdateByIdConfig<\n C extends ICustomizableRoutes['updateById'],\n SelectSchema extends TAnyObjectSchema,\n UpdateSchema extends TAnyObjectSchema,\n >(opts: {\n idType: TIdSchemaType;\n config: C;\n selectSchema: SelectSchema;\n updateSchema: UpdateSchema;\n serverStampedKeys: string[];\n }) {\n const { config, selectSchema, updateSchema, idType, serverStampedKeys } = opts;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n return {\n request: {\n params: RouteConfigResolver.resolveIdParams({ config, idType }),\n body:\n config?.request?.body ??\n RouteConfigResolver.toWriteBodySchema({\n schema: updateSchema,\n route: 'updateById',\n serverStampedKeys,\n }),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Updated record with all current fields',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveUpdateByConfig<\n C extends ICustomizableRoutes['updateBy'],\n SelectSchema extends TAnyObjectSchema,\n UpdateSchema extends TAnyObjectSchema,\n >(opts: {\n config: C;\n selectSchema: SelectSchema;\n updateSchema: UpdateSchema;\n serverStampedKeys: string[];\n }) {\n const { config, selectSchema, updateSchema, serverStampedKeys } = opts;\n const defaultQuery = z.object({ where: WhereSchema.optional() }).openapi({\n description:\n 'Where condition selecting the records to update - here or in the body, not both',\n });\n // Built only without a custom body: a custom body must not trip the entity schema's checks.\n const buildDefaultBody = () => {\n const writableSchema = RouteConfigResolver.toWriteBodySchema({\n schema: updateSchema,\n route: 'updateBy',\n serverStampedKeys,\n });\n // A model with a real `where` column keeps it: the body reserves the name only when it is\n // free, and the handler then simply finds no `where` there.\n return 'where' in writableSchema.shape\n ? writableSchema\n : writableSchema.extend({ where: WhereSchema.optional() });\n };\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(z.array(selectSchema));\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n body: config?.request?.body ?? buildDefaultBody(),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Array of updated records',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveDeleteByIdConfig<\n C extends ICustomizableRoutes['deleteById'],\n SelectSchema extends TAnyObjectSchema,\n >(opts: { idType: TIdSchemaType; config: C; selectSchema: SelectSchema }) {\n const { config, selectSchema, idType } = opts;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n return {\n request: {\n params: RouteConfigResolver.resolveIdParams({ config, idType }),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Deleted record data',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveDeleteByConfig<\n C extends ICustomizableRoutes['deleteBy'],\n SelectSchema extends TAnyObjectSchema,\n >(opts: { config: C; selectSchema: SelectSchema }) {\n const { config, selectSchema } = opts;\n const defaultQuery = z.object({ where: WhereSchema.optional() }).openapi({\n description:\n 'Where condition selecting the records to delete - here or in the body, not both',\n });\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(z.array(selectSchema));\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n // No DEFAULT body schema. Declaring one makes `@hono/zod-openapi` gate the media type, and a\n // client that sends `content-type: application/json` with no body then gets 400 where it used\n // to get 200. The handler reads the body itself; name one here to get the Swagger editor.\n body: config?.request?.body,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Array of deleted records',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n /**\n * Generates complete route configurations for a CRUD controller. `serverStampedKeys` - what the\n * entity reports from `getServerStampedKeys()`; the default write bodies leave them out.\n */\n static defineControllerRouteConfigs<\n Routes extends ICustomizableRoutes,\n SelectSchema extends TAnyObjectSchema,\n CreateSchema extends TAnyObjectSchema,\n UpdateSchema extends TAnyObjectSchema,\n >(opts: {\n isStrict: boolean;\n idType: TIdSchemaType;\n authenticate?: { strategies?: TAuthStrategy[]; mode?: TAuthMode };\n authorize?: IAuthorizationSpec | IAuthorizationSpec[];\n schema: { select: SelectSchema; create: CreateSchema; update: UpdateSchema };\n serverStampedKeys?: string[];\n routes?: Routes;\n }) {\n const {\n isStrict,\n idType,\n authenticate: controllerAuth = {},\n authorize: controllerAuthorize,\n schema: { select: selectSchema, create: createSchema, update: updateSchema },\n serverStampedKeys = [],\n routes,\n } = opts;\n const { strategies: defaultStrategies = [], mode: defaultMode } = controllerAuth;\n\n // `Routes` is caller-bound but otherwise unconstrained here, so `{}` cannot be proven to satisfy it structurally even though every field ICustomizableRoutes declares is optional.\n const routesConfig = (routes ?? {}) as Routes;\n\n type TAuthenticateConfig = { strategies?: TAuthStrategy[]; mode?: TAuthMode };\n\n /** Priority: endpoint authenticate > controller authenticate. */\n const resolveRouteAuth = (routeKey: keyof ICustomizableRoutes): TAuthenticateConfig => {\n const endpointConfig = routesConfig[routeKey];\n const authConfig = endpointConfig?.authenticate;\n\n if (authConfig == null) {\n return { strategies: defaultStrategies, mode: defaultMode };\n }\n\n if (authConfig.skip === true) {\n return { strategies: [] };\n }\n\n return {\n strategies: authConfig.strategies ?? defaultStrategies,\n mode: authConfig.mode ?? defaultMode,\n };\n };\n\n type TAuthorizeConfig = IAuthorizationSpec | IAuthorizationSpec[] | undefined;\n\n /** Priority: endpoint authenticate.skip > endpoint authorize.skip > endpoint authorize > controller authorize. */\n const resolveRouteAuthorize = (routeKey: keyof ICustomizableRoutes): TAuthorizeConfig => {\n const endpointConfig = routesConfig[routeKey];\n\n if (endpointConfig?.authenticate?.skip === true) {\n return undefined;\n }\n\n const authorize = endpointConfig?.authorize;\n\n if (authorize == null) {\n return controllerAuthorize;\n }\n\n if (Array.isArray(authorize)) {\n return authorize;\n }\n\n if ('skip' in authorize) {\n return undefined;\n }\n\n return authorize;\n };\n\n const count = RouteConfigResolver.resolveCountConfig({ config: routesConfig.count, isStrict });\n const find = RouteConfigResolver.resolveFindConfig({ config: routesConfig.find, selectSchema });\n const findById = RouteConfigResolver.resolveFindByIdConfig({\n config: routesConfig.findById,\n selectSchema,\n idType,\n });\n const findOne = RouteConfigResolver.resolveFindOneConfig({\n config: routesConfig.findOne,\n selectSchema,\n });\n const create = RouteConfigResolver.resolveCreateConfig({\n config: routesConfig.create,\n selectSchema,\n createSchema,\n serverStampedKeys,\n });\n const updateById = RouteConfigResolver.resolveUpdateByIdConfig({\n config: routesConfig.updateById,\n selectSchema,\n updateSchema,\n idType,\n serverStampedKeys,\n });\n const updateBy = RouteConfigResolver.resolveUpdateByConfig({\n config: routesConfig.updateBy,\n selectSchema,\n updateSchema,\n serverStampedKeys,\n });\n const deleteById = RouteConfigResolver.resolveDeleteByIdConfig({\n config: routesConfig.deleteById,\n selectSchema,\n idType,\n });\n const deleteBy = RouteConfigResolver.resolveDeleteByConfig({\n config: routesConfig.deleteBy,\n selectSchema,\n });\n\n const rs = {\n COUNT: {\n method: HTTP.Methods.GET,\n path: RestPaths.COUNT,\n description: 'Count records matching where condition',\n authenticate: resolveRouteAuth('count'),\n authorize: resolveRouteAuthorize('count'),\n request: count.request,\n responses: jsonResponse(count.response),\n },\n\n FIND: {\n method: HTTP.Methods.GET,\n path: RestPaths.ROOT,\n description: 'Find records with filter, pagination, sorting, and relations',\n authenticate: resolveRouteAuth('find'),\n authorize: resolveRouteAuthorize('find'),\n request: find.request,\n responses: jsonResponse(find.response),\n },\n\n FIND_BY_ID: {\n method: HTTP.Methods.GET,\n path: '/{id}',\n description: 'Find single record by ID',\n authenticate: resolveRouteAuth('findById'),\n authorize: resolveRouteAuthorize('findById'),\n request: findById.request,\n responses: jsonResponse(findById.response),\n },\n\n FIND_ONE: {\n method: HTTP.Methods.GET,\n path: RestPaths.FIND_ONE,\n description: 'Find first record matching filter',\n authenticate: resolveRouteAuth('findOne'),\n authorize: resolveRouteAuthorize('findOne'),\n request: findOne.request,\n responses: jsonResponse(findOne.response),\n },\n\n CREATE: {\n method: HTTP.Methods.POST,\n path: RestPaths.ROOT,\n description: 'Create new record',\n authenticate: resolveRouteAuth('create'),\n authorize: resolveRouteAuthorize('create'),\n request: {\n body: jsonContent({\n description: 'Record data (required fields must be provided)',\n schema: create.request.body,\n }),\n headers: create.request.headers,\n },\n responses: jsonResponse(create.response),\n },\n\n UPDATE_BY_ID: {\n method: HTTP.Methods.PATCH,\n path: '/{id}',\n description: 'Partial update record by ID',\n authenticate: resolveRouteAuth('updateById'),\n authorize: resolveRouteAuthorize('updateById'),\n request: {\n params: updateById.request.params,\n body: jsonContent({\n description: 'Partial data (only changed fields)',\n schema: updateById.request.body,\n }),\n headers: updateById.request.headers,\n },\n responses: jsonResponse(updateById.response),\n },\n\n UPDATE_BY: {\n method: HTTP.Methods.PATCH,\n path: RestPaths.ROOT,\n description: 'Bulk update records matching where condition',\n authenticate: resolveRouteAuth('updateBy'),\n authorize: resolveRouteAuthorize('updateBy'),\n request: {\n query: updateBy.request.query,\n body: jsonContent({\n description: 'Partial data to apply to all matches',\n schema: updateBy.request.body,\n }),\n headers: updateBy.request.headers,\n },\n responses: jsonResponse(updateBy.response),\n },\n\n DELETE_BY_ID: {\n method: HTTP.Methods.DELETE,\n path: '/{id}',\n description: 'Delete record by ID (irreversible)',\n authenticate: resolveRouteAuth('deleteById'),\n authorize: resolveRouteAuthorize('deleteById'),\n request: deleteById.request,\n responses: jsonResponse(deleteById.response),\n },\n\n DELETE_BY: {\n method: HTTP.Methods.DELETE,\n path: RestPaths.ROOT,\n description: 'Bulk delete records matching where condition (irreversible)',\n authenticate: resolveRouteAuth('deleteBy'),\n authorize: resolveRouteAuthorize('deleteBy'),\n request: {\n query: deleteBy.request.query,\n ...(deleteBy.request.body\n ? {\n body: jsonContent({\n description: 'Where condition, when it does not fit in the query',\n schema: deleteBy.request.body,\n required: false,\n }),\n }\n : {}),\n headers: deleteBy.request.headers,\n },\n responses: jsonResponse(deleteBy.response),\n },\n } as const;\n\n return rs;\n }\n}\n\nexport const conditionalCountResponse = RouteConfigResolver.conditionalCountResponse;\nexport const resolveCountConfig = RouteConfigResolver.resolveCountConfig;\nexport const resolveFindConfig = RouteConfigResolver.resolveFindConfig;\nexport const resolveFindByIdConfig = RouteConfigResolver.resolveFindByIdConfig;\nexport const resolveFindOneConfig = RouteConfigResolver.resolveFindOneConfig;\nexport const resolveCreateConfig = RouteConfigResolver.resolveCreateConfig;\nexport const defineControllerRouteConfigs = RouteConfigResolver.defineControllerRouteConfigs;\n"]}
1
+ {"version":3,"file":"definition.js","sourceRoot":"","sources":["../../../../../src/base/controllers/factory/definition.ts"],"names":[],"mappings":"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","sourcesContent":["import type { TAuthMode, TAuthStrategy } from '@/base/auth/authenticate/common/constants';\nimport type { IAuthorizationSpec } from '@/base/auth/authorize/common/types';\nimport type { TIdSchemaType } from '@/base/models/common';\nimport { idParamsSchema, jsonContent, jsonResponse } from '@/base/models/common';\nimport { CountSchema } from '@/base/repositories/common';\nimport { FilterQuerySchema, WhereSchema } from '@/base/repositories/query-schemas';\nimport type { TAnyObjectSchema } from '@/base/controllers/common/schema-builders';\nimport { z } from '@hono/zod-openapi';\nimport { HTTP } from '@venizia/ignis-helpers/common';\nimport { getError } from '@venizia/ignis-helpers/core';\nimport type { ICustomizableRoutes } from '../common';\nimport {\n commonResponseHeaders,\n defaultRequestHeaders,\n findResponseHeaders,\n RestPaths,\n trackableHeaders,\n} from '../common';\n\n/** Picks user-overridden response schema if present (and non-undefined), else the default. */\ntype TResolvedResponseSchema<C, D extends z.ZodType> = C extends {\n response: {\n schema: infer S extends z.ZodType;\n };\n}\n ? S\n : D;\n\n/**\n * Every method here is an unbound static, called from the exported aliases below without a\n * receiver - a method must call another via `RouteConfigResolver.other(...)`, never\n * `this.other(...)`, or `this` is `undefined` at the call site.\n */\nexport class RouteConfigResolver {\n /** Path params always reach the validator as strings, so a number-typed id must be coerced before `z.number()` sees it - `idParamsSchema` alone rejects `/accounts/7`. */\n private static idPathParamsSchema(opts: { idType: TIdSchemaType }) {\n const { idType } = opts;\n\n if (idType !== 'number') {\n return idParamsSchema({ idType });\n }\n\n return z.object({\n id: z.coerce.number().openapi({\n param: { name: 'id', in: 'path', description: 'The unique id of the resource' },\n examples: [1, 2, 3],\n }),\n });\n }\n\n /**\n * The default body of a write route: the entity schema without the keys the entity stamps, and on\n * an update without `id` - the path or `where` names the rows. Zod strips a left-out key a client\n * sends. With nothing to leave out the schema itself is the body, refinements and OpenAPI name kept.\n */\n private static toWriteBodySchema(opts: {\n schema: TAnyObjectSchema;\n route: keyof ICustomizableRoutes;\n serverStampedKeys: string[];\n }): TAnyObjectSchema {\n const { schema, route, serverStampedKeys } = opts;\n const droppedKeys = route === 'create' ? serverStampedKeys : [...serverStampedKeys, 'id'];\n // A `.transform()` pipe has no shape to read, so every key it might hold counts.\n const isObjectSchema = schema instanceof z.ZodObject;\n const omittedKeys = isObjectSchema\n ? droppedKeys.filter((key) => Object.hasOwn(schema.shape, key))\n : droppedKeys;\n\n if (omittedKeys.length === 0) {\n return schema;\n }\n\n if (!isObjectSchema || schema.def.checks?.length) {\n throw getError({\n message: `[defineControllerRouteConfigs] Cannot build the default ${route} body | keys to leave out: ${omittedKeys.join(', ')} | The schema is refined or transformed, so zod cannot remove them | Pass routes.${route}.request.body`,\n });\n }\n\n const mask: Record<string, true> = {};\n for (const key of omittedKeys) {\n mask[key] = true;\n }\n\n return schema.omit(mask);\n }\n\n /** Picks the caller's per-route `request.params` override, else the entity's id path-param schema. */\n private static resolveIdParams<\n C extends { request?: { params?: TAnyObjectSchema } } | undefined,\n >(opts: { config: C; idType: TIdSchemaType }) {\n const { config, idType } = opts;\n return config?.request?.params ?? RouteConfigResolver.idPathParamsSchema({ idType });\n }\n\n /** Creates conditional count response schema. */\n static conditionalCountResponse<T extends z.ZodType>(dataSchema: T) {\n return z.union([\n CountSchema.extend({ data: dataSchema }).openapi({\n description: 'Response with count (when x-request-count header is \"true\" or omitted)',\n }),\n dataSchema.openapi({\n description: 'Data only response (when x-request-count header is \"false\")',\n }),\n ]);\n }\n\n /** Resolves a route's response schema - user override or default. Holds the one cast every `resolve*Config` needs: generic `C` is only known by its wider structural constraint, so it cannot be proven at the value level to collapse to `TResolvedResponseSchema`. */\n private static resolveResponseSchema<\n C extends { response?: { schema?: z.ZodType } } | undefined,\n D extends z.ZodType,\n >(opts: { config: C; defaultSchema: D }): TResolvedResponseSchema<C, D> {\n const { config, defaultSchema } = opts;\n return (config?.response?.schema ?? defaultSchema) as TResolvedResponseSchema<C, D>;\n }\n\n static resolveCountConfig<C extends ICustomizableRoutes['count']>(opts: {\n config: C;\n isStrict: boolean;\n }) {\n const { config, isStrict } = opts;\n const defaultQuery = z\n .object({\n where: isStrict\n ? WhereSchema\n : z.optional(WhereSchema).openapi({ description: 'Filter conditions' }),\n })\n .openapi({ description: 'Count query params' });\n\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? trackableHeaders,\n },\n response: {\n description: 'Total count of matching records',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema: CountSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n static resolveFindConfig<\n C extends ICustomizableRoutes['find'],\n FindSchema extends TAnyObjectSchema,\n >(opts: { config: C; selectSchema: FindSchema }) {\n const { config, selectSchema } = opts;\n const defaultQuery = FilterQuerySchema;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(z.array(selectSchema));\n\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Array of matching records (with optional count)',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? findResponseHeaders,\n },\n };\n }\n\n static resolveFindByIdConfig<\n C extends ICustomizableRoutes['findById'],\n FindByIdSchema extends TAnyObjectSchema,\n >(opts: { idType: TIdSchemaType; config: C; selectSchema: FindByIdSchema }) {\n const { config, selectSchema, idType } = opts;\n const defaultQuery = FilterQuerySchema.openapi({\n description: 'Filter with fields, order, include (where ignored)',\n });\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n\n return {\n request: {\n params: RouteConfigResolver.resolveIdParams({ config, idType }),\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Single record matching ID or null',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n static resolveFindOneConfig<\n C extends ICustomizableRoutes['findOne'],\n FindOneSchema extends TAnyObjectSchema,\n >(opts: { config: C; selectSchema: FindOneSchema }) {\n const { config, selectSchema } = opts;\n const defaultQuery = FilterQuerySchema.openapi({\n description: 'Filter with where, fields, order, include',\n });\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'First matching record or null',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n /** `serverStampedKeys` - what the entity reports from `getServerStampedKeys()`; the default body leaves them out. */\n static resolveCreateConfig<\n C extends ICustomizableRoutes['create'],\n SelectSchema extends TAnyObjectSchema,\n CreateSchema extends TAnyObjectSchema,\n >(opts: {\n config: C;\n selectSchema: SelectSchema;\n createSchema: CreateSchema;\n serverStampedKeys?: string[];\n }) {\n const { config, selectSchema, createSchema, serverStampedKeys = [] } = opts;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n\n return {\n request: {\n body:\n config?.request?.body ??\n RouteConfigResolver.toWriteBodySchema({\n schema: createSchema,\n route: 'create',\n serverStampedKeys,\n }),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Created record with generated fields (id, createdAt, etc.)',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveUpdateByIdConfig<\n C extends ICustomizableRoutes['updateById'],\n SelectSchema extends TAnyObjectSchema,\n UpdateSchema extends TAnyObjectSchema,\n >(opts: {\n idType: TIdSchemaType;\n config: C;\n selectSchema: SelectSchema;\n updateSchema: UpdateSchema;\n serverStampedKeys: string[];\n }) {\n const { config, selectSchema, updateSchema, idType, serverStampedKeys } = opts;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n return {\n request: {\n params: RouteConfigResolver.resolveIdParams({ config, idType }),\n body:\n config?.request?.body ??\n RouteConfigResolver.toWriteBodySchema({\n schema: updateSchema,\n route: 'updateById',\n serverStampedKeys,\n }),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Updated record with all current fields',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveUpdateByConfig<\n C extends ICustomizableRoutes['updateBy'],\n SelectSchema extends TAnyObjectSchema,\n UpdateSchema extends TAnyObjectSchema,\n >(opts: {\n config: C;\n selectSchema: SelectSchema;\n updateSchema: UpdateSchema;\n serverStampedKeys: string[];\n }) {\n const { config, selectSchema, updateSchema, serverStampedKeys } = opts;\n const defaultQuery = z.object({ where: WhereSchema.optional() }).openapi({\n description:\n 'Where condition selecting the records to update - here or in the body, not both',\n });\n // Built only without a custom body: a custom body must not trip the entity schema's checks.\n const buildDefaultBody = () => {\n const writableSchema = RouteConfigResolver.toWriteBodySchema({\n schema: updateSchema,\n route: 'updateBy',\n serverStampedKeys,\n });\n // A model with a real `where` column keeps it: the body reserves the name only when it is\n // free, and the handler then simply finds no `where` there.\n return 'where' in writableSchema.shape\n ? writableSchema\n : writableSchema.extend({ where: WhereSchema.optional() });\n };\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(z.array(selectSchema));\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n body: config?.request?.body ?? buildDefaultBody(),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Array of updated records',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveDeleteByIdConfig<\n C extends ICustomizableRoutes['deleteById'],\n SelectSchema extends TAnyObjectSchema,\n >(opts: { idType: TIdSchemaType; config: C; selectSchema: SelectSchema }) {\n const { config, selectSchema, idType } = opts;\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(selectSchema);\n return {\n request: {\n params: RouteConfigResolver.resolveIdParams({ config, idType }),\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Deleted record data',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n private static resolveDeleteByConfig<\n C extends ICustomizableRoutes['deleteBy'],\n SelectSchema extends TAnyObjectSchema,\n >(opts: { config: C; selectSchema: SelectSchema }) {\n const { config, selectSchema } = opts;\n const defaultQuery = z.object({ where: WhereSchema.optional() }).openapi({\n description:\n 'Where condition selecting the records to delete - here or in the body, not both',\n });\n const defaultSchema = RouteConfigResolver.conditionalCountResponse(z.array(selectSchema));\n return {\n request: {\n query: config?.request?.query ?? defaultQuery,\n // No DEFAULT body schema. Declaring one makes `@hono/zod-openapi` gate the media type, and a\n // client that sends `content-type: application/json` with no body then gets 400 where it used\n // to get 200. The handler reads the body itself; name one here to get the Swagger editor.\n body: config?.request?.body,\n headers: config?.request?.headers ?? defaultRequestHeaders,\n },\n response: {\n description: 'Array of deleted records',\n schema: RouteConfigResolver.resolveResponseSchema({ config, defaultSchema }),\n headers: config?.response?.headers ?? commonResponseHeaders,\n },\n };\n }\n\n /**\n * Generates complete route configurations for a CRUD controller. `serverStampedKeys` - what the\n * entity reports from `getServerStampedKeys()`; the default write bodies leave them out.\n */\n static defineControllerRouteConfigs<\n Routes extends ICustomizableRoutes,\n SelectSchema extends TAnyObjectSchema,\n CreateSchema extends TAnyObjectSchema,\n UpdateSchema extends TAnyObjectSchema,\n >(opts: {\n isStrict: boolean;\n idType: TIdSchemaType;\n authenticate?: { strategies?: TAuthStrategy[]; mode?: TAuthMode };\n authorize?: IAuthorizationSpec | IAuthorizationSpec[];\n schema: { select: SelectSchema; create: CreateSchema; update: UpdateSchema };\n serverStampedKeys?: string[];\n routes?: Routes;\n }) {\n const {\n isStrict,\n idType,\n authenticate: controllerAuth = {},\n authorize: controllerAuthorize,\n schema: { select: selectSchema, create: createSchema, update: updateSchema },\n serverStampedKeys = [],\n routes,\n } = opts;\n const { strategies: defaultStrategies = [], mode: defaultMode } = controllerAuth;\n\n // `Routes` is caller-bound but otherwise unconstrained here, so `{}` cannot be proven to satisfy it structurally even though every field ICustomizableRoutes declares is optional.\n const routesConfig = (routes ?? {}) as Routes;\n\n type TAuthenticateConfig = { strategies?: TAuthStrategy[]; mode?: TAuthMode };\n\n /** Priority: endpoint authenticate > controller authenticate. */\n const resolveRouteAuth = (routeKey: keyof ICustomizableRoutes): TAuthenticateConfig => {\n const endpointConfig = routesConfig[routeKey];\n const authConfig = endpointConfig?.authenticate;\n\n if (authConfig == null) {\n return { strategies: defaultStrategies, mode: defaultMode };\n }\n\n if (authConfig.skip === true) {\n return { strategies: [] };\n }\n\n return {\n strategies: authConfig.strategies ?? defaultStrategies,\n mode: authConfig.mode ?? defaultMode,\n };\n };\n\n type TAuthorizeConfig = IAuthorizationSpec | IAuthorizationSpec[] | undefined;\n\n /** Priority: endpoint authenticate.skip > endpoint authorize.skip > endpoint authorize > controller authorize. */\n const resolveRouteAuthorize = (routeKey: keyof ICustomizableRoutes): TAuthorizeConfig => {\n const endpointConfig = routesConfig[routeKey];\n\n if (endpointConfig?.authenticate?.skip === true) {\n return undefined;\n }\n\n const authorize = endpointConfig?.authorize;\n\n if (authorize == null) {\n return controllerAuthorize;\n }\n\n if (Array.isArray(authorize)) {\n return authorize;\n }\n\n if ('skip' in authorize) {\n return undefined;\n }\n\n return authorize;\n };\n\n const count = RouteConfigResolver.resolveCountConfig({ config: routesConfig.count, isStrict });\n const find = RouteConfigResolver.resolveFindConfig({ config: routesConfig.find, selectSchema });\n const findById = RouteConfigResolver.resolveFindByIdConfig({\n config: routesConfig.findById,\n selectSchema,\n idType,\n });\n const findOne = RouteConfigResolver.resolveFindOneConfig({\n config: routesConfig.findOne,\n selectSchema,\n });\n const create = RouteConfigResolver.resolveCreateConfig({\n config: routesConfig.create,\n selectSchema,\n createSchema,\n serverStampedKeys,\n });\n const updateById = RouteConfigResolver.resolveUpdateByIdConfig({\n config: routesConfig.updateById,\n selectSchema,\n updateSchema,\n idType,\n serverStampedKeys,\n });\n const updateBy = RouteConfigResolver.resolveUpdateByConfig({\n config: routesConfig.updateBy,\n selectSchema,\n updateSchema,\n serverStampedKeys,\n });\n const deleteById = RouteConfigResolver.resolveDeleteByIdConfig({\n config: routesConfig.deleteById,\n selectSchema,\n idType,\n });\n const deleteBy = RouteConfigResolver.resolveDeleteByConfig({\n config: routesConfig.deleteBy,\n selectSchema,\n });\n\n const rs = {\n COUNT: {\n method: HTTP.Methods.GET,\n path: RestPaths.COUNT,\n description: 'Count records matching where condition',\n authenticate: resolveRouteAuth('count'),\n authorize: resolveRouteAuthorize('count'),\n request: count.request,\n responses: jsonResponse(count.response),\n },\n\n FIND: {\n method: HTTP.Methods.GET,\n path: RestPaths.ROOT,\n description: 'Find records with filter, pagination, sorting, and relations',\n authenticate: resolveRouteAuth('find'),\n authorize: resolveRouteAuthorize('find'),\n request: find.request,\n responses: jsonResponse(find.response),\n },\n\n FIND_BY_ID: {\n method: HTTP.Methods.GET,\n path: '/{id}',\n description: 'Find single record by ID',\n authenticate: resolveRouteAuth('findById'),\n authorize: resolveRouteAuthorize('findById'),\n request: findById.request,\n responses: jsonResponse(findById.response),\n },\n\n FIND_ONE: {\n method: HTTP.Methods.GET,\n path: RestPaths.FIND_ONE,\n description: 'Find first record matching filter',\n authenticate: resolveRouteAuth('findOne'),\n authorize: resolveRouteAuthorize('findOne'),\n request: findOne.request,\n responses: jsonResponse(findOne.response),\n },\n\n CREATE: {\n method: HTTP.Methods.POST,\n path: RestPaths.ROOT,\n description: 'Create new record',\n authenticate: resolveRouteAuth('create'),\n authorize: resolveRouteAuthorize('create'),\n request: {\n body: jsonContent({\n description: 'Record data (required fields must be provided)',\n schema: create.request.body,\n }),\n headers: create.request.headers,\n },\n responses: jsonResponse(create.response),\n },\n\n UPDATE_BY_ID: {\n method: HTTP.Methods.PATCH,\n path: '/{id}',\n description: 'Partial update record by ID',\n authenticate: resolveRouteAuth('updateById'),\n authorize: resolveRouteAuthorize('updateById'),\n request: {\n params: updateById.request.params,\n body: jsonContent({\n description: 'Partial data (only changed fields)',\n schema: updateById.request.body,\n }),\n headers: updateById.request.headers,\n },\n responses: jsonResponse(updateById.response),\n },\n\n UPDATE_BY: {\n method: HTTP.Methods.PATCH,\n path: RestPaths.ROOT,\n description: 'Bulk update records matching where condition',\n authenticate: resolveRouteAuth('updateBy'),\n authorize: resolveRouteAuthorize('updateBy'),\n request: {\n query: updateBy.request.query,\n body: jsonContent({\n description: 'Partial data to apply to all matches',\n schema: updateBy.request.body,\n }),\n headers: updateBy.request.headers,\n },\n responses: jsonResponse(updateBy.response),\n },\n\n DELETE_BY_ID: {\n method: HTTP.Methods.DELETE,\n path: '/{id}',\n description: 'Delete record by ID (irreversible)',\n authenticate: resolveRouteAuth('deleteById'),\n authorize: resolveRouteAuthorize('deleteById'),\n request: deleteById.request,\n responses: jsonResponse(deleteById.response),\n },\n\n DELETE_BY: {\n method: HTTP.Methods.DELETE,\n path: RestPaths.ROOT,\n description: 'Bulk delete records matching where condition (irreversible)',\n authenticate: resolveRouteAuth('deleteBy'),\n authorize: resolveRouteAuthorize('deleteBy'),\n request: {\n query: deleteBy.request.query,\n ...(deleteBy.request.body\n ? {\n body: jsonContent({\n description: 'Where condition, when it does not fit in the query',\n schema: deleteBy.request.body,\n required: false,\n }),\n }\n : {}),\n headers: deleteBy.request.headers,\n },\n responses: jsonResponse(deleteBy.response),\n },\n } as const;\n\n return rs;\n }\n}\n\nexport const conditionalCountResponse = RouteConfigResolver.conditionalCountResponse;\nexport const resolveCountConfig = RouteConfigResolver.resolveCountConfig;\nexport const resolveFindConfig = RouteConfigResolver.resolveFindConfig;\nexport const resolveFindByIdConfig = RouteConfigResolver.resolveFindByIdConfig;\nexport const resolveFindOneConfig = RouteConfigResolver.resolveFindOneConfig;\nexport const resolveCreateConfig = RouteConfigResolver.resolveCreateConfig;\nexport const defineControllerRouteConfigs = RouteConfigResolver.defineControllerRouteConfigs;\n"]}
@@ -28,9 +28,9 @@ class ResponseExtras {
28
28
  ? undefined
29
29
  : match[3]
30
30
  .split(',')
31
- .map(key => key.trim())
32
- .filter(key => key.length > 0);
33
- if (keys?.some(key => !IDENTIFIER.test(key))) {
31
+ .map((key) => key.trim())
32
+ .filter((key) => key.length > 0);
33
+ if (keys?.some((key) => !IDENTIFIER.test(key))) {
34
34
  throw ResponseExtras.badRequest({ message: `Malformed key in extra '${raw.trim()}'` });
35
35
  }
36
36
  entries.push({ name, isExcluded: match[1] === '-', keys });
@@ -80,7 +80,7 @@ class ResponseExtras {
80
80
  message: `Extra '${entry.name}' needs keys: ${definition.keys.join(', ')} | Name them as ${entry.name}(key,key)`,
81
81
  });
82
82
  }
83
- const unknown = entry.keys.filter(key => !definition.keys.includes(key));
83
+ const unknown = entry.keys.filter((key) => !definition.keys.includes(key));
84
84
  if (unknown.length > 0) {
85
85
  throw ResponseExtras.badRequest({
86
86
  message: `Unknown key for extra '${entry.name}': ${unknown.join(', ')} | It offers: ${definition.keys.join(', ')}`,
@@ -140,7 +140,7 @@ class ResponseExtras {
140
140
  current += character;
141
141
  }
142
142
  parts.push(current);
143
- return parts.filter(part => part.trim().length > 0);
143
+ return parts.filter((part) => part.trim().length > 0);
144
144
  }
145
145
  static badRequest(opts) {
146
146
  return (0, core_1.getError)({
@@ -1 +1 @@
1
- {"version":3,"file":"extras.js","sourceRoot":"","sources":["../../../../../src/base/controllers/rest/extras.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ValueOrPromise } from '@venizia/ignis-helpers/common';\nimport { HTTP } from '@venizia/ignis-helpers/common';\nimport { getError } from '@venizia/ignis-helpers/core';\n\n/**\n * A figure a list route offers beside its rows:\n * - a function runs when the client names it;\n * - `{ isDefault: true, compute }` always runs, unless the client switches it off with `-name`;\n * - `{ keys, compute }` is a group - the client names the keys it wants (`facets(status,tag)`), and\n * `compute` receives exactly those, so one aggregate pass serves them all.\n */\nexport type TResponseExtra =\n | (() => ValueOrPromise<unknown>)\n | { isDefault: boolean; compute: () => ValueOrPromise<unknown>; keys?: never }\n | {\n keys: ReadonlyArray<string>;\n compute: (opts: { keys: Array<string> }) => ValueOrPromise<unknown>;\n isDefault?: never;\n };\n\n/** One entry of `x-request-extra`: `name`, `-name` (a default switched off), `-*` (every default off) or `name(key,key)`. */\nexport interface IRequestedExtra {\n name: string;\n isExcluded: boolean;\n keys?: Array<string>;\n}\n\n/** A name or a key: letters, digits, `_`, `.` and `-` inside. Anything else is refused, never evaluated. */\nconst IDENTIFIER = /^[A-Za-z_][\\w.-]*$/;\nconst ENTRY = /^(-?)([^()\\s]+)(?:\\(([^()]*)\\))?$/;\n\n/** `-*`: every default off - for a read that wants the rows alone. */\nconst ALL_DEFAULTS = '*';\n\n/** Parses `x-request-extra` and resolves it against what a route offers. */\nexport class ResponseExtras {\n /** The entries of the header, in the order written. Malformed input is a 400 naming it. */\n static parse(opts: { header?: string | null }): Array<IRequestedExtra> {\n const header = opts.header?.trim() ?? '';\n if (header === '') {\n return [];\n }\n\n const entries: Array<IRequestedExtra> = [];\n for (const raw of ResponseExtras.splitTopLevel({ header })) {\n const match = raw.trim().match(ENTRY);\n const name = match?.[2];\n\n const isAllDefaultsOff =\n match?.[1] === '-' && name === ALL_DEFAULTS && match[3] === undefined;\n if (!match || !name || (!isAllDefaultsOff && !IDENTIFIER.test(name))) {\n throw ResponseExtras.badRequest({ message: `Malformed extra '${raw.trim()}'` });\n }\n\n const keys =\n match[3] === undefined\n ? undefined\n : match[3]\n .split(',')\n .map(key => key.trim())\n .filter(key => key.length > 0);\n\n if (keys?.some(key => !IDENTIFIER.test(key))) {\n throw ResponseExtras.badRequest({ message: `Malformed key in extra '${raw.trim()}'` });\n }\n\n entries.push({ name, isExcluded: match[1] === '-', keys });\n }\n\n return entries;\n }\n\n /**\n * What to compute: the asked-for extras and the defaults, minus the ones switched off - each with the\n * keys asked for, de-duplicated in the order asked. Every name and key is checked against `offered`.\n */\n static resolve(opts: {\n requested: Array<IRequestedExtra>;\n offered: Record<string, TResponseExtra>;\n }): Map<string, Array<string> | undefined> {\n const { requested, offered } = opts;\n const offeredNames = Object.keys(offered).join(', ') || 'none';\n const plan = new Map<string, Array<string> | undefined>();\n const excluded = new Set<string>();\n\n let isEveryDefaultOff = false;\n\n for (const entry of requested) {\n if (entry.isExcluded && entry.name === ALL_DEFAULTS) {\n isEveryDefaultOff = true;\n continue;\n }\n\n if (!Object.hasOwn(offered, entry.name)) {\n throw ResponseExtras.badRequest({\n message: `Unknown extra requested: ${entry.name} | This route offers: ${offeredNames}`,\n });\n }\n\n if (entry.isExcluded) {\n if (entry.keys !== undefined) {\n throw ResponseExtras.badRequest({\n message: `Switching '${entry.name}' off takes no keys`,\n });\n }\n\n excluded.add(entry.name);\n continue;\n }\n\n const definition = offered[entry.name];\n const isGroup = typeof definition !== 'function' && definition.keys !== undefined;\n\n if (!isGroup) {\n if (entry.keys !== undefined) {\n throw ResponseExtras.badRequest({ message: `Extra '${entry.name}' takes no keys` });\n }\n\n plan.set(entry.name, undefined);\n continue;\n }\n\n if (!entry.keys?.length) {\n throw ResponseExtras.badRequest({\n message: `Extra '${entry.name}' needs keys: ${definition.keys.join(', ')} | Name them as ${entry.name}(key,key)`,\n });\n }\n\n const unknown = entry.keys.filter(key => !definition.keys.includes(key));\n if (unknown.length > 0) {\n throw ResponseExtras.badRequest({\n message: `Unknown key for extra '${entry.name}': ${unknown.join(', ')} | It offers: ${definition.keys.join(', ')}`,\n });\n }\n\n plan.set(entry.name, [...new Set([...(plan.get(entry.name) ?? []), ...entry.keys])]);\n }\n\n for (const [name, definition] of Object.entries(offered)) {\n // A group needs keys, so it never runs unasked, whatever its declaration claims.\n const isDefault =\n typeof definition !== 'function' &&\n definition.keys === undefined &&\n definition.isDefault === true;\n if (isDefault && !isEveryDefaultOff && !plan.has(name)) {\n plan.set(name, undefined);\n }\n }\n\n for (const name of excluded) {\n plan.delete(name);\n }\n\n return plan;\n }\n\n /** Runs the plan in parallel; each value under its name. */\n static async compute(opts: {\n plan: Map<string, Array<string> | undefined>;\n offered: Record<string, TResponseExtra>;\n }): Promise<Record<string, unknown>> {\n const { plan, offered } = opts;\n const names = [...plan.keys()];\n\n // Async, so an extra that throws synchronously becomes a rejection Promise.all owns, never an\n // unhandled one left behind by a sibling already running.\n const values = await Promise.all(\n names.map(async name => {\n const definition = offered[name];\n\n if (typeof definition === 'function') {\n return definition();\n }\n\n if (definition.keys !== undefined) {\n return definition.compute({ keys: plan.get(name) ?? [] });\n }\n\n return definition.compute();\n }),\n );\n\n return Object.fromEntries(names.map((name, index) => [name, values[index]]));\n }\n\n /** Commas inside `( )` belong to the keys, not to the list of extras. */\n private static splitTopLevel(opts: { header: string }): Array<string> {\n const parts: Array<string> = [];\n let depth = 0;\n let current = '';\n\n for (const character of opts.header) {\n if (character === '(') {\n depth++;\n } else if (character === ')') {\n depth--;\n }\n\n if (character === ',' && depth === 0) {\n parts.push(current);\n current = '';\n continue;\n }\n\n current += character;\n }\n\n parts.push(current);\n return parts.filter(part => part.trim().length > 0);\n }\n\n private static badRequest(opts: { message: string }) {\n return getError({\n statusCode: HTTP.ResultCodes.RS_4.BadRequest,\n message: `[x-request-extra] ${opts.message}`,\n });\n }\n}\n"]}
1
+ {"version":3,"file":"extras.js","sourceRoot":"","sources":["../../../../../src/base/controllers/rest/extras.ts"],"names":[],"mappings":"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","sourcesContent":["import type { ValueOrPromise } from '@venizia/ignis-helpers/common';\nimport { HTTP } from '@venizia/ignis-helpers/common';\nimport { getError } from '@venizia/ignis-helpers/core';\n\n/**\n * A figure a list route offers beside its rows:\n * - a function runs when the client names it;\n * - `{ isDefault: true, compute }` always runs, unless the client switches it off with `-name`;\n * - `{ keys, compute }` is a group - the client names the keys it wants (`facets(status,tag)`), and\n * `compute` receives exactly those, so one aggregate pass serves them all.\n */\nexport type TResponseExtra =\n | (() => ValueOrPromise<unknown>)\n | { isDefault: boolean; compute: () => ValueOrPromise<unknown>; keys?: never }\n | {\n keys: ReadonlyArray<string>;\n compute: (opts: { keys: Array<string> }) => ValueOrPromise<unknown>;\n isDefault?: never;\n };\n\n/** One entry of `x-request-extra`: `name`, `-name` (a default switched off), `-*` (every default off) or `name(key,key)`. */\nexport interface IRequestedExtra {\n name: string;\n isExcluded: boolean;\n keys?: Array<string>;\n}\n\n/** A name or a key: letters, digits, `_`, `.` and `-` inside. Anything else is refused, never evaluated. */\nconst IDENTIFIER = /^[A-Za-z_][\\w.-]*$/;\nconst ENTRY = /^(-?)([^()\\s]+)(?:\\(([^()]*)\\))?$/;\n\n/** `-*`: every default off - for a read that wants the rows alone. */\nconst ALL_DEFAULTS = '*';\n\n/** Parses `x-request-extra` and resolves it against what a route offers. */\nexport class ResponseExtras {\n /** The entries of the header, in the order written. Malformed input is a 400 naming it. */\n static parse(opts: { header?: string | null }): Array<IRequestedExtra> {\n const header = opts.header?.trim() ?? '';\n if (header === '') {\n return [];\n }\n\n const entries: Array<IRequestedExtra> = [];\n for (const raw of ResponseExtras.splitTopLevel({ header })) {\n const match = raw.trim().match(ENTRY);\n const name = match?.[2];\n\n const isAllDefaultsOff =\n match?.[1] === '-' && name === ALL_DEFAULTS && match[3] === undefined;\n if (!match || !name || (!isAllDefaultsOff && !IDENTIFIER.test(name))) {\n throw ResponseExtras.badRequest({ message: `Malformed extra '${raw.trim()}'` });\n }\n\n const keys =\n match[3] === undefined\n ? undefined\n : match[3]\n .split(',')\n .map((key) => key.trim())\n .filter((key) => key.length > 0);\n\n if (keys?.some((key) => !IDENTIFIER.test(key))) {\n throw ResponseExtras.badRequest({ message: `Malformed key in extra '${raw.trim()}'` });\n }\n\n entries.push({ name, isExcluded: match[1] === '-', keys });\n }\n\n return entries;\n }\n\n /**\n * What to compute: the asked-for extras and the defaults, minus the ones switched off - each with the\n * keys asked for, de-duplicated in the order asked. Every name and key is checked against `offered`.\n */\n static resolve(opts: {\n requested: Array<IRequestedExtra>;\n offered: Record<string, TResponseExtra>;\n }): Map<string, Array<string> | undefined> {\n const { requested, offered } = opts;\n const offeredNames = Object.keys(offered).join(', ') || 'none';\n const plan = new Map<string, Array<string> | undefined>();\n const excluded = new Set<string>();\n\n let isEveryDefaultOff = false;\n\n for (const entry of requested) {\n if (entry.isExcluded && entry.name === ALL_DEFAULTS) {\n isEveryDefaultOff = true;\n continue;\n }\n\n if (!Object.hasOwn(offered, entry.name)) {\n throw ResponseExtras.badRequest({\n message: `Unknown extra requested: ${entry.name} | This route offers: ${offeredNames}`,\n });\n }\n\n if (entry.isExcluded) {\n if (entry.keys !== undefined) {\n throw ResponseExtras.badRequest({\n message: `Switching '${entry.name}' off takes no keys`,\n });\n }\n\n excluded.add(entry.name);\n continue;\n }\n\n const definition = offered[entry.name];\n const isGroup = typeof definition !== 'function' && definition.keys !== undefined;\n\n if (!isGroup) {\n if (entry.keys !== undefined) {\n throw ResponseExtras.badRequest({ message: `Extra '${entry.name}' takes no keys` });\n }\n\n plan.set(entry.name, undefined);\n continue;\n }\n\n if (!entry.keys?.length) {\n throw ResponseExtras.badRequest({\n message: `Extra '${entry.name}' needs keys: ${definition.keys.join(', ')} | Name them as ${entry.name}(key,key)`,\n });\n }\n\n const unknown = entry.keys.filter((key) => !definition.keys.includes(key));\n if (unknown.length > 0) {\n throw ResponseExtras.badRequest({\n message: `Unknown key for extra '${entry.name}': ${unknown.join(', ')} | It offers: ${definition.keys.join(', ')}`,\n });\n }\n\n plan.set(entry.name, [...new Set([...(plan.get(entry.name) ?? []), ...entry.keys])]);\n }\n\n for (const [name, definition] of Object.entries(offered)) {\n // A group needs keys, so it never runs unasked, whatever its declaration claims.\n const isDefault =\n typeof definition !== 'function' &&\n definition.keys === undefined &&\n definition.isDefault === true;\n if (isDefault && !isEveryDefaultOff && !plan.has(name)) {\n plan.set(name, undefined);\n }\n }\n\n for (const name of excluded) {\n plan.delete(name);\n }\n\n return plan;\n }\n\n /** Runs the plan in parallel; each value under its name. */\n static async compute(opts: {\n plan: Map<string, Array<string> | undefined>;\n offered: Record<string, TResponseExtra>;\n }): Promise<Record<string, unknown>> {\n const { plan, offered } = opts;\n const names = [...plan.keys()];\n\n // Async, so an extra that throws synchronously becomes a rejection Promise.all owns, never an\n // unhandled one left behind by a sibling already running.\n const values = await Promise.all(\n names.map(async (name) => {\n const definition = offered[name];\n\n if (typeof definition === 'function') {\n return definition();\n }\n\n if (definition.keys !== undefined) {\n return definition.compute({ keys: plan.get(name) ?? [] });\n }\n\n return definition.compute();\n }),\n );\n\n return Object.fromEntries(names.map((name, index) => [name, values[index]]));\n }\n\n /** Commas inside `( )` belong to the keys, not to the list of extras. */\n private static splitTopLevel(opts: { header: string }): Array<string> {\n const parts: Array<string> = [];\n let depth = 0;\n let current = '';\n\n for (const character of opts.header) {\n if (character === '(') {\n depth++;\n } else if (character === ')') {\n depth--;\n }\n\n if (character === ',' && depth === 0) {\n parts.push(current);\n current = '';\n continue;\n }\n\n current += character;\n }\n\n parts.push(current);\n return parts.filter((part) => part.trim().length > 0);\n }\n\n private static badRequest(opts: { message: string }) {\n return getError({\n statusCode: HTTP.ResultCodes.RS_4.BadRequest,\n message: `[x-request-extra] ${opts.message}`,\n });\n }\n}\n"]}
@@ -7,7 +7,7 @@ const artifact_keys_1 = require("./artifact-keys");
7
7
  const core_1 = require("@venizia/ignis-helpers/core");
8
8
  /** The root stereotype: marks a class as an artifact the application registers, with its registration defaults. Every other stereotype calls it. */
9
9
  const injectable = (opts) => {
10
- return target => {
10
+ return (target) => {
11
11
  if (!inversion_1.ArtifactTypes.isValid(opts.type)) {
12
12
  throw (0, core_1.getError)({
13
13
  message: `[injectable][${target.name}] Invalid artifact type: '${opts.type}' | Expected one of: ${[...inversion_1.ArtifactTypes.SCHEME_SET].join(', ')}`,
@@ -1 +1 @@
1
- {"version":3,"file":"injectable.js","sourceRoot":"","sources":["../../../../src/base/metadata/injectable.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n IArtifactMetadata,\n IArtifactRegistrationOptions,\n TBindingScope,\n} from '@/helpers/inversion';\nimport { ArtifactNamespaces, BindingNamespaces } from '@/common/bindings';\nimport { ArtifactTypes, MetadataRegistry } from '@/helpers/inversion';\nimport { ArtifactBindingKeys } from './artifact-keys';\nimport { getError } from '@venizia/ignis-helpers/core';\n\n/** The root stereotype: marks a class as an artifact the application registers, with its registration defaults. Every other stereotype calls it. */\nexport const injectable = <ApplicationType = unknown>(\n opts: IArtifactMetadata<ApplicationType>,\n): ClassDecorator => {\n return target => {\n if (!ArtifactTypes.isValid(opts.type)) {\n throw getError({\n message: `[injectable][${target.name}] Invalid artifact type: '${opts.type}' | Expected one of: ${[...ArtifactTypes.SCHEME_SET].join(', ')}`,\n });\n }\n\n // At import time, so the failure lands where the binding is written, not at boot.\n if (opts.binding) {\n BindingNamespaces.assertArtifactNamespace({\n namespace: opts.binding.namespace,\n artifact: target.name,\n caller: 'injectable',\n });\n }\n\n const registry = MetadataRegistry.getInstance();\n registry.setArtifactMetadata({ target, metadata: opts });\n\n // Discovery happens HERE, at import time. A boot-time filesystem scan cannot see a compiled\n // single-file binary, and a class exists at run time only because something imported it.\n registry.addDiscoveredArtifact({ target });\n\n // The key this class WOULD get; `registerArtifact` overwrites it with the one actually bound.\n registry.setBindingKey({\n target,\n key: ArtifactBindingKeys.resolve({\n target,\n namespace: ArtifactNamespaces.resolve({ type: opts.type }),\n binding: opts.binding,\n }).key,\n isProvisional: true,\n });\n };\n};\n\nexport const service = <ApplicationType = unknown>(\n opts?: IArtifactRegistrationOptions<ApplicationType>,\n): ClassDecorator => {\n return injectable<ApplicationType>({ type: ArtifactTypes.SERVICE, ...opts });\n};\n\nexport const component = <ApplicationType = unknown>(\n opts?: IArtifactRegistrationOptions<ApplicationType>,\n): ClassDecorator => {\n return injectable<ApplicationType>({ type: ArtifactTypes.COMPONENT, ...opts });\n};\n\nexport const configuration = <ApplicationType = unknown>(\n opts?: IArtifactRegistrationOptions<ApplicationType>,\n): ClassDecorator => {\n return injectable<ApplicationType>({ type: ArtifactTypes.CONFIGURATION, ...opts });\n};\n/** Marks a component method as the provider of `key`. `registerArtifacts` binds the key to a lazy provider that resolves the component and calls the method; SINGLETON unless `scope` says otherwise. */\nexport const provide = (opts: { key: string; scope?: TBindingScope }): MethodDecorator => {\n return (target, propertyKey) => {\n MetadataRegistry.getInstance().addProvideMetadata({\n target: target.constructor,\n metadata: {\n methodName: propertyKey,\n key: opts.key,\n ...(opts.scope ? { scope: opts.scope } : {}),\n },\n });\n };\n};\n\n/** The registration defaults a stereotype forwards to `@injectable`, copied field by field so an absent option stays absent. */\nexport const pickRegistrationOptions = <ApplicationType = unknown>(opts: {\n metadata: IArtifactRegistrationOptions<ApplicationType>;\n}): IArtifactRegistrationOptions<ApplicationType> => {\n const { binding, allowOverride, scope, order, when, after } = opts.metadata;\n const registration: IArtifactRegistrationOptions<ApplicationType> = {};\n\n if (binding !== undefined) {\n registration.binding = binding;\n }\n\n if (allowOverride !== undefined) {\n registration.allowOverride = allowOverride;\n }\n\n if (scope !== undefined) {\n registration.scope = scope;\n }\n\n if (order !== undefined) {\n registration.order = order;\n }\n\n if (when !== undefined) {\n registration.when = when;\n }\n\n if (after !== undefined) {\n registration.after = after;\n }\n\n return registration;\n};\n"]}
1
+ {"version":3,"file":"injectable.js","sourceRoot":"","sources":["../../../../src/base/metadata/injectable.ts"],"names":[],"mappings":"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","sourcesContent":["import type {\n IArtifactMetadata,\n IArtifactRegistrationOptions,\n TBindingScope,\n} from '@/helpers/inversion';\nimport { ArtifactNamespaces, BindingNamespaces } from '@/common/bindings';\nimport { ArtifactTypes, MetadataRegistry } from '@/helpers/inversion';\nimport { ArtifactBindingKeys } from './artifact-keys';\nimport { getError } from '@venizia/ignis-helpers/core';\n\n/** The root stereotype: marks a class as an artifact the application registers, with its registration defaults. Every other stereotype calls it. */\nexport const injectable = <ApplicationType = unknown>(\n opts: IArtifactMetadata<ApplicationType>,\n): ClassDecorator => {\n return (target) => {\n if (!ArtifactTypes.isValid(opts.type)) {\n throw getError({\n message: `[injectable][${target.name}] Invalid artifact type: '${opts.type}' | Expected one of: ${[...ArtifactTypes.SCHEME_SET].join(', ')}`,\n });\n }\n\n // At import time, so the failure lands where the binding is written, not at boot.\n if (opts.binding) {\n BindingNamespaces.assertArtifactNamespace({\n namespace: opts.binding.namespace,\n artifact: target.name,\n caller: 'injectable',\n });\n }\n\n const registry = MetadataRegistry.getInstance();\n registry.setArtifactMetadata({ target, metadata: opts });\n\n // Discovery happens HERE, at import time. A boot-time filesystem scan cannot see a compiled\n // single-file binary, and a class exists at run time only because something imported it.\n registry.addDiscoveredArtifact({ target });\n\n // The key this class WOULD get; `registerArtifact` overwrites it with the one actually bound.\n registry.setBindingKey({\n target,\n key: ArtifactBindingKeys.resolve({\n target,\n namespace: ArtifactNamespaces.resolve({ type: opts.type }),\n binding: opts.binding,\n }).key,\n isProvisional: true,\n });\n };\n};\n\nexport const service = <ApplicationType = unknown>(\n opts?: IArtifactRegistrationOptions<ApplicationType>,\n): ClassDecorator => {\n return injectable<ApplicationType>({ type: ArtifactTypes.SERVICE, ...opts });\n};\n\nexport const component = <ApplicationType = unknown>(\n opts?: IArtifactRegistrationOptions<ApplicationType>,\n): ClassDecorator => {\n return injectable<ApplicationType>({ type: ArtifactTypes.COMPONENT, ...opts });\n};\n\nexport const configuration = <ApplicationType = unknown>(\n opts?: IArtifactRegistrationOptions<ApplicationType>,\n): ClassDecorator => {\n return injectable<ApplicationType>({ type: ArtifactTypes.CONFIGURATION, ...opts });\n};\n/** Marks a component method as the provider of `key`. `registerArtifacts` binds the key to a lazy provider that resolves the component and calls the method; SINGLETON unless `scope` says otherwise. */\nexport const provide = (opts: { key: string; scope?: TBindingScope }): MethodDecorator => {\n return (target, propertyKey) => {\n MetadataRegistry.getInstance().addProvideMetadata({\n target: target.constructor,\n metadata: {\n methodName: propertyKey,\n key: opts.key,\n ...(opts.scope ? { scope: opts.scope } : {}),\n },\n });\n };\n};\n\n/** The registration defaults a stereotype forwards to `@injectable`, copied field by field so an absent option stays absent. */\nexport const pickRegistrationOptions = <ApplicationType = unknown>(opts: {\n metadata: IArtifactRegistrationOptions<ApplicationType>;\n}): IArtifactRegistrationOptions<ApplicationType> => {\n const { binding, allowOverride, scope, order, when, after } = opts.metadata;\n const registration: IArtifactRegistrationOptions<ApplicationType> = {};\n\n if (binding !== undefined) {\n registration.binding = binding;\n }\n\n if (allowOverride !== undefined) {\n registration.allowOverride = allowOverride;\n }\n\n if (scope !== undefined) {\n registration.scope = scope;\n }\n\n if (order !== undefined) {\n registration.order = order;\n }\n\n if (when !== undefined) {\n registration.when = when;\n }\n\n if (after !== undefined) {\n registration.after = after;\n }\n\n return registration;\n};\n"]}
@@ -0,0 +1,21 @@
1
+ import type { IDeprecatedModelSetting, IModelSettings } from '../../helpers/inversion';
2
+ /** The release that drops the deprecated keys. */
3
+ export declare const DEPRECATED_MODEL_SETTINGS_REMOVED_IN = "0.4.3";
4
+ /**
5
+ * The one place the old flat settings become the new grouped ones. Everything that reads model
6
+ * settings reads the result, so no reader knows two shapes.
7
+ *
8
+ * - `defaultFilter` -> `query.filter`; `defaultLimit` -> `query.limit.default`; `maxLimit` ->
9
+ * `query.limit.max`; `scopeFilter` -> `access` (`writeGuard` -> `access.write.mode`, `sharedRows`
10
+ * -> `access.write.sharedRows`).
11
+ * - An old key together with the key that replaces it is an error.
12
+ * - Returns the old keys in use so the application can warn once at boot.
13
+ */
14
+ export declare const normalizeModelSettings: (opts: {
15
+ model: string;
16
+ settings: IModelSettings | undefined;
17
+ }) => {
18
+ settings: IModelSettings | undefined;
19
+ deprecated: IDeprecatedModelSetting[];
20
+ };
21
+ //# sourceMappingURL=model-settings.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"model-settings.d.ts","sourceRoot":"","sources":["../../../../src/base/metadata/model-settings.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EACV,uBAAuB,EAEvB,cAAc,EACf,MAAM,qBAAqB,CAAC;AAE7B,kDAAkD;AAClD,eAAO,MAAM,oCAAoC,UAAU,CAAC;AAQ5D;;;;;;;;;GASG;AACH,eAAO,MAAM,sBAAsB,GAAI,MAAM;IAC3C,KAAK,EAAE,MAAM,CAAC;IACd,QAAQ,EAAE,cAAc,GAAG,SAAS,CAAC;CACtC,KAAG;IAAE,QAAQ,EAAE,cAAc,GAAG,SAAS,CAAC;IAAC,UAAU,EAAE,uBAAuB,EAAE,CAAA;CAmEhF,CAAC"}
@@ -0,0 +1,77 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.normalizeModelSettings = exports.DEPRECATED_MODEL_SETTINGS_REMOVED_IN = void 0;
4
+ const core_1 = require("@venizia/ignis-helpers/core");
5
+ /** The release that drops the deprecated keys. */
6
+ exports.DEPRECATED_MODEL_SETTINGS_REMOVED_IN = '0.4.3';
7
+ const conflict = (opts) => {
8
+ return (0, core_1.getError)({
9
+ message: `[model][${opts.model}] settings.${opts.old} and settings.${opts.use} are both set | ${opts.old} is the deprecated name of ${opts.use} | keep ${opts.use} and remove ${opts.old}`,
10
+ });
11
+ };
12
+ /**
13
+ * The one place the old flat settings become the new grouped ones. Everything that reads model
14
+ * settings reads the result, so no reader knows two shapes.
15
+ *
16
+ * - `defaultFilter` -> `query.filter`; `defaultLimit` -> `query.limit.default`; `maxLimit` ->
17
+ * `query.limit.max`; `scopeFilter` -> `access` (`writeGuard` -> `access.write.mode`, `sharedRows`
18
+ * -> `access.write.sharedRows`).
19
+ * - An old key together with the key that replaces it is an error.
20
+ * - Returns the old keys in use so the application can warn once at boot.
21
+ */
22
+ const normalizeModelSettings = (opts) => {
23
+ const { model, settings } = opts;
24
+ if (!settings) {
25
+ return { settings, deprecated: [] };
26
+ }
27
+ const { defaultFilter, defaultLimit, maxLimit, scopeFilter, ...current } = settings;
28
+ const deprecated = [];
29
+ const normalized = { ...current };
30
+ if (defaultFilter !== undefined) {
31
+ if (current.query?.filter !== undefined) {
32
+ throw conflict({ model, old: 'defaultFilter', use: 'query.filter' });
33
+ }
34
+ normalized.query = { ...normalized.query, filter: defaultFilter };
35
+ deprecated.push({ key: 'defaultFilter', use: 'query.filter' });
36
+ }
37
+ if (defaultLimit !== undefined) {
38
+ if (current.query?.limit?.default !== undefined) {
39
+ throw conflict({ model, old: 'defaultLimit', use: 'query.limit.default' });
40
+ }
41
+ normalized.query = {
42
+ ...normalized.query,
43
+ limit: { ...normalized.query?.limit, default: defaultLimit },
44
+ };
45
+ deprecated.push({ key: 'defaultLimit', use: 'query.limit.default' });
46
+ }
47
+ if (maxLimit !== undefined) {
48
+ if (current.query?.limit?.max !== undefined) {
49
+ throw conflict({ model, old: 'maxLimit', use: 'query.limit.max' });
50
+ }
51
+ normalized.query = {
52
+ ...normalized.query,
53
+ limit: { ...normalized.query?.limit, max: maxLimit },
54
+ };
55
+ deprecated.push({ key: 'maxLimit', use: 'query.limit.max' });
56
+ }
57
+ if (scopeFilter !== undefined) {
58
+ if (current.access !== undefined) {
59
+ throw conflict({ model, old: 'scopeFilter', use: 'access' });
60
+ }
61
+ const { writeGuard, sharedRows, ...rest } = scopeFilter;
62
+ const access = { ...rest };
63
+ deprecated.push({ key: 'scopeFilter', use: 'access' });
64
+ if (writeGuard !== undefined) {
65
+ access.write = { ...access.write, mode: writeGuard };
66
+ deprecated.push({ key: 'scopeFilter.writeGuard', use: 'access.write.mode' });
67
+ }
68
+ if (sharedRows !== undefined) {
69
+ access.write = { ...access.write, sharedRows };
70
+ deprecated.push({ key: 'scopeFilter.sharedRows', use: 'access.write.sharedRows' });
71
+ }
72
+ normalized.access = access;
73
+ }
74
+ return { settings: normalized, deprecated };
75
+ };
76
+ exports.normalizeModelSettings = normalizeModelSettings;
77
+ //# sourceMappingURL=model-settings.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"model-settings.js","sourceRoot":"","sources":["../../../../src/base/metadata/model-settings.ts"],"names":[],"mappings":"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","sourcesContent":["import { getError } from '@venizia/ignis-helpers/core';\nimport type {\n IDeprecatedModelSetting,\n IModelAccessSettings,\n IModelSettings,\n} from '@/helpers/inversion';\n\n/** The release that drops the deprecated keys. */\nexport const DEPRECATED_MODEL_SETTINGS_REMOVED_IN = '0.4.3';\n\nconst conflict = (opts: { model: string; old: string; use: string }) => {\n return getError({\n message: `[model][${opts.model}] settings.${opts.old} and settings.${opts.use} are both set | ${opts.old} is the deprecated name of ${opts.use} | keep ${opts.use} and remove ${opts.old}`,\n });\n};\n\n/**\n * The one place the old flat settings become the new grouped ones. Everything that reads model\n * settings reads the result, so no reader knows two shapes.\n *\n * - `defaultFilter` -> `query.filter`; `defaultLimit` -> `query.limit.default`; `maxLimit` ->\n * `query.limit.max`; `scopeFilter` -> `access` (`writeGuard` -> `access.write.mode`, `sharedRows`\n * -> `access.write.sharedRows`).\n * - An old key together with the key that replaces it is an error.\n * - Returns the old keys in use so the application can warn once at boot.\n */\nexport const normalizeModelSettings = (opts: {\n model: string;\n settings: IModelSettings | undefined;\n}): { settings: IModelSettings | undefined; deprecated: IDeprecatedModelSetting[] } => {\n const { model, settings } = opts;\n\n if (!settings) {\n return { settings, deprecated: [] };\n }\n\n const { defaultFilter, defaultLimit, maxLimit, scopeFilter, ...current } = settings;\n const deprecated: IDeprecatedModelSetting[] = [];\n const normalized: IModelSettings = { ...current };\n\n if (defaultFilter !== undefined) {\n if (current.query?.filter !== undefined) {\n throw conflict({ model, old: 'defaultFilter', use: 'query.filter' });\n }\n\n normalized.query = { ...normalized.query, filter: defaultFilter };\n deprecated.push({ key: 'defaultFilter', use: 'query.filter' });\n }\n\n if (defaultLimit !== undefined) {\n if (current.query?.limit?.default !== undefined) {\n throw conflict({ model, old: 'defaultLimit', use: 'query.limit.default' });\n }\n\n normalized.query = {\n ...normalized.query,\n limit: { ...normalized.query?.limit, default: defaultLimit },\n };\n deprecated.push({ key: 'defaultLimit', use: 'query.limit.default' });\n }\n\n if (maxLimit !== undefined) {\n if (current.query?.limit?.max !== undefined) {\n throw conflict({ model, old: 'maxLimit', use: 'query.limit.max' });\n }\n\n normalized.query = {\n ...normalized.query,\n limit: { ...normalized.query?.limit, max: maxLimit },\n };\n deprecated.push({ key: 'maxLimit', use: 'query.limit.max' });\n }\n\n if (scopeFilter !== undefined) {\n if (current.access !== undefined) {\n throw conflict({ model, old: 'scopeFilter', use: 'access' });\n }\n\n const { writeGuard, sharedRows, ...rest } = scopeFilter;\n const access: IModelAccessSettings = { ...rest };\n deprecated.push({ key: 'scopeFilter', use: 'access' });\n\n if (writeGuard !== undefined) {\n access.write = { ...access.write, mode: writeGuard };\n deprecated.push({ key: 'scopeFilter.writeGuard', use: 'access.write.mode' });\n }\n\n if (sharedRows !== undefined) {\n access.write = { ...access.write, sharedRows };\n deprecated.push({ key: 'scopeFilter.sharedRows', use: 'access.write.sharedRows' });\n }\n\n normalized.access = access;\n }\n\n return { settings: normalized, deprecated };\n};\n"]}
@@ -2,7 +2,7 @@ import type { IDataSourceMetadata, IModelMetadata, TRepositoryMetadata } from '.
2
2
  import type { IDataSource } from '../datasources';
3
3
  import type { AbstractEntity } from '../models';
4
4
  /** Registers a model class with its static schema and relations. */
5
- export declare const model: (metadata: IModelMetadata) => ClassDecorator;
5
+ export declare const model: (input: IModelMetadata) => ClassDecorator;
6
6
  /** Registers a datasource with driver and auto-discovery settings. */
7
7
  export declare const datasource: (metadata?: IDataSourceMetadata) => ClassDecorator;
8
8
  export declare const repository: <Model extends AbstractEntity = AbstractEntity, DataSource extends IDataSource = IDataSource>(metadata?: TRepositoryMetadata<Model, DataSource>) => ClassDecorator;
@@ -1 +1 @@
1
- {"version":3,"file":"persistents.d.ts","sourceRoot":"","sources":["../../../../src/base/metadata/persistents.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEV,mBAAmB,EAEnB,cAAc,EAEd,mBAAmB,EACpB,MAAM,qBAAqB,CAAC;AAU7B,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAElD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAIhD,oEAAoE;AACpE,eAAO,MAAM,KAAK,GAAI,UAAU,cAAc,KAAG,cA4BhD,CAAC;AAEF,sEAAsE;AACtE,eAAO,MAAM,UAAU,GAAI,WAAW,mBAAmB,KAAG,cAQ3D,CAAC;AA0PF,eAAO,MAAM,UAAU,GACrB,KAAK,SAAS,cAAc,GAAG,cAAc,EAC7C,UAAU,SAAS,WAAW,GAAG,WAAW,EAE5C,WAAW,mBAAmB,CAAC,KAAK,EAAE,UAAU,CAAC,KAChD,cAeF,CAAC"}
1
+ {"version":3,"file":"persistents.d.ts","sourceRoot":"","sources":["../../../../src/base/metadata/persistents.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAEV,mBAAmB,EAEnB,cAAc,EAEd,mBAAmB,EACpB,MAAM,qBAAqB,CAAC;AAU7B,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,gBAAgB,CAAC;AAElD,OAAO,KAAK,EAAE,cAAc,EAAE,MAAM,WAAW,CAAC;AAKhD,oEAAoE;AACpE,eAAO,MAAM,KAAK,GAAI,OAAO,cAAc,KAAG,cA0C7C,CAAC;AAEF,sEAAsE;AACtE,eAAO,MAAM,UAAU,GAAI,WAAW,mBAAmB,KAAG,cAQ3D,CAAC;AA0PF,eAAO,MAAM,UAAU,GACrB,KAAK,SAAS,cAAc,GAAG,cAAc,EAC7C,UAAU,SAAS,WAAW,GAAG,WAAW,EAE5C,WAAW,mBAAmB,CAAC,KAAK,EAAE,UAAU,CAAC,KAChD,cAeF,CAAC"}
@@ -8,26 +8,38 @@ const core_1 = require("@venizia/ignis-helpers/core");
8
8
  const datasources_1 = require("../datasources");
9
9
  const constants_1 = require("../repositories/common/constants");
10
10
  const injectable_1 = require("./injectable");
11
+ const model_settings_1 = require("./model-settings");
11
12
  /** Registers a model class with its static schema and relations. */
12
- const model = (metadata) => {
13
- return target => {
14
- (0, injectable_1.injectable)({ type: inversion_1.ArtifactTypes.MODEL, ...(0, injectable_1.pickRegistrationOptions)({ metadata }) })(target);
15
- const defaultLimit = metadata.settings?.defaultLimit;
13
+ const model = (input) => {
14
+ return (target) => {
15
+ (0, injectable_1.injectable)({ type: inversion_1.ArtifactTypes.MODEL, ...(0, injectable_1.pickRegistrationOptions)({ metadata: input }) })(target);
16
+ // The one place the deprecated flat keys become the grouped ones; the registry, and so every
17
+ // reader, only ever sees the grouped shape.
18
+ const { settings, deprecated } = (0, model_settings_1.normalizeModelSettings)({
19
+ model: target.name,
20
+ settings: input.settings,
21
+ });
22
+ const metadata = {
23
+ ...input,
24
+ settings,
25
+ ...(deprecated.length > 0 ? { deprecatedSettings: deprecated } : {}),
26
+ };
27
+ const defaultLimit = settings?.query?.limit?.default;
16
28
  if (defaultLimit !== undefined && (!Number.isInteger(defaultLimit) || defaultLimit <= 0)) {
17
29
  throw (0, core_1.getError)({
18
- message: `[model][${target.name}] Invalid 'defaultLimit' | Expected a positive integer | Got: ${defaultLimit}`,
30
+ message: `[model][${target.name}] Invalid 'query.limit.default' | Expected a positive integer | Got: ${defaultLimit}`,
19
31
  });
20
32
  }
21
- // Validated at DECORATION time, like defaultLimit: a bad ceiling is a wiring mistake, and
33
+ // Validated at DECORATION time, like the default limit: a bad ceiling is a wiring mistake, and
22
34
  // catching it at boot beats catching it on the one request that happens to reach the limit.
23
- const maxLimit = metadata.settings?.maxLimit;
35
+ const maxLimit = settings?.query?.limit?.max;
24
36
  if (maxLimit !== undefined && (!Number.isInteger(maxLimit) || maxLimit <= 0)) {
25
37
  throw (0, core_1.getError)({
26
- message: `[model][${target.name}] Invalid 'maxLimit' | Expected a positive integer | Got: ${maxLimit}`,
38
+ message: `[model][${target.name}] Invalid 'query.limit.max' | Expected a positive integer | Got: ${maxLimit}`,
27
39
  });
28
40
  }
29
41
  // Auto-populate AUTHORIZATION_SUBJECT from authorize.principal if not already set
30
- const principal = metadata.settings?.authorize?.principal;
42
+ const principal = settings?.authorize?.principal;
31
43
  if (principal && !Object.hasOwn(target, 'AUTHORIZATION_SUBJECT')) {
32
44
  target.AUTHORIZATION_SUBJECT = principal;
33
45
  }
@@ -37,7 +49,7 @@ const model = (metadata) => {
37
49
  exports.model = model;
38
50
  /** Registers a datasource with driver and auto-discovery settings. */
39
51
  const datasource = (metadata) => {
40
- return target => {
52
+ return (target) => {
41
53
  (0, injectable_1.injectable)({
42
54
  type: inversion_1.ArtifactTypes.DATASOURCE,
43
55
  ...(0, injectable_1.pickRegistrationOptions)({ metadata: metadata ?? {} }),
@@ -101,7 +113,7 @@ const registerDataSourceInjection = (opts) => {
101
113
  const { target, registry, dataSourceRef, resolvedDataSource } = opts;
102
114
  // Own metadata only: `getInjectMetadata` walks the prototype chain, so a repository extending another @repository class would see the BASE's injection at param[0] and silently resolve the base's dataSource.
103
115
  const ownInjects = Reflect.getOwnMetadata(inversion_1.MetadataKeys.INJECT, target);
104
- const injectAtIndex0 = ownInjects?.find(entry => entry?.index === 0);
116
+ const injectAtIndex0 = ownInjects?.find((entry) => entry?.index === 0);
105
117
  if (injectAtIndex0) {
106
118
  // `@inject({ target })` carries no key; read the one recorded on the class. The function form
107
119
  // resolves through the same helper the container uses, so both paths read one class.
@@ -217,7 +229,7 @@ const applyRepositoryMetadata = (opts) => {
217
229
  registry.setRepositoryMetadata({ target, metadata: { ...metadata, _resolved: resolved } });
218
230
  };
219
231
  const repository = (metadata) => {
220
- return target => {
232
+ return (target) => {
221
233
  const registry = inversion_1.MetadataRegistry.getInstance();
222
234
  if (!metadata) {
223
235
  applyRepositoryMetadata({