@decohere/http 0.0.1-dev.125 → 0.0.1-dev.5

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 (292) hide show
  1. package/package.json +4 -13
  2. package/src/app/app.ts +147 -0
  3. package/src/app/module.ts +19 -0
  4. package/src/auth/ability.ts +56 -0
  5. package/src/auth/auth.config.ts +34 -0
  6. package/src/auth/auth.extensions.ts +115 -0
  7. package/src/auth/auth.types.ts +124 -0
  8. package/src/auth/casl-authorization.service.ts +62 -0
  9. package/{types/src/auth/principal-provider.d.ts → src/auth/principal-provider.ts} +13 -5
  10. package/src/auth/safe-outbound-url.ts +117 -0
  11. package/src/auth/token-service.ts +192 -0
  12. package/src/builder/builder.ts +118 -0
  13. package/{es6/src/const.js → src/const.ts} +25 -17
  14. package/src/health/health.controller.ts +34 -0
  15. package/src/health/health.extensions.ts +53 -0
  16. package/src/health/readiness.service.ts +33 -0
  17. package/{types/src/health/readiness.types.d.ts → src/health/readiness.types.ts} +4 -8
  18. package/src/hosting/hosted-service-host.ts +102 -0
  19. package/src/hosting/hosted-service.ts +31 -0
  20. package/src/http/http.compression.ts +38 -0
  21. package/src/http/http.extensions.ts +244 -0
  22. package/{types/src/http/http.options.store.d.ts → src/http/http.options.store.ts} +11 -1
  23. package/src/http/http.options.ts +41 -0
  24. package/{types/src/http/http.security.d.ts → src/http/http.security.ts} +16 -10
  25. package/src/http/http.static.ts +359 -0
  26. package/{es6/src/index.js → src/index.ts} +1 -0
  27. package/src/openapi/index.ts +22 -0
  28. package/src/openapi/openapi.generator.ts +78 -0
  29. package/src/openapi/openapi.types.ts +60 -0
  30. package/src/openapi/request-schema.ts +155 -0
  31. package/src/openapi/request-validator.ts +95 -0
  32. package/src/providers/fastify.provider.ts +454 -0
  33. package/src/routing/anvil.types.ts +150 -0
  34. package/src/routing/decorators/argument.decorator.ts +33 -0
  35. package/src/routing/decorators/auth.decorator.ts +79 -0
  36. package/src/routing/decorators/controller.decorator.ts +9 -0
  37. package/src/routing/decorators/field.decorator.ts +15 -0
  38. package/src/routing/decorators/request.decorator.ts +34 -0
  39. package/src/routing/decorators/response.decorator.ts +18 -0
  40. package/src/routing/decorators/route.decorator.ts +52 -0
  41. package/src/routing/filters/exception-filter-host.ts +90 -0
  42. package/src/routing/filters/exception-filter.ts +29 -0
  43. package/src/routing/middleware/http-access-log.middleware.ts +36 -0
  44. package/src/routing/middleware/middleware.ts +26 -0
  45. package/src/routing/middleware/request-id.ts +18 -0
  46. package/src/routing/path.util.ts +38 -0
  47. package/src/routing/pipes/pipes.ts +132 -0
  48. package/src/routing/services/route-argument-resolver.ts +92 -0
  49. package/src/routing/services/route-registry.ts +229 -0
  50. package/src/routing/services/router.ts +166 -0
  51. package/src/sse/sse.decorator.ts +41 -0
  52. package/src/sse/sse.encoder.ts +86 -0
  53. package/src/sse/sse.types.ts +47 -0
  54. package/src/sse/sse.wire.ts +34 -0
  55. package/src/testing/boot-module.ts +63 -0
  56. package/src/testing/sse-reader.ts +120 -0
  57. package/tests/app.hosted-services.spec.ts +292 -0
  58. package/tests/app.shutdown.integration.spec.ts +160 -0
  59. package/tests/app.spec.ts +132 -0
  60. package/tests/auth.ability.spec.ts +48 -0
  61. package/tests/auth.decorators.spec.ts +20 -0
  62. package/tests/auth.fail-closed.pentest.spec.ts +77 -0
  63. package/tests/auth.integration.spec.ts +234 -0
  64. package/tests/auth.jwks-cache.spec.ts +52 -0
  65. package/tests/auth.missing-auth.pentest.spec.ts +56 -0
  66. package/tests/auth.oidc-ssrf.pentest.spec.ts +72 -0
  67. package/tests/auth.oidc.integration.spec.ts +161 -0
  68. package/tests/auth.token-service.spec.ts +251 -0
  69. package/tests/builder.spec.ts +12 -0
  70. package/tests/health.integration.spec.ts +111 -0
  71. package/tests/helpers/listen-ephemeral.ts +13 -0
  72. package/tests/helpers/local-oidc-server.ts +100 -0
  73. package/tests/http.access-log.integration.spec.ts +111 -0
  74. package/tests/http.boolean-query.integration.spec.ts +59 -0
  75. package/tests/http.compression.integration.spec.ts +604 -0
  76. package/tests/http.date-query.integration.spec.ts +71 -0
  77. package/tests/http.global-prefix.integration.spec.ts +284 -0
  78. package/tests/http.number-query.integration.spec.ts +65 -0
  79. package/tests/http.pino-roll-hmr.integration.spec.ts +79 -0
  80. package/tests/http.pipeline-order.integration.spec.ts +95 -0
  81. package/tests/http.request-cleanup.integration.spec.ts +57 -0
  82. package/tests/http.request-id-scope.pentest.spec.ts +50 -0
  83. package/tests/http.security.integration.spec.ts +106 -0
  84. package/tests/http.static.integration.spec.ts +847 -0
  85. package/tests/http.static.spec.ts +111 -0
  86. package/tests/http.surface.integration.spec.ts +167 -0
  87. package/tests/openapi.integration.spec.ts +193 -0
  88. package/tests/openapi.validator-cache.integration.spec.ts +55 -0
  89. package/tests/routing.decorators.spec.ts +15 -0
  90. package/tests/routing.registry.spec.ts +44 -0
  91. package/tests/routing.resolver.spec.ts +92 -0
  92. package/tests/sse.integration.spec.ts +421 -0
  93. package/tests/sse.wire.spec.ts +33 -0
  94. package/LICENSE +0 -15
  95. package/commonjs/src/app/app.js +0 -166
  96. package/commonjs/src/app/index.js +0 -19
  97. package/commonjs/src/app/module.js +0 -17
  98. package/commonjs/src/auth/ability.js +0 -54
  99. package/commonjs/src/auth/auth.config.js +0 -23
  100. package/commonjs/src/auth/auth.extensions.js +0 -106
  101. package/commonjs/src/auth/auth.types.js +0 -65
  102. package/commonjs/src/auth/casl-authorization.service.js +0 -36
  103. package/commonjs/src/auth/index.js +0 -23
  104. package/commonjs/src/auth/principal-provider.js +0 -19
  105. package/commonjs/src/auth/safe-outbound-url.js +0 -102
  106. package/commonjs/src/auth/token-service.js +0 -151
  107. package/commonjs/src/builder/builder.js +0 -95
  108. package/commonjs/src/builder/index.js +0 -18
  109. package/commonjs/src/const.js +0 -87
  110. package/commonjs/src/health/health.controller.js +0 -75
  111. package/commonjs/src/health/health.extensions.js +0 -50
  112. package/commonjs/src/health/index.js +0 -21
  113. package/commonjs/src/health/readiness.service.js +0 -67
  114. package/commonjs/src/health/readiness.types.js +0 -7
  115. package/commonjs/src/hosting/hosted-service-host.js +0 -88
  116. package/commonjs/src/hosting/hosted-service.js +0 -11
  117. package/commonjs/src/hosting/index.js +0 -19
  118. package/commonjs/src/http/http.compression.js +0 -27
  119. package/commonjs/src/http/http.extensions.js +0 -269
  120. package/commonjs/src/http/http.options.js +0 -26
  121. package/commonjs/src/http/http.options.store.js +0 -20
  122. package/commonjs/src/http/http.security.js +0 -27
  123. package/commonjs/src/http/http.static.js +0 -248
  124. package/commonjs/src/http/index.js +0 -22
  125. package/commonjs/src/index.js +0 -27
  126. package/commonjs/src/openapi/index.js +0 -45
  127. package/commonjs/src/openapi/openapi.generator.js +0 -103
  128. package/commonjs/src/openapi/openapi.types.js +0 -4
  129. package/commonjs/src/openapi/request-schema.js +0 -187
  130. package/commonjs/src/openapi/request-validator.js +0 -85
  131. package/commonjs/src/providers/fastify.provider.js +0 -391
  132. package/commonjs/src/providers/index.js +0 -18
  133. package/commonjs/src/routing/anvil.types.js +0 -99
  134. package/commonjs/src/routing/decorators/argument.decorator.js +0 -49
  135. package/commonjs/src/routing/decorators/auth.decorator.js +0 -70
  136. package/commonjs/src/routing/decorators/controller.decorator.js +0 -16
  137. package/commonjs/src/routing/decorators/field.decorator.js +0 -25
  138. package/commonjs/src/routing/decorators/index.js +0 -24
  139. package/commonjs/src/routing/decorators/request.decorator.js +0 -30
  140. package/commonjs/src/routing/decorators/response.decorator.js +0 -34
  141. package/commonjs/src/routing/decorators/route.decorator.js +0 -67
  142. package/commonjs/src/routing/filters/exception-filter-host.js +0 -145
  143. package/commonjs/src/routing/filters/exception-filter.js +0 -28
  144. package/commonjs/src/routing/index.js +0 -25
  145. package/commonjs/src/routing/middleware/http-access-log.middleware.js +0 -47
  146. package/commonjs/src/routing/middleware/middleware.js +0 -20
  147. package/commonjs/src/routing/middleware/request-id.js +0 -30
  148. package/commonjs/src/routing/path.util.js +0 -51
  149. package/commonjs/src/routing/pipes/index.js +0 -18
  150. package/commonjs/src/routing/pipes/pipes.js +0 -145
  151. package/commonjs/src/routing/services/index.js +0 -18
  152. package/commonjs/src/routing/services/route-argument-resolver.js +0 -77
  153. package/commonjs/src/routing/services/route-registry.js +0 -194
  154. package/commonjs/src/routing/services/router.js +0 -158
  155. package/commonjs/src/sse/index.js +0 -26
  156. package/commonjs/src/sse/sse.decorator.js +0 -42
  157. package/commonjs/src/sse/sse.encoder.js +0 -73
  158. package/commonjs/src/sse/sse.types.js +0 -36
  159. package/commonjs/src/sse/sse.wire.js +0 -40
  160. package/commonjs/src/testing/boot-module.js +0 -38
  161. package/commonjs/src/testing/index.js +0 -20
  162. package/commonjs/src/testing/sse-reader.js +0 -98
  163. package/es6/src/app/app.js +0 -148
  164. package/es6/src/app/index.js +0 -2
  165. package/es6/src/app/module.js +0 -7
  166. package/es6/src/auth/ability.js +0 -45
  167. package/es6/src/auth/auth.config.js +0 -19
  168. package/es6/src/auth/auth.extensions.js +0 -83
  169. package/es6/src/auth/auth.types.js +0 -35
  170. package/es6/src/auth/casl-authorization.service.js +0 -40
  171. package/es6/src/auth/index.js +0 -6
  172. package/es6/src/auth/principal-provider.js +0 -14
  173. package/es6/src/auth/safe-outbound-url.js +0 -99
  174. package/es6/src/auth/token-service.js +0 -141
  175. package/es6/src/builder/builder.js +0 -85
  176. package/es6/src/builder/index.js +0 -1
  177. package/es6/src/health/health.controller.js +0 -65
  178. package/es6/src/health/health.extensions.js +0 -40
  179. package/es6/src/health/index.js +0 -4
  180. package/es6/src/health/readiness.service.js +0 -57
  181. package/es6/src/health/readiness.types.js +0 -4
  182. package/es6/src/hosting/hosted-service-host.js +0 -81
  183. package/es6/src/hosting/hosted-service.js +0 -8
  184. package/es6/src/hosting/index.js +0 -2
  185. package/es6/src/http/http.compression.js +0 -9
  186. package/es6/src/http/http.extensions.js +0 -259
  187. package/es6/src/http/http.options.js +0 -16
  188. package/es6/src/http/http.options.store.js +0 -13
  189. package/es6/src/http/http.security.js +0 -9
  190. package/es6/src/http/http.static.js +0 -224
  191. package/es6/src/http/index.js +0 -5
  192. package/es6/src/openapi/index.js +0 -3
  193. package/es6/src/openapi/openapi.generator.js +0 -82
  194. package/es6/src/openapi/openapi.types.js +0 -1
  195. package/es6/src/openapi/request-schema.js +0 -160
  196. package/es6/src/openapi/request-validator.js +0 -71
  197. package/es6/src/providers/fastify.provider.js +0 -376
  198. package/es6/src/providers/index.js +0 -1
  199. package/es6/src/routing/anvil.types.js +0 -57
  200. package/es6/src/routing/decorators/argument.decorator.js +0 -28
  201. package/es6/src/routing/decorators/auth.decorator.js +0 -58
  202. package/es6/src/routing/decorators/controller.decorator.js +0 -6
  203. package/es6/src/routing/decorators/field.decorator.js +0 -15
  204. package/es6/src/routing/decorators/index.js +0 -7
  205. package/es6/src/routing/decorators/request.decorator.js +0 -24
  206. package/es6/src/routing/decorators/response.decorator.js +0 -16
  207. package/es6/src/routing/decorators/route.decorator.js +0 -37
  208. package/es6/src/routing/filters/exception-filter-host.js +0 -127
  209. package/es6/src/routing/filters/exception-filter.js +0 -10
  210. package/es6/src/routing/index.js +0 -8
  211. package/es6/src/routing/middleware/http-access-log.middleware.js +0 -37
  212. package/es6/src/routing/middleware/middleware.js +0 -10
  213. package/es6/src/routing/middleware/request-id.js +0 -14
  214. package/es6/src/routing/path.util.js +0 -33
  215. package/es6/src/routing/pipes/index.js +0 -1
  216. package/es6/src/routing/pipes/pipes.js +0 -118
  217. package/es6/src/routing/services/index.js +0 -1
  218. package/es6/src/routing/services/route-argument-resolver.js +0 -67
  219. package/es6/src/routing/services/route-registry.js +0 -184
  220. package/es6/src/routing/services/router.js +0 -148
  221. package/es6/src/sse/index.js +0 -2
  222. package/es6/src/sse/sse.decorator.js +0 -31
  223. package/es6/src/sse/sse.encoder.js +0 -67
  224. package/es6/src/sse/sse.types.js +0 -22
  225. package/es6/src/sse/sse.wire.js +0 -30
  226. package/es6/src/testing/boot-module.js +0 -35
  227. package/es6/src/testing/index.js +0 -2
  228. package/es6/src/testing/sse-reader.js +0 -91
  229. package/types/src/app/app.d.ts +0 -41
  230. package/types/src/app/module.d.ts +0 -15
  231. package/types/src/auth/ability.d.ts +0 -19
  232. package/types/src/auth/auth.config.d.ts +0 -28
  233. package/types/src/auth/auth.extensions.d.ts +0 -53
  234. package/types/src/auth/auth.types.d.ts +0 -73
  235. package/types/src/auth/casl-authorization.service.d.ts +0 -28
  236. package/types/src/auth/safe-outbound-url.d.ts +0 -9
  237. package/types/src/auth/token-service.d.ts +0 -31
  238. package/types/src/builder/builder.d.ts +0 -36
  239. package/types/src/const.d.ts +0 -32
  240. package/types/src/health/health.controller.d.ts +0 -16
  241. package/types/src/health/health.extensions.d.ts +0 -31
  242. package/types/src/health/readiness.service.d.ts +0 -9
  243. package/types/src/hosting/hosted-service-host.d.ts +0 -37
  244. package/types/src/hosting/hosted-service.d.ts +0 -31
  245. package/types/src/http/http.compression.d.ts +0 -32
  246. package/types/src/http/http.extensions.d.ts +0 -79
  247. package/types/src/http/http.options.d.ts +0 -39
  248. package/types/src/http/http.static.d.ts +0 -160
  249. package/types/src/index.d.ts +0 -10
  250. package/types/src/openapi/index.d.ts +0 -6
  251. package/types/src/openapi/openapi.generator.d.ts +0 -6
  252. package/types/src/openapi/openapi.types.d.ts +0 -58
  253. package/types/src/openapi/request-schema.d.ts +0 -21
  254. package/types/src/openapi/request-validator.d.ts +0 -9
  255. package/types/src/providers/fastify.provider.d.ts +0 -56
  256. package/types/src/routing/anvil.types.d.ts +0 -119
  257. package/types/src/routing/decorators/argument.decorator.d.ts +0 -11
  258. package/types/src/routing/decorators/auth.decorator.d.ts +0 -30
  259. package/types/src/routing/decorators/controller.decorator.d.ts +0 -3
  260. package/types/src/routing/decorators/field.decorator.d.ts +0 -2
  261. package/types/src/routing/decorators/request.decorator.d.ts +0 -8
  262. package/types/src/routing/decorators/response.decorator.d.ts +0 -4
  263. package/types/src/routing/decorators/route.decorator.d.ts +0 -7
  264. package/types/src/routing/filters/exception-filter-host.d.ts +0 -19
  265. package/types/src/routing/filters/exception-filter.d.ts +0 -16
  266. package/types/src/routing/middleware/http-access-log.middleware.d.ts +0 -8
  267. package/types/src/routing/middleware/middleware.d.ts +0 -10
  268. package/types/src/routing/middleware/request-id.d.ts +0 -6
  269. package/types/src/routing/path.util.d.ts +0 -9
  270. package/types/src/routing/pipes/pipes.d.ts +0 -21
  271. package/types/src/routing/services/route-argument-resolver.d.ts +0 -10
  272. package/types/src/routing/services/route-registry.d.ts +0 -20
  273. package/types/src/routing/services/router.d.ts +0 -22
  274. package/types/src/sse/sse.decorator.d.ts +0 -17
  275. package/types/src/sse/sse.encoder.d.ts +0 -16
  276. package/types/src/sse/sse.types.d.ts +0 -37
  277. package/types/src/sse/sse.wire.d.ts +0 -9
  278. package/types/src/testing/boot-module.d.ts +0 -34
  279. package/types/src/testing/sse-reader.d.ts +0 -29
  280. /package/{types/src/app/index.d.ts → src/app/index.ts} +0 -0
  281. /package/{types/src/auth/index.d.ts → src/auth/index.ts} +0 -0
  282. /package/{types/src/builder/index.d.ts → src/builder/index.ts} +0 -0
  283. /package/{types/src/health/index.d.ts → src/health/index.ts} +0 -0
  284. /package/{types/src/hosting/index.d.ts → src/hosting/index.ts} +0 -0
  285. /package/{types/src/http/index.d.ts → src/http/index.ts} +0 -0
  286. /package/{types/src/providers/index.d.ts → src/providers/index.ts} +0 -0
  287. /package/{types/src/routing/decorators/index.d.ts → src/routing/decorators/index.ts} +0 -0
  288. /package/{types/src/routing/index.d.ts → src/routing/index.ts} +0 -0
  289. /package/{types/src/routing/pipes/index.d.ts → src/routing/pipes/index.ts} +0 -0
  290. /package/{types/src/routing/services/index.d.ts → src/routing/services/index.ts} +0 -0
  291. /package/{types/src/sse/index.d.ts → src/sse/index.ts} +0 -0
  292. /package/{types/src/testing/index.d.ts → src/testing/index.ts} +0 -0
@@ -1,45 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- function _export(target, all) {
6
- for(var name in all)Object.defineProperty(target, name, {
7
- enumerable: true,
8
- get: Object.getOwnPropertyDescriptor(all, name).get
9
- });
10
- }
11
- _export(exports, {
12
- get ValidationError () {
13
- return _requestvalidator.ValidationError;
14
- },
15
- get buildRouteRequestSchemas () {
16
- return _requestschema.buildRouteRequestSchemas;
17
- },
18
- get generateOpenApiDocument () {
19
- return _openapigenerator.generateOpenApiDocument;
20
- },
21
- get mergeObjectSchemas () {
22
- return _requestschema.mergeObjectSchemas;
23
- },
24
- get objectArgToParts () {
25
- return _requestschema.objectArgToParts;
26
- },
27
- get pathParamsToSchema () {
28
- return _requestschema.pathParamsToSchema;
29
- },
30
- get resolveOpenApiPath () {
31
- return _openapigenerator.resolveOpenApiPath;
32
- },
33
- get toOpenApiPath () {
34
- return _openapigenerator.toOpenApiPath;
35
- },
36
- get typeToSchema () {
37
- return _requestschema.typeToSchema;
38
- },
39
- get validateRequest () {
40
- return _requestvalidator.validateRequest;
41
- }
42
- });
43
- const _openapigenerator = require("./openapi.generator.js");
44
- const _requestschema = require("./request-schema.js");
45
- const _requestvalidator = require("./request-validator.js");
@@ -1,103 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- function _export(target, all) {
6
- for(var name in all)Object.defineProperty(target, name, {
7
- enumerable: true,
8
- get: Object.getOwnPropertyDescriptor(all, name).get
9
- });
10
- }
11
- _export(exports, {
12
- get generateOpenApiDocument () {
13
- return generateOpenApiDocument;
14
- },
15
- get resolveOpenApiPath () {
16
- return resolveOpenApiPath;
17
- },
18
- get toOpenApiPath () {
19
- return toOpenApiPath;
20
- }
21
- });
22
- const _requestschema = require("./request-schema.js");
23
- const DEFAULT_SPEC_PATH = "/openapi.json";
24
- function resolveOpenApiPath(options) {
25
- const path = options.path?.trim() || DEFAULT_SPEC_PATH;
26
- return path.startsWith("/") ? path : `/${path}`;
27
- }
28
- function toOpenApiPath(fastifyPath) {
29
- return fastifyPath.replace(/:([A-Za-z_][\w]*)/g, "{$1}");
30
- }
31
- function generateOpenApiDocument(registry, options) {
32
- const paths = {};
33
- for (const route of registry.routes){
34
- const path = toOpenApiPath(route.path);
35
- const method = route.method.toLowerCase();
36
- let pathItem = paths[path];
37
- if (pathItem == null) {
38
- pathItem = {};
39
- paths[path] = pathItem;
40
- }
41
- pathItem[method] = buildOperation(route);
42
- }
43
- const document = {
44
- openapi: "3.0.3",
45
- info: options.info,
46
- paths
47
- };
48
- if (options.servers?.length) {
49
- document.servers = options.servers;
50
- }
51
- return document;
52
- }
53
- function buildOperation(route) {
54
- const { queryParams, pathParams, body: bodySchema } = (0, _requestschema.buildRouteRequestSchemas)(route);
55
- const parameters = [
56
- ...queryParams,
57
- ...pathParams
58
- ];
59
- const status = String(route.httpCode ?? 200);
60
- const operation = {
61
- operationId: `${route.controller.name}.${route.handler}`,
62
- tags: [
63
- route.controller.name
64
- ],
65
- responses: {
66
- [status]: route.sse ? {
67
- description: "Server-sent event stream",
68
- content: {
69
- "text/event-stream": {
70
- schema: {
71
- type: "string"
72
- }
73
- }
74
- }
75
- } : {
76
- description: "Successful response"
77
- }
78
- }
79
- };
80
- if (route.routeArgs?.some((arg)=>arg.argumentLocation === "lastEventId")) {
81
- parameters.push({
82
- name: "Last-Event-ID",
83
- in: "header",
84
- schema: {
85
- type: "string"
86
- }
87
- });
88
- }
89
- if (parameters.length > 0) {
90
- operation.parameters = parameters;
91
- }
92
- if (bodySchema != null) {
93
- operation.requestBody = {
94
- required: true,
95
- content: {
96
- "application/json": {
97
- schema: bodySchema
98
- }
99
- }
100
- };
101
- }
102
- return operation;
103
- }
@@ -1,4 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
@@ -1,187 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- function _export(target, all) {
6
- for(var name in all)Object.defineProperty(target, name, {
7
- enumerable: true,
8
- get: Object.getOwnPropertyDescriptor(all, name).get
9
- });
10
- }
11
- _export(exports, {
12
- get buildRouteRequestSchemas () {
13
- return buildRouteRequestSchemas;
14
- },
15
- get mergeObjectSchemas () {
16
- return mergeObjectSchemas;
17
- },
18
- get objectArgToParts () {
19
- return objectArgToParts;
20
- },
21
- get pathParamsToSchema () {
22
- return pathParamsToSchema;
23
- },
24
- get typeToSchema () {
25
- return typeToSchema;
26
- }
27
- });
28
- const _reflection = require("@decohere/core/reflection");
29
- const _anviltypes = require("../routing/anvil.types.js");
30
- function buildRouteRequestSchemas(route) {
31
- const queryParams = [];
32
- const pathParams = [];
33
- let bodySchema;
34
- for (const routeArg of route.routeArgs ?? []){
35
- if (routeArg.argumentLocation != null && _anviltypes.InjectedParts.includes(routeArg.argumentLocation)) {
36
- continue;
37
- }
38
- if ((0, _reflection.isPrimitiveOrDateType)(routeArg.argumentType)) {
39
- const location = routeArg.argumentLocation;
40
- if (location === "query" || location === "params") {
41
- const param = {
42
- name: routeArg.mappingKey ?? "value",
43
- in: location === "params" ? "path" : "query",
44
- required: location === "params",
45
- schema: typeToSchema(routeArg.argumentType.name)
46
- };
47
- if (location === "params") {
48
- pathParams.push(param);
49
- } else {
50
- queryParams.push(param);
51
- }
52
- }
53
- continue;
54
- }
55
- const parts = objectArgToParts(routeArg);
56
- queryParams.push(...parts.queryParams);
57
- pathParams.push(...parts.pathParams);
58
- if (parts.body != null) {
59
- bodySchema = mergeObjectSchemas(bodySchema, parts.body);
60
- }
61
- }
62
- return {
63
- queryParams,
64
- pathParams,
65
- body: bodySchema
66
- };
67
- }
68
- function objectArgToParts(routeArg) {
69
- const queryParams = [];
70
- const pathParams = [];
71
- const bodyProperties = {};
72
- const bodyRequired = [];
73
- const argLocation = routeArg.argumentLocation;
74
- for (const [, meta] of routeArg.fieldMap?.entries() ?? []){
75
- const location = meta.fieldLocation ?? argLocation;
76
- const name = meta.mappingKey || meta.fieldKey;
77
- const schema = typeToSchema(meta.fieldType?.name);
78
- if (location === "query") {
79
- queryParams.push({
80
- name,
81
- in: "query",
82
- required: false,
83
- schema
84
- });
85
- } else if (location === "params") {
86
- pathParams.push({
87
- name,
88
- in: "path",
89
- required: true,
90
- schema
91
- });
92
- } else if (location === "body" || location == null && argLocation === "body") {
93
- bodyProperties[name] = schema;
94
- bodyRequired.push(name);
95
- } else if (location == null && argLocation == null) {
96
- // Unlocated object fields default to body for OpenAPI (common DTO pattern).
97
- bodyProperties[name] = schema;
98
- bodyRequired.push(name);
99
- }
100
- }
101
- // Whole-object body argument with no fields still advertises an object body.
102
- if (argLocation === "body" && Object.keys(bodyProperties).length === 0) {
103
- return {
104
- queryParams,
105
- pathParams,
106
- body: {
107
- type: "object",
108
- additionalProperties: true
109
- }
110
- };
111
- }
112
- const body = Object.keys(bodyProperties).length > 0 ? {
113
- type: "object",
114
- properties: bodyProperties,
115
- required: bodyRequired,
116
- additionalProperties: false
117
- } : undefined;
118
- return {
119
- queryParams,
120
- pathParams,
121
- body
122
- };
123
- }
124
- function mergeObjectSchemas(a, b) {
125
- if (a == null) {
126
- return b;
127
- }
128
- return {
129
- type: "object",
130
- properties: {
131
- ...a.properties,
132
- ...b.properties
133
- },
134
- required: [
135
- ...new Set([
136
- ...a.required ?? [],
137
- ...b.required ?? []
138
- ])
139
- ],
140
- additionalProperties: false
141
- };
142
- }
143
- function typeToSchema(typeName) {
144
- switch(typeName){
145
- case "Number":
146
- return {
147
- type: "number"
148
- };
149
- case "Boolean":
150
- return {
151
- type: "boolean"
152
- };
153
- case "Date":
154
- return {
155
- type: "string",
156
- format: "date-time"
157
- };
158
- case "String":
159
- return {
160
- type: "string"
161
- };
162
- default:
163
- return {};
164
- }
165
- }
166
- function pathParamsToSchema(params) {
167
- if (params.length === 0) {
168
- return undefined;
169
- }
170
- const properties = {};
171
- const required = [];
172
- for (const param of params){
173
- properties[param.name] = {
174
- type: "string",
175
- minLength: 1
176
- };
177
- if (param.required !== false) {
178
- required.push(param.name);
179
- }
180
- }
181
- return {
182
- type: "object",
183
- properties,
184
- required,
185
- additionalProperties: true
186
- };
187
- }
@@ -1,85 +0,0 @@
1
- "use strict";
2
- Object.defineProperty(exports, "__esModule", {
3
- value: true
4
- });
5
- function _export(target, all) {
6
- for(var name in all)Object.defineProperty(target, name, {
7
- enumerable: true,
8
- get: Object.getOwnPropertyDescriptor(all, name).get
9
- });
10
- }
11
- _export(exports, {
12
- get ValidationError () {
13
- return _anviltypes.ValidationError;
14
- },
15
- get validateRequest () {
16
- return validateRequest;
17
- }
18
- });
19
- const _ajv = require("ajv");
20
- const _anviltypes = require("../routing/anvil.types.js");
21
- const _requestschema = require("./request-schema.js");
22
- function validateRequest(route, request) {
23
- const { params, body } = getValidators(route);
24
- const issues = [];
25
- if (params != null) {
26
- collectIssues(params, request.params ?? {}, "/params", issues);
27
- }
28
- if (body != null) {
29
- collectIssues(body, request.body, "/body", issues);
30
- }
31
- if (issues.length > 0) {
32
- throw new _anviltypes.ValidationError("Validation failed", issues);
33
- }
34
- }
35
- const ajv = new _ajv.Ajv({
36
- allErrors: true,
37
- coerceTypes: false,
38
- removeAdditional: false,
39
- useDefaults: false,
40
- strict: false
41
- });
42
- /**
43
- * Compiled once per route and reused. Compiling per request was slow, and AJV keeps every
44
- * schema it compiles, so memory grew with traffic (#498).
45
- */ const validatorsByRoute = new WeakMap();
46
- function getValidators(route) {
47
- let validators = validatorsByRoute.get(route);
48
- if (validators == null) {
49
- const schemas = (0, _requestschema.buildRouteRequestSchemas)(route);
50
- const paramsSchema = (0, _requestschema.pathParamsToSchema)(schemas.pathParams);
51
- validators = {
52
- params: paramsSchema != null ? ajv.compile(paramsSchema) : undefined,
53
- body: schemas.body != null ? ajv.compile(schemas.body) : undefined
54
- };
55
- validatorsByRoute.set(route, validators);
56
- }
57
- return validators;
58
- }
59
- function collectIssues(validate, data, rootPath, issues) {
60
- if (validate(data)) {
61
- return;
62
- }
63
- for (const err of validate.errors ?? []){
64
- issues.push(toIssue(err, rootPath));
65
- }
66
- }
67
- function toIssue(err, rootPath) {
68
- const instance = err.instancePath ?? "";
69
- const path = instance.length > 0 ? `${rootPath}${instance}` : rootPath;
70
- const message = err.message ?? "is invalid";
71
- return {
72
- path,
73
- message: formatAjvMessage(err, message),
74
- keyword: err.keyword
75
- };
76
- }
77
- function formatAjvMessage(err, fallback) {
78
- if (err.keyword === "required" && typeof err.params?.missingProperty === "string") {
79
- return `must have required property '${err.params.missingProperty}'`;
80
- }
81
- if (err.keyword === "additionalProperties" && typeof err.params?.additionalProperty === "string") {
82
- return `must NOT have additional property '${err.params.additionalProperty}'`;
83
- }
84
- return fallback;
85
- }