@opra/nestjs 0.14.0 → 0.16.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (40) hide show
  1. package/cjs/decorators/context.decorator.js +2 -12
  2. package/cjs/enums/handler-paramtype.enum.js +2 -3
  3. package/cjs/factories/opra-api.factory.js +56 -65
  4. package/cjs/factories/params.factory.js +4 -6
  5. package/cjs/services/nest-explorer.js +1 -1
  6. package/cjs/services/opra-api-loader.js +6 -2
  7. package/cjs/utils/param.utils.js +2 -0
  8. package/esm/constants.js +7 -4
  9. package/esm/decorators/context.decorator.js +7 -14
  10. package/esm/enums/handler-paramtype.enum.js +7 -5
  11. package/esm/factories/opra-api.factory.js +102 -108
  12. package/esm/factories/params.factory.js +12 -10
  13. package/esm/index.js +7 -4
  14. package/esm/interfaces/opra-module-options.interface.js +2 -1
  15. package/esm/opra-core.module.js +30 -27
  16. package/esm/opra.module.js +11 -8
  17. package/esm/services/nest-explorer.js +7 -3
  18. package/esm/services/opra-api-loader.js +32 -24
  19. package/esm/types.js +2 -1
  20. package/esm/utils/class.utils.js +12 -6
  21. package/esm/utils/function.utils.js +8 -4
  22. package/esm/utils/param.utils.js +11 -5
  23. package/package.json +12 -11
  24. package/types/decorators/context.decorator.d.ts +10 -0
  25. package/types/enums/handler-paramtype.enum.d.ts +6 -0
  26. package/{esm → types}/factories/opra-api.factory.d.ts +2 -2
  27. package/{esm → types}/services/opra-api-loader.d.ts +2 -2
  28. package/esm/decorators/context.decorator.d.ts +0 -20
  29. package/esm/enums/handler-paramtype.enum.d.ts +0 -7
  30. /package/{esm → types}/constants.d.ts +0 -0
  31. /package/{esm → types}/factories/params.factory.d.ts +0 -0
  32. /package/{esm → types}/index.d.ts +0 -0
  33. /package/{esm → types}/interfaces/opra-module-options.interface.d.ts +0 -0
  34. /package/{esm → types}/opra-core.module.d.ts +0 -0
  35. /package/{esm → types}/opra.module.d.ts +0 -0
  36. /package/{esm → types}/services/nest-explorer.d.ts +0 -0
  37. /package/{esm → types}/types.d.ts +0 -0
  38. /package/{esm → types}/utils/class.utils.d.ts +0 -0
  39. /package/{esm → types}/utils/function.utils.d.ts +0 -0
  40. /package/{esm → types}/utils/param.utils.d.ts +0 -0
@@ -1,6 +1,6 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.Query = exports.Service = exports.Response = exports.Context = void 0;
3
+ exports.ApiDoc = exports.Context = void 0;
4
4
  const handler_paramtype_enum_js_1 = require("../enums/handler-paramtype.enum.js");
5
5
  const param_utils_js_1 = require("../utils/param.utils.js");
6
6
  /**
@@ -8,18 +8,8 @@ const param_utils_js_1 = require("../utils/param.utils.js");
8
8
  * parameter with the value of `RequestContext`.
9
9
  */
10
10
  exports.Context = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.CONTEXT);
11
- /**
12
- * Handler method parameter decorator. Populates the decorated
13
- * parameter with the value of `QueryResponse`.
14
- */
15
- exports.Response = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.RESPONSE);
16
- /**
17
- * Handler method parameter decorator. Populates the decorated
18
- * parameter with the value of `OpraService`.
19
- */
20
- exports.Service = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.SERVICE);
21
11
  /**
22
12
  * Handler method parameter decorator. Populates the decorated
23
13
  * parameter with the value of `OpraService`.
24
14
  */
25
- exports.Query = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.QUERY);
15
+ exports.ApiDoc = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.API);
@@ -4,8 +4,7 @@ exports.HandlerParamType = void 0;
4
4
  var HandlerParamType;
5
5
  (function (HandlerParamType) {
6
6
  HandlerParamType[HandlerParamType["CONTEXT"] = 0] = "CONTEXT";
7
- HandlerParamType[HandlerParamType["SERVICE"] = 1] = "SERVICE";
8
- HandlerParamType[HandlerParamType["QUERY"] = 2] = "QUERY";
7
+ HandlerParamType[HandlerParamType["API"] = 1] = "API";
8
+ HandlerParamType[HandlerParamType["REQUEST"] = 2] = "REQUEST";
9
9
  HandlerParamType[HandlerParamType["RESPONSE"] = 3] = "RESPONSE";
10
- HandlerParamType[HandlerParamType["USER_CONTEXT"] = 4] = "USER_CONTEXT";
11
10
  })(HandlerParamType = exports.HandlerParamType || (exports.HandlerParamType = {}));
@@ -17,7 +17,6 @@ const nest_explorer_js_1 = require("../services/nest-explorer.js");
17
17
  const function_utils_js_1 = require("../utils/function.utils.js");
18
18
  const params_factory_js_1 = require("./params.factory.js");
19
19
  const noOpFunction = () => void 0;
20
- const METHOD_PATCHED = 'ServiceFactory.method-patched';
21
20
  let OpraApiFactory = class OpraApiFactory {
22
21
  constructor() {
23
22
  this.paramsFactory = new params_factory_js_1.OpraParamsFactory();
@@ -28,15 +27,27 @@ let OpraApiFactory = class OpraApiFactory {
28
27
  info.title = info.title || 'Untitled service';
29
28
  info.version = info.version || '1';
30
29
  const resources = [];
31
- const serviceArgs = {
30
+ const apiSchema = {
31
+ version: common_2.OpraSchema.SpecVersion,
32
32
  info,
33
33
  types: [],
34
34
  resources,
35
35
  };
36
+ /*
37
+ * Walk through modules and add Resource instances to the api schema
38
+ */
36
39
  const wrappers = this.explorerService.exploreResourceWrappers(rootModule);
37
40
  for (const wrapper of wrappers) {
38
41
  const instance = wrapper.instance;
39
- const resourceDef = Reflect.getMetadata(common_2.RESOURCE_METADATA, instance.constructor);
42
+ const ctor = instance.constructor;
43
+ const metadata = Reflect.getMetadata(common_2.METADATA_KEY, ctor);
44
+ if (common_2.OpraSchema.isResource(metadata))
45
+ resources.push(instance);
46
+ }
47
+ for (const wrapper of wrappers) {
48
+ const instance = wrapper.instance;
49
+ const ctor = instance.constructor;
50
+ const resourceDef = Reflect.getMetadata(common_2.METADATA_KEY, ctor);
40
51
  /* istanbul ignore next */
41
52
  if (!resourceDef)
42
53
  continue;
@@ -44,88 +55,68 @@ let OpraApiFactory = class OpraApiFactory {
44
55
  /* Wrap resolver functions */
45
56
  const prototype = Object.getPrototypeOf(instance);
46
57
  const isRequestScoped = !wrapper.isDependencyTreeStatic();
47
- const methodsToWrap = common_2.OpraSchema.isCollectionResource(resourceDef) ? common_2.collectionMethods : [];
48
- for (const methodName of methodsToWrap) {
49
- const fn = prototype[methodName];
50
- if (typeof fn !== 'function')
51
- continue;
52
- // We add special non-operational "prepare" method to prototype.
53
- // This allows us to call Guards, Interceptors etc, before calling handler method
54
- const oldPreFn = prototype['pre_' + methodName] = noOpFunction;
55
- // Copy all metadata info
56
- Reflect.getMetadataKeys(fn).forEach(k => {
57
- const metadata = Reflect.getMetadata(k, fn);
58
- Reflect.defineMetadata(k, metadata, oldPreFn);
59
- });
60
- const preCallback = this._createContextCallback(instance, prototype, wrapper, rootModule, methodName, isRequestScoped, undefined, contextType, true);
61
- const newPreFn = instance['pre_' + methodName] = function (ctx) {
62
- switch (ctx.type) {
63
- case 'http':
64
- const http = ctx.switchToHttp();
65
- const req = http.getRequest().getInstance();
66
- const res = http.getResponse().getInstance();
67
- return preCallback(req, res, noOpFunction, ctx);
68
- default:
69
- throw new Error(`"${ctx.type}" context type is not implemented yet`);
70
- }
71
- };
72
- Object.defineProperty(newPreFn, 'name', {
73
- configurable: false,
74
- writable: false,
75
- enumerable: true,
76
- value: 'pre_' + methodName
77
- });
78
- if (!Reflect.hasMetadata(METHOD_PATCHED, fn)) {
79
- const hasParamsArgs = Reflect.hasMetadata(constants_js_1.PARAM_ARGS_METADATA, instance.constructor, methodName);
80
- const patchedFn = prototype[methodName] = function (...args) {
58
+ // const methodsToWrap = OpraSchema.isCollectionResource(resourceDef) ? collectionMethods : [];
59
+ if ((common_2.OpraSchema.isCollection(resourceDef) || common_2.OpraSchema.isSingleton(resourceDef)) && resourceDef.operations) {
60
+ for (const opr of Object.values(resourceDef.operations)) {
61
+ const { handlerName } = opr;
62
+ const fn = prototype[handlerName];
63
+ if (typeof fn !== 'function')
64
+ continue;
65
+ // NestJs requires calling handler function in different order than Opra.
66
+ // In NestJS, handler functions must be called with these parameters (req, res, next)
67
+ // In Opra, handler functions must be called with these parameters (context)
68
+ // To work handlers properly we create new handlers that will work as a proxy to wrap parameters
69
+ // Opra request (context) -> Nest (req, res, next, context: QueryRequestContext) -> Opra response (context)
70
+ const nestHandlerName = handlerName + '::nestjs';
71
+ const paramArgsMetadata = Reflect.getMetadata(constants_js_1.PARAM_ARGS_METADATA, instance.constructor, handlerName);
72
+ const hasParamsArgs = !!paramArgsMetadata;
73
+ const patchedFn = prototype[nestHandlerName] = function (...args) {
81
74
  if (hasParamsArgs)
82
75
  return fn.apply(this, args);
83
76
  return fn.call(this, args[3]);
84
77
  };
85
- Reflect.defineMetadata(METHOD_PATCHED, true, patchedFn);
78
+ if (paramArgsMetadata)
79
+ Reflect.defineMetadata(constants_js_1.PARAM_ARGS_METADATA, paramArgsMetadata, instance.constructor, nestHandlerName);
80
+ // Copy all metadata from old Function to new one
86
81
  Reflect.getMetadataKeys(fn).forEach(k => {
87
- const metadata = Reflect.getMetadata(k, fn);
88
- Reflect.defineMetadata(k, metadata, patchedFn);
82
+ const m = Reflect.getMetadata(k, fn);
83
+ Reflect.defineMetadata(k, m, patchedFn);
84
+ });
85
+ const callback = this._createContextCallback(instance, prototype, wrapper, rootModule, nestHandlerName, isRequestScoped, undefined, contextType);
86
+ opr.handler = function (ctx) {
87
+ switch (ctx.protocol) {
88
+ case 'http':
89
+ const httpContext = ctx.switchToHttp();
90
+ return callback(httpContext.request, httpContext.response, noOpFunction, ctx);
91
+ default:
92
+ throw new Error(`"${ctx.protocol}" context type is not implemented yet`);
93
+ }
94
+ };
95
+ Object.defineProperty(opr.handler, 'name', {
96
+ configurable: false,
97
+ writable: false,
98
+ enumerable: true,
99
+ value: handlerName
89
100
  });
90
101
  }
91
- const callback = this._createContextCallback(instance, prototype, wrapper, rootModule, methodName, isRequestScoped, undefined, contextType, false);
92
- const newFn = instance[methodName] = function (ctx) {
93
- switch (ctx.type) {
94
- case 'http':
95
- const http = ctx.switchToHttp();
96
- const req = http.getRequest().getInstance();
97
- const res = http.getResponse().getInstance();
98
- return callback(req, res, noOpFunction, ctx);
99
- default:
100
- throw new Error(`"${ctx.type}" context type is not implemented yet`);
101
- }
102
- };
103
- Object.defineProperty(newFn, 'name', {
104
- configurable: false,
105
- writable: false,
106
- enumerable: true,
107
- value: methodName
108
- });
109
102
  }
110
103
  }
111
- return await common_2.OpraDocument.create(serviceArgs);
104
+ // Create api document
105
+ return common_2.DocumentFactory.createDocument(apiSchema);
112
106
  }
113
- _createContextCallback(instance, prototype, wrapper, moduleRef, methodName, isRequestScoped, transform = lodash_identity_1.default, contextType, forPre) {
107
+ _createContextCallback(instance, prototype, wrapper, moduleRef, methodName, isRequestScoped, transform = lodash_identity_1.default, contextType, options) {
114
108
  const paramsFactory = this.paramsFactory;
115
- const options = !forPre ?
116
- { guards: false, interceptors: false, filters: false } : undefined;
117
- const fnName = forPre ? 'pre_' + methodName : methodName;
118
109
  if (isRequestScoped) {
119
110
  return async (...args) => {
120
111
  const opraContext = paramsFactory.exchangeKeyForValue(handler_paramtype_enum_js_1.HandlerParamType.CONTEXT, undefined, args);
121
112
  const contextId = this.getContextId(opraContext);
122
113
  this.registerContextProvider(opraContext, contextId);
123
114
  const contextInstance = await this.injector.loadPerContext(instance, moduleRef, moduleRef.providers, contextId);
124
- const callback = this.externalContextCreator.create(contextInstance, transform(contextInstance[fnName]), methodName, constants_js_1.PARAM_ARGS_METADATA, paramsFactory, contextId, wrapper.id, options, opraContext.type);
115
+ const callback = this.externalContextCreator.create(contextInstance, transform(contextInstance[methodName]), methodName, constants_js_1.PARAM_ARGS_METADATA, paramsFactory, contextId, wrapper.id, options, opraContext.protocol);
125
116
  return callback(...args);
126
117
  };
127
118
  }
128
- return this.externalContextCreator.create(instance, prototype[fnName], methodName, constants_js_1.PARAM_ARGS_METADATA, paramsFactory, undefined, undefined, options, contextType);
119
+ return this.externalContextCreator.create(instance, prototype[methodName], methodName, constants_js_1.PARAM_ARGS_METADATA, paramsFactory, undefined, undefined, options, contextType);
129
120
  }
130
121
  // noinspection JSMethodCanBeStatic
131
122
  getContextId(gqlContext) {
@@ -11,14 +11,12 @@ class OpraParamsFactory {
11
11
  switch (type) {
12
12
  case handler_paramtype_enum_js_1.HandlerParamType.CONTEXT:
13
13
  return args[3];
14
- case handler_paramtype_enum_js_1.HandlerParamType.SERVICE:
15
- return args[3].service;
16
- case handler_paramtype_enum_js_1.HandlerParamType.QUERY:
17
- return args[3].query;
14
+ case handler_paramtype_enum_js_1.HandlerParamType.API:
15
+ return args[3].api;
16
+ case handler_paramtype_enum_js_1.HandlerParamType.REQUEST:
17
+ return args[3].request;
18
18
  case handler_paramtype_enum_js_1.HandlerParamType.RESPONSE:
19
19
  return args[3].response;
20
- case handler_paramtype_enum_js_1.HandlerParamType.USER_CONTEXT:
21
- return args[3].executionContext.userContext;
22
20
  default:
23
21
  return null;
24
22
  }
@@ -28,7 +28,7 @@ class NestExplorer {
28
28
  return !!(wrapper.instance
29
29
  && typeof wrapper.instance === 'object'
30
30
  && wrapper.instance.constructor
31
- && Reflect.hasMetadata(common_1.RESOURCE_METADATA, wrapper.instance.constructor));
31
+ && common_1.OpraSchema.isResource(Reflect.getMetadata(common_1.METADATA_KEY, wrapper.instance.constructor)));
32
32
  });
33
33
  }
34
34
  }
@@ -52,8 +52,12 @@ class OpraApiLoader {
52
52
  if (!httpAdapter)
53
53
  return;
54
54
  const app = httpAdapter.getInstance();
55
- const logger = moduleOptions.logger || new common_1.Logger(service.info.title);
56
- return core_2.OpraExpressAdapter.init(app, service, {
55
+ let logger = moduleOptions.logger;
56
+ if (!logger) {
57
+ logger = new common_1.Logger(service.info.title);
58
+ logger.fatal = logger.error.bind(logger);
59
+ }
60
+ return core_2.OpraExpressAdapter.create(app, service, {
57
61
  logger,
58
62
  ...moduleOptions
59
63
  });
@@ -15,6 +15,8 @@ function assignMetadata(args, paramType, index, data, ...pipes) {
15
15
  }
16
16
  function createOpraParamDecorator(paramType) {
17
17
  return (target, key, index) => {
18
+ if (!key)
19
+ return;
18
20
  const args = Reflect.getMetadata(constants_js_1.PARAM_ARGS_METADATA, target.constructor, key) || {};
19
21
  Reflect.defineMetadata(constants_js_1.PARAM_ARGS_METADATA, assignMetadata(args, paramType, index), target.constructor, key);
20
22
  };
package/esm/constants.js CHANGED
@@ -1,4 +1,7 @@
1
- export const OPRA_MODULE_OPTIONS = 'opra:module_options';
2
- export const OPRA_MODULE_ID = 'opra:module_id';
3
- export const OPRA_INITIALIZER = 'opra_initializer';
4
- export const PARAM_ARGS_METADATA = '__routeArguments__';
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.PARAM_ARGS_METADATA = exports.OPRA_INITIALIZER = exports.OPRA_MODULE_ID = exports.OPRA_MODULE_OPTIONS = void 0;
4
+ exports.OPRA_MODULE_OPTIONS = 'opra:module_options';
5
+ exports.OPRA_MODULE_ID = 'opra:module_id';
6
+ exports.OPRA_INITIALIZER = 'opra_initializer';
7
+ exports.PARAM_ARGS_METADATA = '__routeArguments__';
@@ -1,22 +1,15 @@
1
- import { HandlerParamType } from '../enums/handler-paramtype.enum.js';
2
- import { createOpraParamDecorator } from '../utils/param.utils.js';
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.ApiDoc = exports.Context = void 0;
4
+ const handler_paramtype_enum_js_1 = require("../enums/handler-paramtype.enum.js");
5
+ const param_utils_js_1 = require("../utils/param.utils.js");
3
6
  /**
4
7
  * Handler method parameter decorator. Populates the decorated
5
8
  * parameter with the value of `RequestContext`.
6
9
  */
7
- export const Context = createOpraParamDecorator(HandlerParamType.CONTEXT);
8
- /**
9
- * Handler method parameter decorator. Populates the decorated
10
- * parameter with the value of `QueryResponse`.
11
- */
12
- export const Response = createOpraParamDecorator(HandlerParamType.RESPONSE);
13
- /**
14
- * Handler method parameter decorator. Populates the decorated
15
- * parameter with the value of `OpraService`.
16
- */
17
- export const Service = createOpraParamDecorator(HandlerParamType.SERVICE);
10
+ exports.Context = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.CONTEXT);
18
11
  /**
19
12
  * Handler method parameter decorator. Populates the decorated
20
13
  * parameter with the value of `OpraService`.
21
14
  */
22
- export const Query = createOpraParamDecorator(HandlerParamType.QUERY);
15
+ exports.ApiDoc = (0, param_utils_js_1.createOpraParamDecorator)(handler_paramtype_enum_js_1.HandlerParamType.API);
@@ -1,8 +1,10 @@
1
- export var HandlerParamType;
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.HandlerParamType = void 0;
4
+ var HandlerParamType;
2
5
  (function (HandlerParamType) {
3
6
  HandlerParamType[HandlerParamType["CONTEXT"] = 0] = "CONTEXT";
4
- HandlerParamType[HandlerParamType["SERVICE"] = 1] = "SERVICE";
5
- HandlerParamType[HandlerParamType["QUERY"] = 2] = "QUERY";
7
+ HandlerParamType[HandlerParamType["API"] = 1] = "API";
8
+ HandlerParamType[HandlerParamType["REQUEST"] = 2] = "REQUEST";
6
9
  HandlerParamType[HandlerParamType["RESPONSE"] = 3] = "RESPONSE";
7
- HandlerParamType[HandlerParamType["USER_CONTEXT"] = 4] = "USER_CONTEXT";
8
- })(HandlerParamType || (HandlerParamType = {}));
10
+ })(HandlerParamType = exports.HandlerParamType || (exports.HandlerParamType = {}));
@@ -1,39 +1,53 @@
1
- import { __decorate, __metadata } from "tslib";
2
- import head from 'lodash.head';
3
- import identity from 'lodash.identity';
4
- import { Inject, Injectable } from '@nestjs/common';
5
- import { ContextIdFactory, createContextId, ModulesContainer, REQUEST } from '@nestjs/core';
6
- import { ExternalContextCreator } from '@nestjs/core/helpers/external-context-creator';
7
- import { Injector } from '@nestjs/core/injector/injector';
8
- import { InternalCoreModule } from '@nestjs/core/injector/internal-core-module';
9
- import { REQUEST_CONTEXT_ID } from '@nestjs/core/router/request/request-constants';
10
- import { collectionMethods, OpraDocument, OpraSchema, RESOURCE_METADATA } from '@opra/common';
11
- import { PARAM_ARGS_METADATA } from '../constants.js';
12
- import { HandlerParamType } from '../enums/handler-paramtype.enum.js';
13
- import { NestExplorer } from '../services/nest-explorer.js';
14
- import { getNumberOfArguments } from '../utils/function.utils.js';
15
- import { OpraParamsFactory } from './params.factory.js';
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.OpraApiFactory = void 0;
4
+ const tslib_1 = require("tslib");
5
+ const lodash_head_1 = tslib_1.__importDefault(require("lodash.head"));
6
+ const lodash_identity_1 = tslib_1.__importDefault(require("lodash.identity"));
7
+ const common_1 = require("@nestjs/common");
8
+ const core_1 = require("@nestjs/core");
9
+ const external_context_creator_1 = require("@nestjs/core/helpers/external-context-creator");
10
+ const injector_1 = require("@nestjs/core/injector/injector");
11
+ const internal_core_module_1 = require("@nestjs/core/injector/internal-core-module");
12
+ const request_constants_1 = require("@nestjs/core/router/request/request-constants");
13
+ const common_2 = require("@opra/common");
14
+ const constants_js_1 = require("../constants.js");
15
+ const handler_paramtype_enum_js_1 = require("../enums/handler-paramtype.enum.js");
16
+ const nest_explorer_js_1 = require("../services/nest-explorer.js");
17
+ const function_utils_js_1 = require("../utils/function.utils.js");
18
+ const params_factory_js_1 = require("./params.factory.js");
16
19
  const noOpFunction = () => void 0;
17
- const METHOD_PATCHED = 'ServiceFactory.method-patched';
18
20
  let OpraApiFactory = class OpraApiFactory {
19
21
  constructor() {
20
- this.paramsFactory = new OpraParamsFactory();
21
- this.injector = new Injector();
22
+ this.paramsFactory = new params_factory_js_1.OpraParamsFactory();
23
+ this.injector = new injector_1.Injector();
22
24
  }
23
25
  async generateService(rootModule, moduleOptions, contextType) {
24
26
  const info = { title: '', version: '', ...moduleOptions.info };
25
27
  info.title = info.title || 'Untitled service';
26
28
  info.version = info.version || '1';
27
29
  const resources = [];
28
- const serviceArgs = {
30
+ const apiSchema = {
31
+ version: common_2.OpraSchema.SpecVersion,
29
32
  info,
30
33
  types: [],
31
34
  resources,
32
35
  };
36
+ /*
37
+ * Walk through modules and add Resource instances to the api schema
38
+ */
33
39
  const wrappers = this.explorerService.exploreResourceWrappers(rootModule);
34
40
  for (const wrapper of wrappers) {
35
41
  const instance = wrapper.instance;
36
- const resourceDef = Reflect.getMetadata(RESOURCE_METADATA, instance.constructor);
42
+ const ctor = instance.constructor;
43
+ const metadata = Reflect.getMetadata(common_2.METADATA_KEY, ctor);
44
+ if (common_2.OpraSchema.isResource(metadata))
45
+ resources.push(instance);
46
+ }
47
+ for (const wrapper of wrappers) {
48
+ const instance = wrapper.instance;
49
+ const ctor = instance.constructor;
50
+ const resourceDef = Reflect.getMetadata(common_2.METADATA_KEY, ctor);
37
51
  /* istanbul ignore next */
38
52
  if (!resourceDef)
39
53
  continue;
@@ -41,97 +55,77 @@ let OpraApiFactory = class OpraApiFactory {
41
55
  /* Wrap resolver functions */
42
56
  const prototype = Object.getPrototypeOf(instance);
43
57
  const isRequestScoped = !wrapper.isDependencyTreeStatic();
44
- const methodsToWrap = OpraSchema.isCollectionResource(resourceDef) ? collectionMethods : [];
45
- for (const methodName of methodsToWrap) {
46
- const fn = prototype[methodName];
47
- if (typeof fn !== 'function')
48
- continue;
49
- // We add special non-operational "prepare" method to prototype.
50
- // This allows us to call Guards, Interceptors etc, before calling handler method
51
- const oldPreFn = prototype['pre_' + methodName] = noOpFunction;
52
- // Copy all metadata info
53
- Reflect.getMetadataKeys(fn).forEach(k => {
54
- const metadata = Reflect.getMetadata(k, fn);
55
- Reflect.defineMetadata(k, metadata, oldPreFn);
56
- });
57
- const preCallback = this._createContextCallback(instance, prototype, wrapper, rootModule, methodName, isRequestScoped, undefined, contextType, true);
58
- const newPreFn = instance['pre_' + methodName] = function (ctx) {
59
- switch (ctx.type) {
60
- case 'http':
61
- const http = ctx.switchToHttp();
62
- const req = http.getRequest().getInstance();
63
- const res = http.getResponse().getInstance();
64
- return preCallback(req, res, noOpFunction, ctx);
65
- default:
66
- throw new Error(`"${ctx.type}" context type is not implemented yet`);
67
- }
68
- };
69
- Object.defineProperty(newPreFn, 'name', {
70
- configurable: false,
71
- writable: false,
72
- enumerable: true,
73
- value: 'pre_' + methodName
74
- });
75
- if (!Reflect.hasMetadata(METHOD_PATCHED, fn)) {
76
- const hasParamsArgs = Reflect.hasMetadata(PARAM_ARGS_METADATA, instance.constructor, methodName);
77
- const patchedFn = prototype[methodName] = function (...args) {
58
+ // const methodsToWrap = OpraSchema.isCollectionResource(resourceDef) ? collectionMethods : [];
59
+ if ((common_2.OpraSchema.isCollection(resourceDef) || common_2.OpraSchema.isSingleton(resourceDef)) && resourceDef.operations) {
60
+ for (const opr of Object.values(resourceDef.operations)) {
61
+ const { handlerName } = opr;
62
+ const fn = prototype[handlerName];
63
+ if (typeof fn !== 'function')
64
+ continue;
65
+ // NestJs requires calling handler function in different order than Opra.
66
+ // In NestJS, handler functions must be called with these parameters (req, res, next)
67
+ // In Opra, handler functions must be called with these parameters (context)
68
+ // To work handlers properly we create new handlers that will work as a proxy to wrap parameters
69
+ // Opra request (context) -> Nest (req, res, next, context: QueryRequestContext) -> Opra response (context)
70
+ const nestHandlerName = handlerName + '::nestjs';
71
+ const paramArgsMetadata = Reflect.getMetadata(constants_js_1.PARAM_ARGS_METADATA, instance.constructor, handlerName);
72
+ const hasParamsArgs = !!paramArgsMetadata;
73
+ const patchedFn = prototype[nestHandlerName] = function (...args) {
78
74
  if (hasParamsArgs)
79
75
  return fn.apply(this, args);
80
76
  return fn.call(this, args[3]);
81
77
  };
82
- Reflect.defineMetadata(METHOD_PATCHED, true, patchedFn);
78
+ if (paramArgsMetadata)
79
+ Reflect.defineMetadata(constants_js_1.PARAM_ARGS_METADATA, paramArgsMetadata, instance.constructor, nestHandlerName);
80
+ // Copy all metadata from old Function to new one
83
81
  Reflect.getMetadataKeys(fn).forEach(k => {
84
- const metadata = Reflect.getMetadata(k, fn);
85
- Reflect.defineMetadata(k, metadata, patchedFn);
82
+ const m = Reflect.getMetadata(k, fn);
83
+ Reflect.defineMetadata(k, m, patchedFn);
84
+ });
85
+ const callback = this._createContextCallback(instance, prototype, wrapper, rootModule, nestHandlerName, isRequestScoped, undefined, contextType);
86
+ opr.handler = function (ctx) {
87
+ switch (ctx.protocol) {
88
+ case 'http':
89
+ const httpContext = ctx.switchToHttp();
90
+ return callback(httpContext.request, httpContext.response, noOpFunction, ctx);
91
+ default:
92
+ throw new Error(`"${ctx.protocol}" context type is not implemented yet`);
93
+ }
94
+ };
95
+ Object.defineProperty(opr.handler, 'name', {
96
+ configurable: false,
97
+ writable: false,
98
+ enumerable: true,
99
+ value: handlerName
86
100
  });
87
101
  }
88
- const callback = this._createContextCallback(instance, prototype, wrapper, rootModule, methodName, isRequestScoped, undefined, contextType, false);
89
- const newFn = instance[methodName] = function (ctx) {
90
- switch (ctx.type) {
91
- case 'http':
92
- const http = ctx.switchToHttp();
93
- const req = http.getRequest().getInstance();
94
- const res = http.getResponse().getInstance();
95
- return callback(req, res, noOpFunction, ctx);
96
- default:
97
- throw new Error(`"${ctx.type}" context type is not implemented yet`);
98
- }
99
- };
100
- Object.defineProperty(newFn, 'name', {
101
- configurable: false,
102
- writable: false,
103
- enumerable: true,
104
- value: methodName
105
- });
106
102
  }
107
103
  }
108
- return await OpraDocument.create(serviceArgs);
104
+ // Create api document
105
+ return common_2.DocumentFactory.createDocument(apiSchema);
109
106
  }
110
- _createContextCallback(instance, prototype, wrapper, moduleRef, methodName, isRequestScoped, transform = identity, contextType, forPre) {
107
+ _createContextCallback(instance, prototype, wrapper, moduleRef, methodName, isRequestScoped, transform = lodash_identity_1.default, contextType, options) {
111
108
  const paramsFactory = this.paramsFactory;
112
- const options = !forPre ?
113
- { guards: false, interceptors: false, filters: false } : undefined;
114
- const fnName = forPre ? 'pre_' + methodName : methodName;
115
109
  if (isRequestScoped) {
116
110
  return async (...args) => {
117
- const opraContext = paramsFactory.exchangeKeyForValue(HandlerParamType.CONTEXT, undefined, args);
111
+ const opraContext = paramsFactory.exchangeKeyForValue(handler_paramtype_enum_js_1.HandlerParamType.CONTEXT, undefined, args);
118
112
  const contextId = this.getContextId(opraContext);
119
113
  this.registerContextProvider(opraContext, contextId);
120
114
  const contextInstance = await this.injector.loadPerContext(instance, moduleRef, moduleRef.providers, contextId);
121
- const callback = this.externalContextCreator.create(contextInstance, transform(contextInstance[fnName]), methodName, PARAM_ARGS_METADATA, paramsFactory, contextId, wrapper.id, options, opraContext.type);
115
+ const callback = this.externalContextCreator.create(contextInstance, transform(contextInstance[methodName]), methodName, constants_js_1.PARAM_ARGS_METADATA, paramsFactory, contextId, wrapper.id, options, opraContext.protocol);
122
116
  return callback(...args);
123
117
  };
124
118
  }
125
- return this.externalContextCreator.create(instance, prototype[fnName], methodName, PARAM_ARGS_METADATA, paramsFactory, undefined, undefined, options, contextType);
119
+ return this.externalContextCreator.create(instance, prototype[methodName], methodName, constants_js_1.PARAM_ARGS_METADATA, paramsFactory, undefined, undefined, options, contextType);
126
120
  }
127
121
  // noinspection JSMethodCanBeStatic
128
122
  getContextId(gqlContext) {
129
- const numberOfArguments = getNumberOfArguments(ContextIdFactory.getByRequest);
123
+ const numberOfArguments = (0, function_utils_js_1.getNumberOfArguments)(core_1.ContextIdFactory.getByRequest);
130
124
  if (numberOfArguments === 2) {
131
125
  // @ts-ignore
132
- const contextId = ContextIdFactory.getByRequest(gqlContext, ['req']);
133
- if (!gqlContext[REQUEST_CONTEXT_ID]) {
134
- Object.defineProperty(gqlContext, REQUEST_CONTEXT_ID, {
126
+ const contextId = core_1.ContextIdFactory.getByRequest(gqlContext, ['req']);
127
+ if (!gqlContext[request_constants_1.REQUEST_CONTEXT_ID]) {
128
+ Object.defineProperty(gqlContext, request_constants_1.REQUEST_CONTEXT_ID, {
135
129
  value: contextId,
136
130
  enumerable: false,
137
131
  configurable: false,
@@ -144,17 +138,17 @@ let OpraApiFactory = class OpraApiFactory {
144
138
  // TODO remove in the next version (backward-compatibility layer)
145
139
  // Left for backward compatibility purposes
146
140
  let contextId;
147
- if (gqlContext && gqlContext[REQUEST_CONTEXT_ID]) {
148
- contextId = gqlContext[REQUEST_CONTEXT_ID];
141
+ if (gqlContext && gqlContext[request_constants_1.REQUEST_CONTEXT_ID]) {
142
+ contextId = gqlContext[request_constants_1.REQUEST_CONTEXT_ID];
149
143
  }
150
144
  else if (gqlContext &&
151
145
  gqlContext.req &&
152
- gqlContext.req[REQUEST_CONTEXT_ID]) {
153
- contextId = gqlContext.req[REQUEST_CONTEXT_ID];
146
+ gqlContext.req[request_constants_1.REQUEST_CONTEXT_ID]) {
147
+ contextId = gqlContext.req[request_constants_1.REQUEST_CONTEXT_ID];
154
148
  }
155
149
  else {
156
- contextId = createContextId();
157
- Object.defineProperty(gqlContext, REQUEST_CONTEXT_ID, {
150
+ contextId = (0, core_1.createContextId)();
151
+ Object.defineProperty(gqlContext, request_constants_1.REQUEST_CONTEXT_ID, {
158
152
  value: contextId,
159
153
  enumerable: false,
160
154
  configurable: false,
@@ -168,33 +162,33 @@ let OpraApiFactory = class OpraApiFactory {
168
162
  const coreModuleArray = [...this.modulesContainer.entries()]
169
163
  .filter(
170
164
  // eslint-disable-next-line @typescript-eslint/no-unused-vars
171
- ([key, { metatype }]) => metatype && metatype.name === InternalCoreModule.name)
165
+ ([key, { metatype }]) => metatype && metatype.name === internal_core_module_1.InternalCoreModule.name)
172
166
  // eslint-disable-next-line @typescript-eslint/no-unused-vars
173
167
  .map(([key, value]) => value);
174
- const coreModuleRef = head(coreModuleArray);
168
+ const coreModuleRef = (0, lodash_head_1.default)(coreModuleArray);
175
169
  if (!coreModuleRef) {
176
170
  return;
177
171
  }
178
- const wrapper = coreModuleRef.getProviderByKey(REQUEST);
172
+ const wrapper = coreModuleRef.getProviderByKey(core_1.REQUEST);
179
173
  wrapper.setInstanceByContextId(contextId, {
180
174
  instance: request,
181
175
  isResolved: true,
182
176
  });
183
177
  }
184
178
  };
185
- __decorate([
186
- Inject(),
187
- __metadata("design:type", ModulesContainer)
179
+ tslib_1.__decorate([
180
+ (0, common_1.Inject)(),
181
+ tslib_1.__metadata("design:type", core_1.ModulesContainer)
188
182
  ], OpraApiFactory.prototype, "modulesContainer", void 0);
189
- __decorate([
190
- Inject(),
191
- __metadata("design:type", ExternalContextCreator)
183
+ tslib_1.__decorate([
184
+ (0, common_1.Inject)(),
185
+ tslib_1.__metadata("design:type", external_context_creator_1.ExternalContextCreator)
192
186
  ], OpraApiFactory.prototype, "externalContextCreator", void 0);
193
- __decorate([
194
- Inject(),
195
- __metadata("design:type", NestExplorer)
187
+ tslib_1.__decorate([
188
+ (0, common_1.Inject)(),
189
+ tslib_1.__metadata("design:type", nest_explorer_js_1.NestExplorer)
196
190
  ], OpraApiFactory.prototype, "explorerService", void 0);
197
- OpraApiFactory = __decorate([
198
- Injectable()
191
+ OpraApiFactory = tslib_1.__decorate([
192
+ (0, common_1.Injectable)()
199
193
  ], OpraApiFactory);
200
- export { OpraApiFactory };
194
+ exports.OpraApiFactory = OpraApiFactory;
@@ -1,23 +1,25 @@
1
- import { HandlerParamType } from '../enums/handler-paramtype.enum.js';
2
- export class OpraParamsFactory {
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.OpraParamsFactory = void 0;
4
+ const handler_paramtype_enum_js_1 = require("../enums/handler-paramtype.enum.js");
5
+ class OpraParamsFactory {
3
6
  exchangeKeyForValue(type, data, args) {
4
7
  if (!args) {
5
8
  return null;
6
9
  }
7
10
  args = Array.isArray(args) ? args : [];
8
11
  switch (type) {
9
- case HandlerParamType.CONTEXT:
12
+ case handler_paramtype_enum_js_1.HandlerParamType.CONTEXT:
10
13
  return args[3];
11
- case HandlerParamType.SERVICE:
12
- return args[3].service;
13
- case HandlerParamType.QUERY:
14
- return args[3].query;
15
- case HandlerParamType.RESPONSE:
14
+ case handler_paramtype_enum_js_1.HandlerParamType.API:
15
+ return args[3].api;
16
+ case handler_paramtype_enum_js_1.HandlerParamType.REQUEST:
17
+ return args[3].request;
18
+ case handler_paramtype_enum_js_1.HandlerParamType.RESPONSE:
16
19
  return args[3].response;
17
- case HandlerParamType.USER_CONTEXT:
18
- return args[3].executionContext.userContext;
19
20
  default:
20
21
  return null;
21
22
  }
22
23
  }
23
24
  }
25
+ exports.OpraParamsFactory = OpraParamsFactory;
package/esm/index.js CHANGED
@@ -1,5 +1,8 @@
1
- import 'reflect-metadata';
2
- export * from './opra.module.js';
3
- export * from './decorators/context.decorator.js';
4
- export * from './interfaces/opra-module-options.interface.js';
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ const tslib_1 = require("tslib");
4
+ require("reflect-metadata");
5
+ tslib_1.__exportStar(require("./opra.module.js"), exports);
6
+ tslib_1.__exportStar(require("./decorators/context.decorator.js"), exports);
7
+ tslib_1.__exportStar(require("./interfaces/opra-module-options.interface.js"), exports);
5
8
  // export * as Api from './decorators/api.ns.js';
@@ -1 +1,2 @@
1
- export {};
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -1,13 +1,16 @@
1
+ "use strict";
1
2
  var OpraCoreModule_1;
2
- import { __decorate, __metadata, __param } from "tslib";
3
- import * as crypto from 'crypto';
4
- import { Inject, Module } from '@nestjs/common';
5
- import { HttpAdapterHost, ModulesContainer } from '@nestjs/core';
6
- import { MetadataScanner } from '@nestjs/core/metadata-scanner';
7
- import { OPRA_INITIALIZER, OPRA_MODULE_ID, OPRA_MODULE_OPTIONS } from './constants.js';
8
- import { OpraApiFactory } from './factories/opra-api.factory.js';
9
- import { NestExplorer } from './services/nest-explorer.js';
10
- import { OpraApiLoader } from './services/opra-api-loader.js';
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.OpraCoreModule = void 0;
5
+ const tslib_1 = require("tslib");
6
+ const crypto = tslib_1.__importStar(require("crypto"));
7
+ const common_1 = require("@nestjs/common");
8
+ const core_1 = require("@nestjs/core");
9
+ const metadata_scanner_1 = require("@nestjs/core/metadata-scanner");
10
+ const constants_js_1 = require("./constants.js");
11
+ const opra_api_factory_js_1 = require("./factories/opra-api.factory.js");
12
+ const nest_explorer_js_1 = require("./services/nest-explorer.js");
13
+ const opra_api_loader_js_1 = require("./services/opra-api-loader.js");
11
14
  let OpraCoreModule = OpraCoreModule_1 = class OpraCoreModule {
12
15
  constructor(httpAdapterHost, modulesContainer, options, opraServiceLoader) {
13
16
  this.httpAdapterHost = httpAdapterHost;
@@ -22,12 +25,12 @@ let OpraCoreModule = OpraCoreModule_1 = class OpraCoreModule {
22
25
  providers: [
23
26
  ...(options.providers || []),
24
27
  {
25
- provide: OPRA_MODULE_OPTIONS,
28
+ provide: constants_js_1.OPRA_MODULE_OPTIONS,
26
29
  useValue: options,
27
30
  },
28
31
  {
29
- provide: OPRA_INITIALIZER,
30
- useClass: OpraApiLoader
32
+ provide: constants_js_1.OPRA_INITIALIZER,
33
+ useClass: opra_api_loader_js_1.OpraApiLoader
31
34
  }
32
35
  ],
33
36
  exports: [...(options.exports || [])]
@@ -40,12 +43,12 @@ let OpraCoreModule = OpraCoreModule_1 = class OpraCoreModule {
40
43
  providers: [
41
44
  ...(asyncOptions.providers || []),
42
45
  {
43
- provide: OPRA_MODULE_ID,
46
+ provide: constants_js_1.OPRA_MODULE_ID,
44
47
  useValue: crypto.randomUUID()
45
48
  },
46
49
  {
47
- provide: OPRA_INITIALIZER,
48
- useClass: OpraApiLoader
50
+ provide: constants_js_1.OPRA_INITIALIZER,
51
+ useClass: opra_api_loader_js_1.OpraApiLoader
49
52
  },
50
53
  ...this.createAsyncProviders(asyncOptions)
51
54
  ]
@@ -67,7 +70,7 @@ let OpraCoreModule = OpraCoreModule_1 = class OpraCoreModule {
67
70
  static createAsyncOptionsProvider(asyncOptions) {
68
71
  if (asyncOptions.useFactory) {
69
72
  return {
70
- provide: OPRA_MODULE_OPTIONS,
73
+ provide: constants_js_1.OPRA_MODULE_OPTIONS,
71
74
  useFactory: asyncOptions.useFactory,
72
75
  inject: asyncOptions.inject || []
73
76
  };
@@ -75,7 +78,7 @@ let OpraCoreModule = OpraCoreModule_1 = class OpraCoreModule {
75
78
  const useClass = asyncOptions.useClass || asyncOptions.useExisting;
76
79
  if (useClass) {
77
80
  return {
78
- provide: OPRA_MODULE_OPTIONS,
81
+ provide: constants_js_1.OPRA_MODULE_OPTIONS,
79
82
  useFactory: (optionsFactory) => optionsFactory.createOptions(),
80
83
  inject: [useClass]
81
84
  };
@@ -104,17 +107,17 @@ let OpraCoreModule = OpraCoreModule_1 = class OpraCoreModule {
104
107
  await this.opraServiceLoader.stop();
105
108
  }
106
109
  };
107
- OpraCoreModule = OpraCoreModule_1 = __decorate([
108
- Module({
110
+ OpraCoreModule = OpraCoreModule_1 = tslib_1.__decorate([
111
+ (0, common_1.Module)({
109
112
  providers: [
110
- OpraApiFactory,
111
- MetadataScanner,
112
- NestExplorer
113
+ opra_api_factory_js_1.OpraApiFactory,
114
+ metadata_scanner_1.MetadataScanner,
115
+ nest_explorer_js_1.NestExplorer
113
116
  ]
114
117
  }),
115
- __param(2, Inject(OPRA_MODULE_OPTIONS)),
116
- __param(3, Inject(OPRA_INITIALIZER)),
117
- __metadata("design:paramtypes", [HttpAdapterHost,
118
- ModulesContainer, Object, OpraApiLoader])
118
+ tslib_1.__param(2, (0, common_1.Inject)(constants_js_1.OPRA_MODULE_OPTIONS)),
119
+ tslib_1.__param(3, (0, common_1.Inject)(constants_js_1.OPRA_INITIALIZER)),
120
+ tslib_1.__metadata("design:paramtypes", [core_1.HttpAdapterHost,
121
+ core_1.ModulesContainer, Object, opra_api_loader_js_1.OpraApiLoader])
119
122
  ], OpraCoreModule);
120
- export { OpraCoreModule };
123
+ exports.OpraCoreModule = OpraCoreModule;
@@ -1,22 +1,25 @@
1
+ "use strict";
1
2
  var OpraModule_1;
2
- import { __decorate } from "tslib";
3
- import { Module } from '@nestjs/common';
4
- import { OpraCoreModule } from './opra-core.module.js';
3
+ Object.defineProperty(exports, "__esModule", { value: true });
4
+ exports.OpraModule = void 0;
5
+ const tslib_1 = require("tslib");
6
+ const common_1 = require("@nestjs/common");
7
+ const opra_core_module_js_1 = require("./opra-core.module.js");
5
8
  let OpraModule = OpraModule_1 = class OpraModule {
6
9
  static forRoot(options) {
7
10
  return {
8
11
  module: OpraModule_1,
9
- imports: [OpraCoreModule.forRoot(options)]
12
+ imports: [opra_core_module_js_1.OpraCoreModule.forRoot(options)]
10
13
  };
11
14
  }
12
15
  static forRootAsync(asyncOptions) {
13
16
  return {
14
17
  module: OpraModule_1,
15
- imports: [OpraCoreModule.forRootAsync(asyncOptions)]
18
+ imports: [opra_core_module_js_1.OpraCoreModule.forRootAsync(asyncOptions)]
16
19
  };
17
20
  }
18
21
  };
19
- OpraModule = OpraModule_1 = __decorate([
20
- Module({})
22
+ OpraModule = OpraModule_1 = tslib_1.__decorate([
23
+ (0, common_1.Module)({})
21
24
  ], OpraModule);
22
- export { OpraModule };
25
+ exports.OpraModule = OpraModule;
@@ -1,5 +1,8 @@
1
- import { RESOURCE_METADATA } from '@opra/common';
2
- export class NestExplorer {
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.NestExplorer = void 0;
4
+ const common_1 = require("@opra/common");
5
+ class NestExplorer {
3
6
  exploreProviders(rootModule, predicate) {
4
7
  const modules = new Set();
5
8
  const wrappers = new Set();
@@ -25,7 +28,8 @@ export class NestExplorer {
25
28
  return !!(wrapper.instance
26
29
  && typeof wrapper.instance === 'object'
27
30
  && wrapper.instance.constructor
28
- && Reflect.hasMetadata(RESOURCE_METADATA, wrapper.instance.constructor));
31
+ && common_1.OpraSchema.isResource(Reflect.getMetadata(common_1.METADATA_KEY, wrapper.instance.constructor)));
29
32
  });
30
33
  }
31
34
  }
35
+ exports.NestExplorer = NestExplorer;
@@ -1,20 +1,23 @@
1
- import { __decorate, __metadata } from "tslib";
2
- import { Inject, Logger } from '@nestjs/common';
3
- import { ApplicationConfig, HttpAdapterHost } from '@nestjs/core';
4
- import { joinPath, normalizePath } from '@opra/common';
5
- import { OpraExpressAdapter } from '@opra/core';
6
- import { OPRA_MODULE_OPTIONS } from '../constants.js';
7
- import { OpraApiFactory } from '../factories/opra-api.factory.js';
8
- export class OpraApiLoader {
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.OpraApiLoader = void 0;
4
+ const tslib_1 = require("tslib");
5
+ const common_1 = require("@nestjs/common");
6
+ const core_1 = require("@nestjs/core");
7
+ const common_2 = require("@opra/common");
8
+ const core_2 = require("@opra/core");
9
+ const constants_js_1 = require("../constants.js");
10
+ const opra_api_factory_js_1 = require("../factories/opra-api.factory.js");
11
+ class OpraApiLoader {
9
12
  constructor() {
10
- this.logger = new Logger(OpraApiLoader.name, { timestamp: true });
13
+ this.logger = new common_1.Logger(OpraApiLoader.name, { timestamp: true });
11
14
  }
12
15
  async initialize(rootModule) {
13
16
  const httpAdapter = this.httpAdapterHost?.httpAdapter;
14
17
  const globalPrefix = this.applicationConfig.getGlobalPrefix();
15
18
  const platformName = httpAdapter.getType();
16
19
  const moduleOptions = this.opraModuleOptions;
17
- const prefix = '/' + normalizePath(joinPath((moduleOptions.useGlobalPrefix !== false ? globalPrefix : ''), moduleOptions.prefix || ''), true);
20
+ const prefix = '/' + (0, common_2.normalizePath)((0, common_2.joinPath)((moduleOptions.useGlobalPrefix !== false ? globalPrefix : ''), moduleOptions.prefix || ''), true);
18
21
  const name = moduleOptions.info?.title || 'untitled service';
19
22
  const options = {
20
23
  ...moduleOptions,
@@ -49,26 +52,31 @@ export class OpraApiLoader {
49
52
  if (!httpAdapter)
50
53
  return;
51
54
  const app = httpAdapter.getInstance();
52
- const logger = moduleOptions.logger || new Logger(service.info.title);
53
- return OpraExpressAdapter.init(app, service, {
55
+ let logger = moduleOptions.logger;
56
+ if (!logger) {
57
+ logger = new common_1.Logger(service.info.title);
58
+ logger.fatal = logger.error.bind(logger);
59
+ }
60
+ return core_2.OpraExpressAdapter.create(app, service, {
54
61
  logger,
55
62
  ...moduleOptions
56
63
  });
57
64
  }
58
65
  }
59
- __decorate([
60
- Inject(),
61
- __metadata("design:type", HttpAdapterHost)
66
+ tslib_1.__decorate([
67
+ (0, common_1.Inject)(),
68
+ tslib_1.__metadata("design:type", core_1.HttpAdapterHost)
62
69
  ], OpraApiLoader.prototype, "httpAdapterHost", void 0);
63
- __decorate([
64
- Inject(),
65
- __metadata("design:type", ApplicationConfig)
70
+ tslib_1.__decorate([
71
+ (0, common_1.Inject)(),
72
+ tslib_1.__metadata("design:type", core_1.ApplicationConfig)
66
73
  ], OpraApiLoader.prototype, "applicationConfig", void 0);
67
- __decorate([
68
- Inject(),
69
- __metadata("design:type", OpraApiFactory)
74
+ tslib_1.__decorate([
75
+ (0, common_1.Inject)(),
76
+ tslib_1.__metadata("design:type", opra_api_factory_js_1.OpraApiFactory)
70
77
  ], OpraApiLoader.prototype, "opraFactory", void 0);
71
- __decorate([
72
- Inject(OPRA_MODULE_OPTIONS),
73
- __metadata("design:type", Object)
78
+ tslib_1.__decorate([
79
+ (0, common_1.Inject)(constants_js_1.OPRA_MODULE_OPTIONS),
80
+ tslib_1.__metadata("design:type", Object)
74
81
  ], OpraApiLoader.prototype, "opraModuleOptions", void 0);
82
+ exports.OpraApiLoader = OpraApiLoader;
package/esm/types.js CHANGED
@@ -1 +1,2 @@
1
- export {};
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
@@ -1,19 +1,25 @@
1
- import { isFunction, isString } from '@nestjs/common/utils/shared.utils';
2
- export function isConstructor(obj) {
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getClassName = exports.getClassOrUndefined = exports.isConstructor = void 0;
4
+ const shared_utils_1 = require("@nestjs/common/utils/shared.utils");
5
+ function isConstructor(obj) {
3
6
  return typeof obj === 'function' &&
4
7
  !!(obj.prototype && obj.prototype.constructor);
5
8
  }
6
- export function getClassOrUndefined(typeOrFunc) {
9
+ exports.isConstructor = isConstructor;
10
+ function getClassOrUndefined(typeOrFunc) {
7
11
  return isConstructor(typeOrFunc)
8
12
  ? typeOrFunc
9
- : isFunction(typeOrFunc)
13
+ : (0, shared_utils_1.isFunction)(typeOrFunc)
10
14
  ? typeOrFunc()
11
15
  : undefined;
12
16
  }
13
- export function getClassName(nameOrType) {
14
- if (isString(nameOrType)) {
17
+ exports.getClassOrUndefined = getClassOrUndefined;
18
+ function getClassName(nameOrType) {
19
+ if ((0, shared_utils_1.isString)(nameOrType)) {
15
20
  return nameOrType;
16
21
  }
17
22
  const classOrUndefined = getClassOrUndefined(nameOrType);
18
23
  return classOrUndefined && classOrUndefined.name;
19
24
  }
25
+ exports.getClassName = getClassName;
@@ -1,7 +1,10 @@
1
- import { splitString, tokenize } from 'fast-tokenizer';
2
- export function getNumberOfArguments(fn) {
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.getNumberOfArguments = void 0;
4
+ const fast_tokenizer_1 = require("fast-tokenizer");
5
+ function getNumberOfArguments(fn) {
3
6
  const functionAsString = fn.toString();
4
- const tokenizer = tokenize(functionAsString, {
7
+ const tokenizer = (0, fast_tokenizer_1.tokenize)(functionAsString, {
5
8
  // keepBrackets: true,
6
9
  keepDelimiters: true,
7
10
  keepQuotes: true,
@@ -21,7 +24,7 @@ export function getNumberOfArguments(fn) {
21
24
  else if (k)
22
25
  s += token;
23
26
  }
24
- const x = splitString(s, {
27
+ const x = (0, fast_tokenizer_1.splitString)(s, {
25
28
  brackets: {
26
29
  '{': '}',
27
30
  '(': ')',
@@ -31,3 +34,4 @@ export function getNumberOfArguments(fn) {
31
34
  });
32
35
  return x.length > 1 ? x.length : (x[0] ? 1 : 0);
33
36
  }
37
+ exports.getNumberOfArguments = getNumberOfArguments;
@@ -1,5 +1,8 @@
1
- import 'reflect-metadata';
2
- import { PARAM_ARGS_METADATA } from '../constants.js';
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.createOpraParamDecorator = void 0;
4
+ require("reflect-metadata");
5
+ const constants_js_1 = require("../constants.js");
3
6
  function assignMetadata(args, paramType, index, data, ...pipes) {
4
7
  return {
5
8
  ...args,
@@ -10,9 +13,12 @@ function assignMetadata(args, paramType, index, data, ...pipes) {
10
13
  },
11
14
  };
12
15
  }
13
- export function createOpraParamDecorator(paramType) {
16
+ function createOpraParamDecorator(paramType) {
14
17
  return (target, key, index) => {
15
- const args = Reflect.getMetadata(PARAM_ARGS_METADATA, target.constructor, key) || {};
16
- Reflect.defineMetadata(PARAM_ARGS_METADATA, assignMetadata(args, paramType, index), target.constructor, key);
18
+ if (!key)
19
+ return;
20
+ const args = Reflect.getMetadata(constants_js_1.PARAM_ARGS_METADATA, target.constructor, key) || {};
21
+ Reflect.defineMetadata(constants_js_1.PARAM_ARGS_METADATA, assignMetadata(args, paramType, index), target.constructor, key);
17
22
  };
18
23
  }
24
+ exports.createOpraParamDecorator = createOpraParamDecorator;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@opra/nestjs",
3
- "version": "0.14.0",
3
+ "version": "0.16.0",
4
4
  "description": "Opra NestJS module",
5
5
  "author": "Panates",
6
6
  "license": "MIT",
@@ -17,32 +17,32 @@
17
17
  "build:esm": "tsc -b tsconfig-build-esm.json",
18
18
  "postbuild": "cp README.md package.json ../../LICENSE ../../build/nestjs && cp ../../package.cjs.json ../../build/nestjs/cjs/package.json",
19
19
  "lint": "eslint .",
20
- "test": "NODE_OPTIONS=--experimental-vm-modules npx jest",
21
- "cover": "NODE_OPTIONS=--experimental-vm-modules npx jest --collect-coverage",
20
+ "test": "jest",
21
+ "cover": "jest --collect-coverage",
22
22
  "clean": "npm run clean:src && npm run clean:dist && npm run clean:cover",
23
23
  "clean:src": "ts-cleanup -s src --all && ts-cleanup -s test --all",
24
24
  "clean:dist": "rimraf ../../build/nestjs",
25
25
  "clean:cover": "rimraf ../../coverage/nestjs"
26
26
  },
27
27
  "dependencies": {
28
- "@opra/common": "^0.14.0",
29
- "@opra/core": "^0.14.0",
30
- "fast-tokenizer": "^1.2.1",
28
+ "@opra/common": "^0.16.0",
29
+ "@opra/core": "^0.16.0",
30
+ "fast-tokenizer": "^1.2.2",
31
31
  "lodash.head": "^4.0.1",
32
32
  "lodash.identity": "^3.0.0",
33
33
  "reflect-metadata": "^0.1.13"
34
34
  },
35
35
  "peerDependencies": {
36
- "@nestjs/common": "^9.2.1"
36
+ "@nestjs/common": "^9.4.0"
37
37
  },
38
38
  "devDependencies": {
39
- "@nestjs/platform-express": "^9.2.1",
40
- "@nestjs/testing": "^9.2.1",
41
- "@types/lodash": "^4.14.191",
39
+ "@nestjs/platform-express": "^9.4.0",
40
+ "@nestjs/testing": "^9.4.0",
41
+ "@types/lodash": "^4.14.194",
42
42
  "filedirname": "^2.7.0"
43
43
  },
44
44
  "type": "module",
45
- "types": "esm/index.d.ts",
45
+ "types": "types/index.d.ts",
46
46
  "exports": {
47
47
  ".": {
48
48
  "require": "./cjs/index.js",
@@ -59,6 +59,7 @@
59
59
  "bin/",
60
60
  "cjs/",
61
61
  "esm/",
62
+ "types/",
62
63
  "LICENSE",
63
64
  "README.md"
64
65
  ],
@@ -0,0 +1,10 @@
1
+ /**
2
+ * Handler method parameter decorator. Populates the decorated
3
+ * parameter with the value of `RequestContext`.
4
+ */
5
+ export declare const Context: ParameterDecorator;
6
+ /**
7
+ * Handler method parameter decorator. Populates the decorated
8
+ * parameter with the value of `OpraService`.
9
+ */
10
+ export declare const ApiDoc: ParameterDecorator;
@@ -0,0 +1,6 @@
1
+ export declare enum HandlerParamType {
2
+ CONTEXT = 0,
3
+ API = 1,
4
+ REQUEST = 2,
5
+ RESPONSE = 3
6
+ }
@@ -1,6 +1,6 @@
1
1
  import { ContextType } from '@nestjs/common';
2
2
  import { Module } from '@nestjs/core/injector/module.js';
3
- import { OpraDocument } from '@opra/common';
3
+ import { ApiDocument } from '@opra/common';
4
4
  import { OpraModuleOptions } from '../interfaces/opra-module-options.interface.js';
5
5
  export declare class OpraApiFactory {
6
6
  private readonly paramsFactory;
@@ -8,7 +8,7 @@ export declare class OpraApiFactory {
8
8
  private readonly modulesContainer;
9
9
  private readonly externalContextCreator;
10
10
  private readonly explorerService;
11
- generateService(rootModule: Module, moduleOptions: OpraModuleOptions, contextType: ContextType): Promise<OpraDocument>;
11
+ generateService(rootModule: Module, moduleOptions: OpraModuleOptions, contextType: ContextType): Promise<ApiDocument>;
12
12
  private _createContextCallback;
13
13
  private getContextId;
14
14
  private registerContextProvider;
@@ -1,6 +1,6 @@
1
1
  import { ApplicationConfig, HttpAdapterHost } from '@nestjs/core';
2
2
  import { Module } from '@nestjs/core/injector/module.js';
3
- import { OpraDocument } from '@opra/common';
3
+ import { ApiDocument } from '@opra/common';
4
4
  import { OpraExpressAdapter } from '@opra/core';
5
5
  import { OpraApiFactory } from '../factories/opra-api.factory.js';
6
6
  import { OpraModuleOptions } from '../interfaces/opra-module-options.interface.js';
@@ -13,5 +13,5 @@ export declare class OpraApiLoader {
13
13
  protected readonly opraModuleOptions: OpraModuleOptions;
14
14
  initialize(rootModule: Module): Promise<void>;
15
15
  stop(): Promise<void>;
16
- protected registerExpress(service: OpraDocument, moduleOptions: OpraModuleOptions): Promise<OpraExpressAdapter | undefined>;
16
+ protected registerExpress(service: ApiDocument, moduleOptions: OpraModuleOptions): Promise<OpraExpressAdapter | undefined>;
17
17
  }
@@ -1,20 +0,0 @@
1
- /**
2
- * Handler method parameter decorator. Populates the decorated
3
- * parameter with the value of `RequestContext`.
4
- */
5
- export declare const Context: ParameterDecorator;
6
- /**
7
- * Handler method parameter decorator. Populates the decorated
8
- * parameter with the value of `QueryResponse`.
9
- */
10
- export declare const Response: ParameterDecorator;
11
- /**
12
- * Handler method parameter decorator. Populates the decorated
13
- * parameter with the value of `OpraService`.
14
- */
15
- export declare const Service: ParameterDecorator;
16
- /**
17
- * Handler method parameter decorator. Populates the decorated
18
- * parameter with the value of `OpraService`.
19
- */
20
- export declare const Query: ParameterDecorator;
@@ -1,7 +0,0 @@
1
- export declare enum HandlerParamType {
2
- CONTEXT = 0,
3
- SERVICE = 1,
4
- QUERY = 2,
5
- RESPONSE = 3,
6
- USER_CONTEXT = 4
7
- }
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes
File without changes