@tsed/di 6.80.1 → 6.84.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.
@@ -2,6 +2,7 @@ export * from "./scope";
2
2
  export * from "./service";
3
3
  export * from "./overrideProvider";
4
4
  export * from "./inject";
5
+ export * from "./lazyInject";
5
6
  export * from "./injectable";
6
7
  export * from "./constant";
7
8
  export * from "./value";
@@ -1,3 +1,5 @@
1
+ import type { InjectablePropertyOptions } from "../interfaces/InjectableProperties";
2
+ export declare function injectProperty(target: any, propertyKey: string, options: Partial<InjectablePropertyOptions>): void;
1
3
  /**
2
4
  * Inject a provider to another provider.
3
5
  *
@@ -0,0 +1,53 @@
1
+ /**
2
+ * Lazy load a provider from his package and invoke only when the provider is used
3
+ *
4
+ * ```typescript
5
+ * import type {PlatformException} from "@tsed/platform-exceptions";
6
+ *
7
+ * @Injectable()
8
+ * export class MyService {
9
+ * @LazyInject("@tsed/platform-exceptions") // work if the module have a class exported with "default"
10
+ * exceptions: Promise<PlatformException>;
11
+ * }
12
+ *
13
+ * @Injectable()
14
+ * export class MyService {
15
+ * @LazyInject(() => import("@tsed/platform-exceptions")) // use this notation is you use webpack
16
+ * exceptions: Promise<PlatformException>;
17
+ * }
18
+ *
19
+ * @Injectable()
20
+ * export class MyService {
21
+ * @LazyInject(async () => (await import("@tsed/platform-exceptions")).PlatformException)
22
+ * exceptions: Promise<PlatformException>;
23
+ * }
24
+ * ```
25
+ *
26
+ * @param packageName
27
+ * @param resolver
28
+ * @param optional
29
+ * @returns {Function}
30
+ * @decorator
31
+ */
32
+ export declare function LazyInject(resolver: () => any, optional?: boolean): PropertyDecorator;
33
+ export declare function LazyInject(packageName: string, optional?: boolean): PropertyDecorator;
34
+ /**
35
+ * Optionally Lazy load a provider from his package and invoke only when the provider is used
36
+ *
37
+ * ```typescript
38
+ * import type {PlatformException} from "@tsed/platform-exceptions";
39
+ *
40
+ * @Injectable()
41
+ * export class MyService {
42
+ * @OptionalLazyInject("@tsed/platform-exceptions")
43
+ * exceptions: Promise<PlatformException>;
44
+ * }
45
+ * ```
46
+ *
47
+ * @param packageName
48
+ * @param resolver
49
+ * @returns {Function}
50
+ * @decorator
51
+ */
52
+ export declare function OptionalLazyInject(resolver: () => any): PropertyDecorator;
53
+ export declare function OptionalLazyInject(packageName: string): PropertyDecorator;
package/lib/index.js CHANGED
@@ -2,11 +2,26 @@ var core = require('@tsed/core');
2
2
  var logger = require('@tsed/logger');
3
3
  var schema = require('@tsed/schema');
4
4
  var tslib = require('tslib');
5
- var chalk = require('chalk');
6
5
 
7
- function _interopDefaultLegacy (e) { return e && typeof e === 'object' && 'default' in e ? e : { 'default': e }; }
8
-
9
- var chalk__default = /*#__PURE__*/_interopDefaultLegacy(chalk);
6
+ function _interopNamespace(e) {
7
+ if (e && e.__esModule) return e;
8
+ var n = Object.create(null);
9
+ if (e) {
10
+ Object.keys(e).forEach(function (k) {
11
+ if (k !== 'default') {
12
+ var d = Object.getOwnPropertyDescriptor(e, k);
13
+ Object.defineProperty(n, k, d.get ? d : {
14
+ enumerable: true,
15
+ get: function () {
16
+ return e[k];
17
+ }
18
+ });
19
+ }
20
+ });
21
+ }
22
+ n['default'] = e;
23
+ return n;
24
+ }
10
25
 
11
26
  const INJECTABLE_PROP = "DI:INJECTABLE_PROP";
12
27
  const DI_PARAMS = "DI:PARAMS";
@@ -631,7 +646,7 @@ class ContextLogger {
631
646
 
632
647
  }
633
648
 
634
- const _excluded$2 = ["id", "injector", "logger", "ignoreLog"];
649
+ const _excluded$3 = ["id", "injector", "logger", "ignoreLog"];
635
650
  class DIContext extends Map {
636
651
  constructor(_ref) {
637
652
  let {
@@ -640,7 +655,7 @@ class DIContext extends Map {
640
655
  logger,
641
656
  ignoreLog
642
657
  } = _ref,
643
- options = _objectWithoutPropertiesLoose(_ref, _excluded$2);
658
+ options = _objectWithoutPropertiesLoose(_ref, _excluded$3);
644
659
 
645
660
  super();
646
661
  /**
@@ -901,6 +916,15 @@ function OverrideProvider(originalProvider) {
901
916
  };
902
917
  }
903
918
 
919
+ const _excluded$2 = ["options"];
920
+ function injectProperty(target, propertyKey, options) {
921
+ core.Store.from(target).merge(INJECTABLE_PROP, {
922
+ [propertyKey]: _extends({
923
+ bindingType: core.DecoratorTypes.PROP,
924
+ propertyKey
925
+ }, options)
926
+ });
927
+ }
904
928
  /**
905
929
  * Inject a provider to another provider.
906
930
  *
@@ -920,7 +944,7 @@ function OverrideProvider(originalProvider) {
920
944
  * @decorator
921
945
  */
922
946
 
923
- function Inject(symbol, onGet) {
947
+ function Inject(symbol, onGet = bean => bean) {
924
948
  return (target, propertyKey, descriptor) => {
925
949
  const bindingType = core.decoratorTypeOf([target, propertyKey, descriptor]);
926
950
 
@@ -936,13 +960,31 @@ function Inject(symbol, onGet) {
936
960
  break;
937
961
 
938
962
  case core.DecoratorTypes.PROP:
939
- core.Store.from(target).merge(INJECTABLE_PROP, {
940
- [propertyKey]: {
941
- bindingType,
942
- propertyKey,
943
- onGet,
944
- useType: symbol || core.Metadata.getType(target, propertyKey)
963
+ injectProperty(target, propertyKey, {
964
+ resolver(injector, locals, _ref) {
965
+ let {
966
+ options
967
+ } = _ref,
968
+ invokeOptions = _objectWithoutPropertiesLoose(_ref, _excluded$2);
969
+
970
+ locals.set(DI_PARAM_OPTIONS, _extends({}, options));
971
+ let bean;
972
+
973
+ if (!bean) {
974
+ const useType = symbol || core.Metadata.getType(target, propertyKey);
975
+ bean = injector.invoke(useType, locals, invokeOptions);
976
+ locals.delete(DI_PARAM_OPTIONS);
977
+ }
978
+
979
+ if (core.isPromise(bean)) {
980
+ bean.then(result => {
981
+ bean = result;
982
+ });
983
+ }
984
+
985
+ return () => onGet(bean);
945
986
  }
987
+
946
988
  });
947
989
  break;
948
990
 
@@ -961,6 +1003,67 @@ function Inject(symbol, onGet) {
961
1003
  };
962
1004
  }
963
1005
 
1006
+ function mapOptions$1(args) {
1007
+ const options = args.reduce((options, item) => {
1008
+ if (core.isString(item)) {
1009
+ options.packageName = item;
1010
+ } else if (core.isFunction(item)) {
1011
+ options.resolver = item;
1012
+ } else if (core.isBoolean(item)) {
1013
+ options.optional = item;
1014
+ }
1015
+
1016
+ return options;
1017
+ }, {
1018
+ optional: false
1019
+ });
1020
+
1021
+ if (!options.packageName && options.resolver) {
1022
+ options.packageName = options.resolver.toString();
1023
+ }
1024
+
1025
+ if (!options.resolver) {
1026
+ options.resolver = () => Promise.resolve().then(function () { return /*#__PURE__*/_interopNamespace(require(options.packageName)); });
1027
+ }
1028
+
1029
+ return options;
1030
+ }
1031
+
1032
+ function LazyInject(...args) {
1033
+ const {
1034
+ packageName,
1035
+ resolver,
1036
+ optional
1037
+ } = mapOptions$1(args);
1038
+ return (target, propertyKey) => {
1039
+ let bean, token;
1040
+ injectProperty(target, propertyKey, {
1041
+ resolver(injector) {
1042
+ return async () => {
1043
+ if (!token) {
1044
+ var _token;
1045
+
1046
+ token = await core.importPackage(packageName, resolver, optional);
1047
+ token = ((_token = token) == null ? void 0 : _token.default) || token;
1048
+
1049
+ if (token && core.classOf(token) === Object && !optional) {
1050
+ throw new Error(`Unable to lazy load the "${packageName}". Resolved token isn\'t a valid provider.`);
1051
+ }
1052
+
1053
+ bean = await injector.lazyInvoke(token);
1054
+ }
1055
+
1056
+ return bean;
1057
+ };
1058
+ }
1059
+
1060
+ });
1061
+ };
1062
+ }
1063
+ function OptionalLazyInject(arg) {
1064
+ return LazyInject(arg, true);
1065
+ }
1066
+
964
1067
  /**
965
1068
  * Return value from Configuration.
966
1069
  *
@@ -1313,6 +1416,9 @@ function Controller(options) {
1313
1416
  }, path && schema.Path(path), schema.Children(...children));
1314
1417
  }
1315
1418
 
1419
+ const colorIfAllowed = colorFn => text => !process.env.NO_COLOR ? colorFn(text) : text;
1420
+
1421
+ const red = colorIfAllowed(text => `\x1B[31m${text}\x1B[39m`);
1316
1422
  class InjectionError extends Error {
1317
1423
  constructor(token, origin) {
1318
1424
  super(core.isString(origin) ? origin : "");
@@ -1359,7 +1465,7 @@ function printDependencyInjectionError(token, options) {
1359
1465
  const args = core.getConstructorArgNames(token).map((arg, index) => {
1360
1466
  if (options.index === index) {
1361
1467
  erroredArg = arg;
1362
- arg = chalk__default['default'].red(arg);
1468
+ arg = red(arg);
1363
1469
  }
1364
1470
 
1365
1471
  return `${arg}: ${core.nameOf(options.deps[index])}`;
@@ -1367,7 +1473,7 @@ function printDependencyInjectionError(token, options) {
1367
1473
  const signature = core.nameOf(token) + "->constructor(" + args + ")";
1368
1474
  const indexOf = signature.indexOf(erroredArg) - 5;
1369
1475
 
1370
- const drawline = indexOf => " ".repeat(indexOf) + chalk__default['default'].red("^" + "‾".repeat(erroredArg.length - 1));
1476
+ const drawline = indexOf => " ".repeat(indexOf) + red("^" + "‾".repeat(erroredArg.length - 1));
1371
1477
 
1372
1478
  return "Unable to inject dependency. " + options.message + "\n\n" + signature + "\n" + (indexOf > -1 ? drawline(indexOf) : "");
1373
1479
  }
@@ -1635,9 +1741,7 @@ exports.InjectorService = InjectorService_1 = class InjectorService extends Cont
1635
1741
 
1636
1742
 
1637
1743
  get(token, options = {}) {
1638
- var _super$get;
1639
-
1640
- const instance = (_super$get = super.get(core.getClassOrSymbol(token))) == null ? void 0 : _super$get.instance;
1744
+ const instance = this.getInstance(token);
1641
1745
 
1642
1746
  if (instance !== undefined) {
1643
1747
  return instance;
@@ -1894,7 +1998,7 @@ exports.InjectorService = InjectorService_1 = class InjectorService extends Cont
1894
1998
  * @param instance
1895
1999
  * @param {string} propertyKey
1896
2000
  * @param {any} useType
1897
- * @param onGet
2001
+ * @param resolver
1898
2002
  * @param options
1899
2003
  * @param locals
1900
2004
  * @param invokeOptions
@@ -1903,23 +2007,15 @@ exports.InjectorService = InjectorService_1 = class InjectorService extends Cont
1903
2007
 
1904
2008
  bindProperty(instance, {
1905
2009
  propertyKey,
1906
- useType,
1907
- onGet = f => f,
1908
- options
2010
+ resolver,
2011
+ options = {}
1909
2012
  }, locals, invokeOptions) {
1910
- invokeOptions = _extends({}, invokeOptions);
1911
- locals.set(DI_PARAM_OPTIONS, _extends({}, options));
1912
- let bean = this.invoke(useType, locals, invokeOptions);
1913
- locals.delete(DI_PARAM_OPTIONS);
1914
-
1915
- if (core.isPromise(bean)) {
1916
- bean.then(result => {
1917
- bean = result;
1918
- });
1919
- }
1920
-
2013
+ let get;
2014
+ get = resolver(this, locals, _extends({}, invokeOptions, {
2015
+ options
2016
+ }));
1921
2017
  core.catchError(() => Object.defineProperty(instance, propertyKey, {
1922
- get: () => onGet(bean)
2018
+ get
1923
2019
  }));
1924
2020
  }
1925
2021
  /**
@@ -2026,6 +2122,22 @@ exports.InjectorService = InjectorService_1 = class InjectorService extends Cont
2026
2122
  return cb();
2027
2123
  }
2028
2124
 
2125
+ async lazyInvoke(token) {
2126
+ let instance = this.getInstance(token);
2127
+
2128
+ if (!instance) {
2129
+ var _instance;
2130
+
2131
+ instance = await this.invoke(token);
2132
+
2133
+ if (core.isFunction((_instance = instance) == null ? void 0 : _instance.$onInit)) {
2134
+ await instance.$onInit();
2135
+ }
2136
+ }
2137
+
2138
+ return instance;
2139
+ }
2140
+
2029
2141
  ensureProvider(token) {
2030
2142
  if (!this.hasProvider(token) && GlobalProviders.has(token)) {
2031
2143
  this.addProvider(token);
@@ -2033,6 +2145,12 @@ exports.InjectorService = InjectorService_1 = class InjectorService extends Cont
2033
2145
 
2034
2146
  return this.getProvider(token);
2035
2147
  }
2148
+
2149
+ getInstance(token) {
2150
+ var _super$get;
2151
+
2152
+ return (_super$get = super.get(core.getClassOrSymbol(token))) == null ? void 0 : _super$get.instance;
2153
+ }
2036
2154
  /**
2037
2155
  * Invoke a class method and inject service.
2038
2156
  *
@@ -2339,8 +2457,10 @@ exports.Injectable = Injectable;
2339
2457
  exports.InjectionError = InjectionError;
2340
2458
  exports.Intercept = Intercept;
2341
2459
  exports.Interceptor = Interceptor;
2460
+ exports.LazyInject = LazyInject;
2342
2461
  exports.LocalsContainer = LocalsContainer;
2343
2462
  exports.Module = Module;
2463
+ exports.OptionalLazyInject = OptionalLazyInject;
2344
2464
  exports.Opts = Opts;
2345
2465
  exports.OverrideProvider = OverrideProvider;
2346
2466
  exports.Provider = Provider;
@@ -2351,6 +2471,7 @@ exports.UseOpts = UseOpts;
2351
2471
  exports.Value = Value;
2352
2472
  exports.createContainer = createContainer;
2353
2473
  exports.getConfiguration = getConfiguration;
2474
+ exports.injectProperty = injectProperty;
2354
2475
  exports.registerController = registerController;
2355
2476
  exports.registerFactory = registerFactory;
2356
2477
  exports.registerProvider = registerProvider;