first commit

This commit is contained in:
Stefan Hacker
2026-04-03 09:38:48 +02:00
commit 37ad745546
47450 changed files with 3120798 additions and 0 deletions
+46
View File
@@ -0,0 +1,46 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const reflection_helpers_1 = require("../reflection-helpers");
const dependency_container_1 = require("../dependency-container");
const injection_token_1 = require("../providers/injection-token");
const error_helpers_1 = require("../error-helpers");
function autoInjectable() {
return function (target) {
const paramInfo = reflection_helpers_1.getParamInfo(target);
return class extends target {
constructor(...args) {
super(...args.concat(paramInfo.slice(args.length).map((type, index) => {
try {
if (injection_token_1.isTokenDescriptor(type)) {
if (injection_token_1.isTransformDescriptor(type)) {
return type.multiple
? dependency_container_1.instance
.resolve(type.transform)
.transform(dependency_container_1.instance.resolveAll(type.token), ...type.transformArgs)
: dependency_container_1.instance
.resolve(type.transform)
.transform(dependency_container_1.instance.resolve(type.token), ...type.transformArgs);
}
else {
return type.multiple
? dependency_container_1.instance.resolveAll(type.token)
: dependency_container_1.instance.resolve(type.token);
}
}
else if (injection_token_1.isTransformDescriptor(type)) {
return dependency_container_1.instance
.resolve(type.transform)
.transform(dependency_container_1.instance.resolve(type.token), ...type.transformArgs);
}
return dependency_container_1.instance.resolve(type);
}
catch (e) {
const argIndex = index + args.length;
throw new Error(error_helpers_1.formatErrorCtor(target, argIndex, e));
}
})));
}
};
};
}
exports.default = autoInjectable;
+20
View File
@@ -0,0 +1,20 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var auto_injectable_1 = require("./auto-injectable");
Object.defineProperty(exports, "autoInjectable", { enumerable: true, get: function () { return auto_injectable_1.default; } });
var inject_1 = require("./inject");
Object.defineProperty(exports, "inject", { enumerable: true, get: function () { return inject_1.default; } });
var injectable_1 = require("./injectable");
Object.defineProperty(exports, "injectable", { enumerable: true, get: function () { return injectable_1.default; } });
var registry_1 = require("./registry");
Object.defineProperty(exports, "registry", { enumerable: true, get: function () { return registry_1.default; } });
var singleton_1 = require("./singleton");
Object.defineProperty(exports, "singleton", { enumerable: true, get: function () { return singleton_1.default; } });
var inject_all_1 = require("./inject-all");
Object.defineProperty(exports, "injectAll", { enumerable: true, get: function () { return inject_all_1.default; } });
var inject_all_with_transform_1 = require("./inject-all-with-transform");
Object.defineProperty(exports, "injectAllWithTransform", { enumerable: true, get: function () { return inject_all_with_transform_1.default; } });
var inject_with_transform_1 = require("./inject-with-transform");
Object.defineProperty(exports, "injectWithTransform", { enumerable: true, get: function () { return inject_with_transform_1.default; } });
var scoped_1 = require("./scoped");
Object.defineProperty(exports, "scoped", { enumerable: true, get: function () { return scoped_1.default; } });
+13
View File
@@ -0,0 +1,13 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const reflection_helpers_1 = require("../reflection-helpers");
function injectAllWithTransform(token, transformer, ...args) {
const data = {
token,
multiple: true,
transform: transformer,
transformArgs: args
};
return reflection_helpers_1.defineInjectionTokenMetadata(data);
}
exports.default = injectAllWithTransform;
+12
View File
@@ -0,0 +1,12 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const reflection_helpers_1 = require("../reflection-helpers");
function injectAll(token, options) {
const data = {
token,
multiple: true,
isOptional: options && options.isOptional
};
return reflection_helpers_1.defineInjectionTokenMetadata(data);
}
exports.default = injectAll;
+10
View File
@@ -0,0 +1,10 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const reflection_helpers_1 = require("../reflection-helpers");
function injectWithTransform(token, transformer, ...args) {
return reflection_helpers_1.defineInjectionTokenMetadata(token, {
transformToken: transformer,
args: args
});
}
exports.default = injectWithTransform;
+12
View File
@@ -0,0 +1,12 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const reflection_helpers_1 = require("../reflection-helpers");
function inject(token, options) {
const data = {
token,
multiple: false,
isOptional: options && options.isOptional
};
return reflection_helpers_1.defineInjectionTokenMetadata(data);
}
exports.default = inject;
+21
View File
@@ -0,0 +1,21 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const reflection_helpers_1 = require("../reflection-helpers");
const dependency_container_1 = require("../dependency-container");
const dependency_container_2 = require("../dependency-container");
function injectable(options) {
return function (target) {
dependency_container_1.typeInfo.set(target, reflection_helpers_1.getParamInfo(target));
if (options && options.token) {
if (!Array.isArray(options.token)) {
dependency_container_2.instance.register(options.token, target);
}
else {
options.token.forEach(token => {
dependency_container_2.instance.register(token, target);
});
}
}
};
}
exports.default = injectable;
+14
View File
@@ -0,0 +1,14 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const tslib_1 = require("tslib");
const dependency_container_1 = require("../dependency-container");
function registry(registrations = []) {
return function (target) {
registrations.forEach((_a) => {
var { token, options } = _a, provider = tslib_1.__rest(_a, ["token", "options"]);
return dependency_container_1.instance.register(token, provider, options);
});
return target;
};
}
exports.default = registry;
+13
View File
@@ -0,0 +1,13 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const injectable_1 = require("./injectable");
const dependency_container_1 = require("../dependency-container");
function scoped(lifecycle, token) {
return function (target) {
injectable_1.default()(target);
dependency_container_1.instance.register(token || target, target, {
lifecycle
});
};
}
exports.default = scoped;
+11
View File
@@ -0,0 +1,11 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const injectable_1 = require("./injectable");
const dependency_container_1 = require("../dependency-container");
function singleton() {
return function (target) {
injectable_1.default()(target);
dependency_container_1.instance.registerSingleton(target);
};
}
exports.default = singleton;
+341
View File
@@ -0,0 +1,341 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.instance = exports.typeInfo = void 0;
const tslib_1 = require("tslib");
const providers_1 = require("./providers");
const provider_1 = require("./providers/provider");
const injection_token_1 = require("./providers/injection-token");
const registry_1 = require("./registry");
const lifecycle_1 = require("./types/lifecycle");
const resolution_context_1 = require("./resolution-context");
const error_helpers_1 = require("./error-helpers");
const lazy_helpers_1 = require("./lazy-helpers");
const disposable_1 = require("./types/disposable");
const interceptors_1 = require("./interceptors");
exports.typeInfo = new Map();
class InternalDependencyContainer {
constructor(parent) {
this.parent = parent;
this._registry = new registry_1.default();
this.interceptors = new interceptors_1.default();
this.disposed = false;
this.disposables = new Set();
}
register(token, providerOrConstructor, options = { lifecycle: lifecycle_1.default.Transient }) {
this.ensureNotDisposed();
let provider;
if (!provider_1.isProvider(providerOrConstructor)) {
provider = { useClass: providerOrConstructor };
}
else {
provider = providerOrConstructor;
}
if (providers_1.isTokenProvider(provider)) {
const path = [token];
let tokenProvider = provider;
while (tokenProvider != null) {
const currentToken = tokenProvider.useToken;
if (path.includes(currentToken)) {
throw new Error(`Token registration cycle detected! ${[...path, currentToken].join(" -> ")}`);
}
path.push(currentToken);
const registration = this._registry.get(currentToken);
if (registration && providers_1.isTokenProvider(registration.provider)) {
tokenProvider = registration.provider;
}
else {
tokenProvider = null;
}
}
}
if (options.lifecycle === lifecycle_1.default.Singleton ||
options.lifecycle == lifecycle_1.default.ContainerScoped ||
options.lifecycle == lifecycle_1.default.ResolutionScoped) {
if (providers_1.isValueProvider(provider) || providers_1.isFactoryProvider(provider)) {
throw new Error(`Cannot use lifecycle "${lifecycle_1.default[options.lifecycle]}" with ValueProviders or FactoryProviders`);
}
}
this._registry.set(token, { provider, options });
return this;
}
registerType(from, to) {
this.ensureNotDisposed();
if (providers_1.isNormalToken(to)) {
return this.register(from, {
useToken: to
});
}
return this.register(from, {
useClass: to
});
}
registerInstance(token, instance) {
this.ensureNotDisposed();
return this.register(token, {
useValue: instance
});
}
registerSingleton(from, to) {
this.ensureNotDisposed();
if (providers_1.isNormalToken(from)) {
if (providers_1.isNormalToken(to)) {
return this.register(from, {
useToken: to
}, { lifecycle: lifecycle_1.default.Singleton });
}
else if (to) {
return this.register(from, {
useClass: to
}, { lifecycle: lifecycle_1.default.Singleton });
}
throw new Error('Cannot register a type name as a singleton without a "to" token');
}
let useClass = from;
if (to && !providers_1.isNormalToken(to)) {
useClass = to;
}
return this.register(from, {
useClass
}, { lifecycle: lifecycle_1.default.Singleton });
}
resolve(token, context = new resolution_context_1.default(), isOptional = false) {
this.ensureNotDisposed();
const registration = this.getRegistration(token);
if (!registration && providers_1.isNormalToken(token)) {
if (isOptional) {
return undefined;
}
throw new Error(`Attempted to resolve unregistered dependency token: "${token.toString()}"`);
}
this.executePreResolutionInterceptor(token, "Single");
if (registration) {
const result = this.resolveRegistration(registration, context);
this.executePostResolutionInterceptor(token, result, "Single");
return result;
}
if (injection_token_1.isConstructorToken(token)) {
const result = this.construct(token, context);
this.executePostResolutionInterceptor(token, result, "Single");
return result;
}
throw new Error("Attempted to construct an undefined constructor. Could mean a circular dependency problem. Try using `delay` function.");
}
executePreResolutionInterceptor(token, resolutionType) {
if (this.interceptors.preResolution.has(token)) {
const remainingInterceptors = [];
for (const interceptor of this.interceptors.preResolution.getAll(token)) {
if (interceptor.options.frequency != "Once") {
remainingInterceptors.push(interceptor);
}
interceptor.callback(token, resolutionType);
}
this.interceptors.preResolution.setAll(token, remainingInterceptors);
}
}
executePostResolutionInterceptor(token, result, resolutionType) {
if (this.interceptors.postResolution.has(token)) {
const remainingInterceptors = [];
for (const interceptor of this.interceptors.postResolution.getAll(token)) {
if (interceptor.options.frequency != "Once") {
remainingInterceptors.push(interceptor);
}
interceptor.callback(token, result, resolutionType);
}
this.interceptors.postResolution.setAll(token, remainingInterceptors);
}
}
resolveRegistration(registration, context) {
this.ensureNotDisposed();
if (registration.options.lifecycle === lifecycle_1.default.ResolutionScoped &&
context.scopedResolutions.has(registration)) {
return context.scopedResolutions.get(registration);
}
const isSingleton = registration.options.lifecycle === lifecycle_1.default.Singleton;
const isContainerScoped = registration.options.lifecycle === lifecycle_1.default.ContainerScoped;
const returnInstance = isSingleton || isContainerScoped;
let resolved;
if (providers_1.isValueProvider(registration.provider)) {
resolved = registration.provider.useValue;
}
else if (providers_1.isTokenProvider(registration.provider)) {
resolved = returnInstance
? registration.instance ||
(registration.instance = this.resolve(registration.provider.useToken, context))
: this.resolve(registration.provider.useToken, context);
}
else if (providers_1.isClassProvider(registration.provider)) {
resolved = returnInstance
? registration.instance ||
(registration.instance = this.construct(registration.provider.useClass, context))
: this.construct(registration.provider.useClass, context);
}
else if (providers_1.isFactoryProvider(registration.provider)) {
resolved = registration.provider.useFactory(this);
}
else {
resolved = this.construct(registration.provider, context);
}
if (registration.options.lifecycle === lifecycle_1.default.ResolutionScoped) {
context.scopedResolutions.set(registration, resolved);
}
return resolved;
}
resolveAll(token, context = new resolution_context_1.default(), isOptional = false) {
this.ensureNotDisposed();
const registrations = this.getAllRegistrations(token);
if (!registrations && providers_1.isNormalToken(token)) {
if (isOptional) {
return [];
}
throw new Error(`Attempted to resolve unregistered dependency token: "${token.toString()}"`);
}
this.executePreResolutionInterceptor(token, "All");
if (registrations) {
const result = registrations.map(item => this.resolveRegistration(item, context));
this.executePostResolutionInterceptor(token, result, "All");
return result;
}
const result = [this.construct(token, context)];
this.executePostResolutionInterceptor(token, result, "All");
return result;
}
isRegistered(token, recursive = false) {
this.ensureNotDisposed();
return (this._registry.has(token) ||
(recursive &&
(this.parent || false) &&
this.parent.isRegistered(token, true)));
}
reset() {
this.ensureNotDisposed();
this._registry.clear();
this.interceptors.preResolution.clear();
this.interceptors.postResolution.clear();
}
clearInstances() {
this.ensureNotDisposed();
for (const [token, registrations] of this._registry.entries()) {
this._registry.setAll(token, registrations
.filter(registration => !providers_1.isValueProvider(registration.provider))
.map(registration => {
registration.instance = undefined;
return registration;
}));
}
}
createChildContainer() {
this.ensureNotDisposed();
const childContainer = new InternalDependencyContainer(this);
for (const [token, registrations] of this._registry.entries()) {
if (registrations.some(({ options }) => options.lifecycle === lifecycle_1.default.ContainerScoped)) {
childContainer._registry.setAll(token, registrations.map(registration => {
if (registration.options.lifecycle === lifecycle_1.default.ContainerScoped) {
return {
provider: registration.provider,
options: registration.options
};
}
return registration;
}));
}
}
return childContainer;
}
beforeResolution(token, callback, options = { frequency: "Always" }) {
this.interceptors.preResolution.set(token, {
callback: callback,
options: options
});
}
afterResolution(token, callback, options = { frequency: "Always" }) {
this.interceptors.postResolution.set(token, {
callback: callback,
options: options
});
}
dispose() {
return tslib_1.__awaiter(this, void 0, void 0, function* () {
this.disposed = true;
const promises = [];
this.disposables.forEach(disposable => {
const maybePromise = disposable.dispose();
if (maybePromise) {
promises.push(maybePromise);
}
});
yield Promise.all(promises);
});
}
getRegistration(token) {
if (this.isRegistered(token)) {
return this._registry.get(token);
}
if (this.parent) {
return this.parent.getRegistration(token);
}
return null;
}
getAllRegistrations(token) {
if (this.isRegistered(token)) {
return this._registry.getAll(token);
}
if (this.parent) {
return this.parent.getAllRegistrations(token);
}
return null;
}
construct(ctor, context) {
if (ctor instanceof lazy_helpers_1.DelayedConstructor) {
return ctor.createProxy((target) => this.resolve(target, context));
}
const instance = (() => {
const paramInfo = exports.typeInfo.get(ctor);
if (!paramInfo || paramInfo.length === 0) {
if (ctor.length === 0) {
return new ctor();
}
else {
throw new Error(`TypeInfo not known for "${ctor.name}"`);
}
}
const params = paramInfo.map(this.resolveParams(context, ctor));
return new ctor(...params);
})();
if (disposable_1.isDisposable(instance)) {
this.disposables.add(instance);
}
return instance;
}
resolveParams(context, ctor) {
return (param, idx) => {
try {
if (injection_token_1.isTokenDescriptor(param)) {
if (injection_token_1.isTransformDescriptor(param)) {
return param.multiple
? this.resolve(param.transform).transform(this.resolveAll(param.token, new resolution_context_1.default(), param.isOptional), ...param.transformArgs)
: this.resolve(param.transform).transform(this.resolve(param.token, context, param.isOptional), ...param.transformArgs);
}
else {
return param.multiple
? this.resolveAll(param.token, new resolution_context_1.default(), param.isOptional)
: this.resolve(param.token, context, param.isOptional);
}
}
else if (injection_token_1.isTransformDescriptor(param)) {
return this.resolve(param.transform, context).transform(this.resolve(param.token, context), ...param.transformArgs);
}
return this.resolve(param, context);
}
catch (e) {
throw new Error(error_helpers_1.formatErrorCtor(ctor, idx, e));
}
};
}
ensureNotDisposed() {
if (this.disposed) {
throw new Error("This container has been disposed, you cannot interact with a disposed container");
}
}
}
exports.instance = new InternalDependencyContainer();
exports.default = exports.instance;
+19
View File
@@ -0,0 +1,19 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.formatErrorCtor = void 0;
function formatDependency(params, idx) {
if (params === null) {
return `at position #${idx}`;
}
const argName = params.split(",")[idx].trim();
return `"${argName}" at position #${idx}`;
}
function composeErrorMessage(msg, e, indent = " ") {
return [msg, ...e.message.split("\n").map(l => indent + l)].join("\n");
}
function formatErrorCtor(ctor, paramIdx, error) {
const [, params = null] = ctor.toString().match(/constructor\(([\w, ]+)\)/) || [];
const dep = formatDependency(params, paramIdx);
return composeErrorMessage(`Cannot inject the dependency ${dep} of "${ctor.name}" constructor. Reason:`, error);
}
exports.formatErrorCtor = formatErrorCtor;
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+8
View File
@@ -0,0 +1,8 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var instance_caching_factory_1 = require("./instance-caching-factory");
Object.defineProperty(exports, "instanceCachingFactory", { enumerable: true, get: function () { return instance_caching_factory_1.default; } });
var instance_per_container_caching_factory_1 = require("./instance-per-container-caching-factory");
Object.defineProperty(exports, "instancePerContainerCachingFactory", { enumerable: true, get: function () { return instance_per_container_caching_factory_1.default; } });
var predicate_aware_class_factory_1 = require("./predicate-aware-class-factory");
Object.defineProperty(exports, "predicateAwareClassFactory", { enumerable: true, get: function () { return predicate_aware_class_factory_1.default; } });
+12
View File
@@ -0,0 +1,12 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
function instanceCachingFactory(factoryFunc) {
let instance;
return (dependencyContainer) => {
if (instance == undefined) {
instance = factoryFunc(dependencyContainer);
}
return instance;
};
}
exports.default = instanceCachingFactory;
@@ -0,0 +1,14 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
function instancePerContainerCachingFactory(factoryFunc) {
const cache = new WeakMap();
return (dependencyContainer) => {
let instance = cache.get(dependencyContainer);
if (instance == undefined) {
instance = factoryFunc(dependencyContainer);
cache.set(dependencyContainer, instance);
}
return instance;
};
}
exports.default = instancePerContainerCachingFactory;
@@ -0,0 +1,19 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
function predicateAwareClassFactory(predicate, trueConstructor, falseConstructor, useCaching = true) {
let instance;
let previousPredicate;
return (dependencyContainer) => {
const currentPredicate = predicate(dependencyContainer);
if (!useCaching || previousPredicate !== currentPredicate) {
if ((previousPredicate = currentPredicate)) {
instance = dependencyContainer.resolve(trueConstructor);
}
else {
instance = dependencyContainer.resolve(falseConstructor);
}
}
return instance;
};
}
exports.default = predicateAwareClassFactory;
+15
View File
@@ -0,0 +1,15 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const tslib_1 = require("tslib");
if (typeof Reflect === "undefined" || !Reflect.getMetadata) {
throw new Error(`tsyringe requires a reflect polyfill. Please add 'import "reflect-metadata"' to the top of your entry point.`);
}
var types_1 = require("./types");
Object.defineProperty(exports, "Lifecycle", { enumerable: true, get: function () { return types_1.Lifecycle; } });
tslib_1.__exportStar(require("./decorators"), exports);
tslib_1.__exportStar(require("./factories"), exports);
tslib_1.__exportStar(require("./providers"), exports);
var lazy_helpers_1 = require("./lazy-helpers");
Object.defineProperty(exports, "delay", { enumerable: true, get: function () { return lazy_helpers_1.delay; } });
var dependency_container_1 = require("./dependency-container");
Object.defineProperty(exports, "container", { enumerable: true, get: function () { return dependency_container_1.instance; } });
+17
View File
@@ -0,0 +1,17 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.PostResolutionInterceptors = exports.PreResolutionInterceptors = void 0;
const registry_base_1 = require("./registry-base");
class PreResolutionInterceptors extends registry_base_1.default {
}
exports.PreResolutionInterceptors = PreResolutionInterceptors;
class PostResolutionInterceptors extends registry_base_1.default {
}
exports.PostResolutionInterceptors = PostResolutionInterceptors;
class Interceptors {
constructor() {
this.preResolution = new PreResolutionInterceptors();
this.postResolution = new PostResolutionInterceptors();
}
}
exports.default = Interceptors;
+54
View File
@@ -0,0 +1,54 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.delay = exports.DelayedConstructor = void 0;
class DelayedConstructor {
constructor(wrap) {
this.wrap = wrap;
this.reflectMethods = [
"get",
"getPrototypeOf",
"setPrototypeOf",
"getOwnPropertyDescriptor",
"defineProperty",
"has",
"set",
"deleteProperty",
"apply",
"construct",
"ownKeys"
];
}
createProxy(createObject) {
const target = {};
let init = false;
let value;
const delayedObject = () => {
if (!init) {
value = createObject(this.wrap());
init = true;
}
return value;
};
return new Proxy(target, this.createHandler(delayedObject));
}
createHandler(delayedObject) {
const handler = {};
const install = (name) => {
handler[name] = (...args) => {
args[0] = delayedObject();
const method = Reflect[name];
return method(...args);
};
};
this.reflectMethods.forEach(install);
return handler;
}
}
exports.DelayedConstructor = DelayedConstructor;
function delay(wrappedConstructor) {
if (typeof wrappedConstructor === "undefined") {
throw new Error("Attempt to `delay` undefined. Constructor must be wrapped in a callback");
}
return new DelayedConstructor(wrappedConstructor);
}
exports.delay = delay;
+7
View File
@@ -0,0 +1,7 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isClassProvider = void 0;
function isClassProvider(provider) {
return !!provider.useClass;
}
exports.isClassProvider = isClassProvider;
+7
View File
@@ -0,0 +1,7 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isFactoryProvider = void 0;
function isFactoryProvider(provider) {
return !!provider.useFactory;
}
exports.isFactoryProvider = isFactoryProvider;
+12
View File
@@ -0,0 +1,12 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var class_provider_1 = require("./class-provider");
Object.defineProperty(exports, "isClassProvider", { enumerable: true, get: function () { return class_provider_1.isClassProvider; } });
var factory_provider_1 = require("./factory-provider");
Object.defineProperty(exports, "isFactoryProvider", { enumerable: true, get: function () { return factory_provider_1.isFactoryProvider; } });
var injection_token_1 = require("./injection-token");
Object.defineProperty(exports, "isNormalToken", { enumerable: true, get: function () { return injection_token_1.isNormalToken; } });
var token_provider_1 = require("./token-provider");
Object.defineProperty(exports, "isTokenProvider", { enumerable: true, get: function () { return token_provider_1.isTokenProvider; } });
var value_provider_1 = require("./value-provider");
Object.defineProperty(exports, "isValueProvider", { enumerable: true, get: function () { return value_provider_1.isValueProvider; } });
+24
View File
@@ -0,0 +1,24 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isConstructorToken = exports.isTransformDescriptor = exports.isTokenDescriptor = exports.isNormalToken = void 0;
const lazy_helpers_1 = require("../lazy-helpers");
function isNormalToken(token) {
return typeof token === "string" || typeof token === "symbol";
}
exports.isNormalToken = isNormalToken;
function isTokenDescriptor(descriptor) {
return (typeof descriptor === "object" &&
"token" in descriptor &&
"multiple" in descriptor);
}
exports.isTokenDescriptor = isTokenDescriptor;
function isTransformDescriptor(descriptor) {
return (typeof descriptor === "object" &&
"token" in descriptor &&
"transform" in descriptor);
}
exports.isTransformDescriptor = isTransformDescriptor;
function isConstructorToken(token) {
return typeof token === "function" || token instanceof lazy_helpers_1.DelayedConstructor;
}
exports.isConstructorToken = isConstructorToken;
+14
View File
@@ -0,0 +1,14 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isProvider = void 0;
const class_provider_1 = require("./class-provider");
const value_provider_1 = require("./value-provider");
const token_provider_1 = require("./token-provider");
const factory_provider_1 = require("./factory-provider");
function isProvider(provider) {
return (class_provider_1.isClassProvider(provider) ||
value_provider_1.isValueProvider(provider) ||
token_provider_1.isTokenProvider(provider) ||
factory_provider_1.isFactoryProvider(provider));
}
exports.isProvider = isProvider;
+7
View File
@@ -0,0 +1,7 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isTokenProvider = void 0;
function isTokenProvider(provider) {
return !!provider.useToken;
}
exports.isTokenProvider = isTokenProvider;
+7
View File
@@ -0,0 +1,7 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isValueProvider = void 0;
function isValueProvider(provider) {
return provider.useValue != undefined;
}
exports.isValueProvider = isValueProvider;
+27
View File
@@ -0,0 +1,27 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.defineInjectionTokenMetadata = exports.getParamInfo = exports.INJECTION_TOKEN_METADATA_KEY = void 0;
exports.INJECTION_TOKEN_METADATA_KEY = "injectionTokens";
function getParamInfo(target) {
const params = Reflect.getMetadata("design:paramtypes", target) || [];
const injectionTokens = Reflect.getOwnMetadata(exports.INJECTION_TOKEN_METADATA_KEY, target) || {};
Object.keys(injectionTokens).forEach(key => {
params[+key] = injectionTokens[key];
});
return params;
}
exports.getParamInfo = getParamInfo;
function defineInjectionTokenMetadata(data, transform) {
return function (target, _propertyKey, parameterIndex) {
const descriptors = Reflect.getOwnMetadata(exports.INJECTION_TOKEN_METADATA_KEY, target) || {};
descriptors[parameterIndex] = transform
? {
token: data,
transform: transform.transformToken,
transformArgs: transform.args || []
}
: data;
Reflect.defineMetadata(exports.INJECTION_TOKEN_METADATA_KEY, descriptors, target);
};
}
exports.defineInjectionTokenMetadata = defineInjectionTokenMetadata;
+39
View File
@@ -0,0 +1,39 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
class RegistryBase {
constructor() {
this._registryMap = new Map();
}
entries() {
return this._registryMap.entries();
}
getAll(key) {
this.ensure(key);
return this._registryMap.get(key);
}
get(key) {
this.ensure(key);
const value = this._registryMap.get(key);
return value[value.length - 1] || null;
}
set(key, value) {
this.ensure(key);
this._registryMap.get(key).push(value);
}
setAll(key, value) {
this._registryMap.set(key, value);
}
has(key) {
this.ensure(key);
return this._registryMap.get(key).length > 0;
}
clear() {
this._registryMap.clear();
}
ensure(key) {
if (!this._registryMap.has(key)) {
this._registryMap.set(key, []);
}
}
}
exports.default = RegistryBase;
+6
View File
@@ -0,0 +1,6 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
const registry_base_1 = require("./registry-base");
class Registry extends registry_base_1.default {
}
exports.default = Registry;
+8
View File
@@ -0,0 +1,8 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
class ResolutionContext {
constructor() {
this.scopedResolutions = new Map();
}
}
exports.default = ResolutionContext;
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+13
View File
@@ -0,0 +1,13 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
exports.isDisposable = void 0;
function isDisposable(value) {
if (typeof value.dispose !== "function")
return false;
const disposeFun = value.dispose;
if (disposeFun.length > 0) {
return false;
}
return true;
}
exports.isDisposable = isDisposable;
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+4
View File
@@ -0,0 +1,4 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var lifecycle_1 = require("./lifecycle");
Object.defineProperty(exports, "Lifecycle", { enumerable: true, get: function () { return lifecycle_1.default; } });
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+10
View File
@@ -0,0 +1,10 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
var Lifecycle;
(function (Lifecycle) {
Lifecycle[Lifecycle["Transient"] = 0] = "Transient";
Lifecycle[Lifecycle["Singleton"] = 1] = "Singleton";
Lifecycle[Lifecycle["ResolutionScoped"] = 2] = "ResolutionScoped";
Lifecycle[Lifecycle["ContainerScoped"] = 3] = "ContainerScoped";
})(Lifecycle || (Lifecycle = {}));
exports.default = Lifecycle;
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+2
View File
@@ -0,0 +1,2 @@
"use strict";
Object.defineProperty(exports, "__esModule", { value: true });
+44
View File
@@ -0,0 +1,44 @@
import { getParamInfo } from "../reflection-helpers";
import { instance as globalContainer } from "../dependency-container";
import { isTokenDescriptor, isTransformDescriptor } from "../providers/injection-token";
import { formatErrorCtor } from "../error-helpers";
function autoInjectable() {
return function (target) {
const paramInfo = getParamInfo(target);
return class extends target {
constructor(...args) {
super(...args.concat(paramInfo.slice(args.length).map((type, index) => {
try {
if (isTokenDescriptor(type)) {
if (isTransformDescriptor(type)) {
return type.multiple
? globalContainer
.resolve(type.transform)
.transform(globalContainer.resolveAll(type.token), ...type.transformArgs)
: globalContainer
.resolve(type.transform)
.transform(globalContainer.resolve(type.token), ...type.transformArgs);
}
else {
return type.multiple
? globalContainer.resolveAll(type.token)
: globalContainer.resolve(type.token);
}
}
else if (isTransformDescriptor(type)) {
return globalContainer
.resolve(type.transform)
.transform(globalContainer.resolve(type.token), ...type.transformArgs);
}
return globalContainer.resolve(type);
}
catch (e) {
const argIndex = index + args.length;
throw new Error(formatErrorCtor(target, argIndex, e));
}
})));
}
};
};
}
export default autoInjectable;
+9
View File
@@ -0,0 +1,9 @@
export { default as autoInjectable } from "./auto-injectable";
export { default as inject } from "./inject";
export { default as injectable } from "./injectable";
export { default as registry } from "./registry";
export { default as singleton } from "./singleton";
export { default as injectAll } from "./inject-all";
export { default as injectAllWithTransform } from "./inject-all-with-transform";
export { default as injectWithTransform } from "./inject-with-transform";
export { default as scoped } from "./scoped";
@@ -0,0 +1,11 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function injectAllWithTransform(token, transformer, ...args) {
const data = {
token,
multiple: true,
transform: transformer,
transformArgs: args
};
return defineInjectionTokenMetadata(data);
}
export default injectAllWithTransform;
+10
View File
@@ -0,0 +1,10 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function injectAll(token, options) {
const data = {
token,
multiple: true,
isOptional: options && options.isOptional
};
return defineInjectionTokenMetadata(data);
}
export default injectAll;
@@ -0,0 +1,8 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function injectWithTransform(token, transformer, ...args) {
return defineInjectionTokenMetadata(token, {
transformToken: transformer,
args: args
});
}
export default injectWithTransform;
+10
View File
@@ -0,0 +1,10 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function inject(token, options) {
const data = {
token,
multiple: false,
isOptional: options && options.isOptional
};
return defineInjectionTokenMetadata(data);
}
export default inject;
+19
View File
@@ -0,0 +1,19 @@
import { getParamInfo } from "../reflection-helpers";
import { typeInfo } from "../dependency-container";
import { instance as globalContainer } from "../dependency-container";
function injectable(options) {
return function (target) {
typeInfo.set(target, getParamInfo(target));
if (options && options.token) {
if (!Array.isArray(options.token)) {
globalContainer.register(options.token, target);
}
else {
options.token.forEach(token => {
globalContainer.register(token, target);
});
}
}
};
}
export default injectable;
+12
View File
@@ -0,0 +1,12 @@
import { __rest } from "tslib";
import { instance as globalContainer } from "../dependency-container";
function registry(registrations = []) {
return function (target) {
registrations.forEach((_a) => {
var { token, options } = _a, provider = __rest(_a, ["token", "options"]);
return globalContainer.register(token, provider, options);
});
return target;
};
}
export default registry;
+10
View File
@@ -0,0 +1,10 @@
import injectable from "./injectable";
import { instance as globalContainer } from "../dependency-container";
export default function scoped(lifecycle, token) {
return function (target) {
injectable()(target);
globalContainer.register(token || target, target, {
lifecycle
});
};
}
+9
View File
@@ -0,0 +1,9 @@
import injectable from "./injectable";
import { instance as globalContainer } from "../dependency-container";
function singleton() {
return function (target) {
injectable()(target);
globalContainer.registerSingleton(target);
};
}
export default singleton;
+338
View File
@@ -0,0 +1,338 @@
import { __awaiter } from "tslib";
import { isClassProvider, isFactoryProvider, isNormalToken, isTokenProvider, isValueProvider } from "./providers";
import { isProvider } from "./providers/provider";
import { isConstructorToken, isTokenDescriptor, isTransformDescriptor } from "./providers/injection-token";
import Registry from "./registry";
import Lifecycle from "./types/lifecycle";
import ResolutionContext from "./resolution-context";
import { formatErrorCtor } from "./error-helpers";
import { DelayedConstructor } from "./lazy-helpers";
import { isDisposable } from "./types/disposable";
import Interceptors from "./interceptors";
export const typeInfo = new Map();
class InternalDependencyContainer {
constructor(parent) {
this.parent = parent;
this._registry = new Registry();
this.interceptors = new Interceptors();
this.disposed = false;
this.disposables = new Set();
}
register(token, providerOrConstructor, options = { lifecycle: Lifecycle.Transient }) {
this.ensureNotDisposed();
let provider;
if (!isProvider(providerOrConstructor)) {
provider = { useClass: providerOrConstructor };
}
else {
provider = providerOrConstructor;
}
if (isTokenProvider(provider)) {
const path = [token];
let tokenProvider = provider;
while (tokenProvider != null) {
const currentToken = tokenProvider.useToken;
if (path.includes(currentToken)) {
throw new Error(`Token registration cycle detected! ${[...path, currentToken].join(" -> ")}`);
}
path.push(currentToken);
const registration = this._registry.get(currentToken);
if (registration && isTokenProvider(registration.provider)) {
tokenProvider = registration.provider;
}
else {
tokenProvider = null;
}
}
}
if (options.lifecycle === Lifecycle.Singleton ||
options.lifecycle == Lifecycle.ContainerScoped ||
options.lifecycle == Lifecycle.ResolutionScoped) {
if (isValueProvider(provider) || isFactoryProvider(provider)) {
throw new Error(`Cannot use lifecycle "${Lifecycle[options.lifecycle]}" with ValueProviders or FactoryProviders`);
}
}
this._registry.set(token, { provider, options });
return this;
}
registerType(from, to) {
this.ensureNotDisposed();
if (isNormalToken(to)) {
return this.register(from, {
useToken: to
});
}
return this.register(from, {
useClass: to
});
}
registerInstance(token, instance) {
this.ensureNotDisposed();
return this.register(token, {
useValue: instance
});
}
registerSingleton(from, to) {
this.ensureNotDisposed();
if (isNormalToken(from)) {
if (isNormalToken(to)) {
return this.register(from, {
useToken: to
}, { lifecycle: Lifecycle.Singleton });
}
else if (to) {
return this.register(from, {
useClass: to
}, { lifecycle: Lifecycle.Singleton });
}
throw new Error('Cannot register a type name as a singleton without a "to" token');
}
let useClass = from;
if (to && !isNormalToken(to)) {
useClass = to;
}
return this.register(from, {
useClass
}, { lifecycle: Lifecycle.Singleton });
}
resolve(token, context = new ResolutionContext(), isOptional = false) {
this.ensureNotDisposed();
const registration = this.getRegistration(token);
if (!registration && isNormalToken(token)) {
if (isOptional) {
return undefined;
}
throw new Error(`Attempted to resolve unregistered dependency token: "${token.toString()}"`);
}
this.executePreResolutionInterceptor(token, "Single");
if (registration) {
const result = this.resolveRegistration(registration, context);
this.executePostResolutionInterceptor(token, result, "Single");
return result;
}
if (isConstructorToken(token)) {
const result = this.construct(token, context);
this.executePostResolutionInterceptor(token, result, "Single");
return result;
}
throw new Error("Attempted to construct an undefined constructor. Could mean a circular dependency problem. Try using `delay` function.");
}
executePreResolutionInterceptor(token, resolutionType) {
if (this.interceptors.preResolution.has(token)) {
const remainingInterceptors = [];
for (const interceptor of this.interceptors.preResolution.getAll(token)) {
if (interceptor.options.frequency != "Once") {
remainingInterceptors.push(interceptor);
}
interceptor.callback(token, resolutionType);
}
this.interceptors.preResolution.setAll(token, remainingInterceptors);
}
}
executePostResolutionInterceptor(token, result, resolutionType) {
if (this.interceptors.postResolution.has(token)) {
const remainingInterceptors = [];
for (const interceptor of this.interceptors.postResolution.getAll(token)) {
if (interceptor.options.frequency != "Once") {
remainingInterceptors.push(interceptor);
}
interceptor.callback(token, result, resolutionType);
}
this.interceptors.postResolution.setAll(token, remainingInterceptors);
}
}
resolveRegistration(registration, context) {
this.ensureNotDisposed();
if (registration.options.lifecycle === Lifecycle.ResolutionScoped &&
context.scopedResolutions.has(registration)) {
return context.scopedResolutions.get(registration);
}
const isSingleton = registration.options.lifecycle === Lifecycle.Singleton;
const isContainerScoped = registration.options.lifecycle === Lifecycle.ContainerScoped;
const returnInstance = isSingleton || isContainerScoped;
let resolved;
if (isValueProvider(registration.provider)) {
resolved = registration.provider.useValue;
}
else if (isTokenProvider(registration.provider)) {
resolved = returnInstance
? registration.instance ||
(registration.instance = this.resolve(registration.provider.useToken, context))
: this.resolve(registration.provider.useToken, context);
}
else if (isClassProvider(registration.provider)) {
resolved = returnInstance
? registration.instance ||
(registration.instance = this.construct(registration.provider.useClass, context))
: this.construct(registration.provider.useClass, context);
}
else if (isFactoryProvider(registration.provider)) {
resolved = registration.provider.useFactory(this);
}
else {
resolved = this.construct(registration.provider, context);
}
if (registration.options.lifecycle === Lifecycle.ResolutionScoped) {
context.scopedResolutions.set(registration, resolved);
}
return resolved;
}
resolveAll(token, context = new ResolutionContext(), isOptional = false) {
this.ensureNotDisposed();
const registrations = this.getAllRegistrations(token);
if (!registrations && isNormalToken(token)) {
if (isOptional) {
return [];
}
throw new Error(`Attempted to resolve unregistered dependency token: "${token.toString()}"`);
}
this.executePreResolutionInterceptor(token, "All");
if (registrations) {
const result = registrations.map(item => this.resolveRegistration(item, context));
this.executePostResolutionInterceptor(token, result, "All");
return result;
}
const result = [this.construct(token, context)];
this.executePostResolutionInterceptor(token, result, "All");
return result;
}
isRegistered(token, recursive = false) {
this.ensureNotDisposed();
return (this._registry.has(token) ||
(recursive &&
(this.parent || false) &&
this.parent.isRegistered(token, true)));
}
reset() {
this.ensureNotDisposed();
this._registry.clear();
this.interceptors.preResolution.clear();
this.interceptors.postResolution.clear();
}
clearInstances() {
this.ensureNotDisposed();
for (const [token, registrations] of this._registry.entries()) {
this._registry.setAll(token, registrations
.filter(registration => !isValueProvider(registration.provider))
.map(registration => {
registration.instance = undefined;
return registration;
}));
}
}
createChildContainer() {
this.ensureNotDisposed();
const childContainer = new InternalDependencyContainer(this);
for (const [token, registrations] of this._registry.entries()) {
if (registrations.some(({ options }) => options.lifecycle === Lifecycle.ContainerScoped)) {
childContainer._registry.setAll(token, registrations.map(registration => {
if (registration.options.lifecycle === Lifecycle.ContainerScoped) {
return {
provider: registration.provider,
options: registration.options
};
}
return registration;
}));
}
}
return childContainer;
}
beforeResolution(token, callback, options = { frequency: "Always" }) {
this.interceptors.preResolution.set(token, {
callback: callback,
options: options
});
}
afterResolution(token, callback, options = { frequency: "Always" }) {
this.interceptors.postResolution.set(token, {
callback: callback,
options: options
});
}
dispose() {
return __awaiter(this, void 0, void 0, function* () {
this.disposed = true;
const promises = [];
this.disposables.forEach(disposable => {
const maybePromise = disposable.dispose();
if (maybePromise) {
promises.push(maybePromise);
}
});
yield Promise.all(promises);
});
}
getRegistration(token) {
if (this.isRegistered(token)) {
return this._registry.get(token);
}
if (this.parent) {
return this.parent.getRegistration(token);
}
return null;
}
getAllRegistrations(token) {
if (this.isRegistered(token)) {
return this._registry.getAll(token);
}
if (this.parent) {
return this.parent.getAllRegistrations(token);
}
return null;
}
construct(ctor, context) {
if (ctor instanceof DelayedConstructor) {
return ctor.createProxy((target) => this.resolve(target, context));
}
const instance = (() => {
const paramInfo = typeInfo.get(ctor);
if (!paramInfo || paramInfo.length === 0) {
if (ctor.length === 0) {
return new ctor();
}
else {
throw new Error(`TypeInfo not known for "${ctor.name}"`);
}
}
const params = paramInfo.map(this.resolveParams(context, ctor));
return new ctor(...params);
})();
if (isDisposable(instance)) {
this.disposables.add(instance);
}
return instance;
}
resolveParams(context, ctor) {
return (param, idx) => {
try {
if (isTokenDescriptor(param)) {
if (isTransformDescriptor(param)) {
return param.multiple
? this.resolve(param.transform).transform(this.resolveAll(param.token, new ResolutionContext(), param.isOptional), ...param.transformArgs)
: this.resolve(param.transform).transform(this.resolve(param.token, context, param.isOptional), ...param.transformArgs);
}
else {
return param.multiple
? this.resolveAll(param.token, new ResolutionContext(), param.isOptional)
: this.resolve(param.token, context, param.isOptional);
}
}
else if (isTransformDescriptor(param)) {
return this.resolve(param.transform, context).transform(this.resolve(param.token, context), ...param.transformArgs);
}
return this.resolve(param, context);
}
catch (e) {
throw new Error(formatErrorCtor(ctor, idx, e));
}
};
}
ensureNotDisposed() {
if (this.disposed) {
throw new Error("This container has been disposed, you cannot interact with a disposed container");
}
}
}
export const instance = new InternalDependencyContainer();
export default instance;
+15
View File
@@ -0,0 +1,15 @@
function formatDependency(params, idx) {
if (params === null) {
return `at position #${idx}`;
}
const argName = params.split(",")[idx].trim();
return `"${argName}" at position #${idx}`;
}
function composeErrorMessage(msg, e, indent = " ") {
return [msg, ...e.message.split("\n").map(l => indent + l)].join("\n");
}
export function formatErrorCtor(ctor, paramIdx, error) {
const [, params = null] = ctor.toString().match(/constructor\(([\w, ]+)\)/) || [];
const dep = formatDependency(params, paramIdx);
return composeErrorMessage(`Cannot inject the dependency ${dep} of "${ctor.name}" constructor. Reason:`, error);
}
View File
+3
View File
@@ -0,0 +1,3 @@
export { default as instanceCachingFactory } from "./instance-caching-factory";
export { default as instancePerContainerCachingFactory } from "./instance-per-container-caching-factory";
export { default as predicateAwareClassFactory } from "./predicate-aware-class-factory";
@@ -0,0 +1,9 @@
export default function instanceCachingFactory(factoryFunc) {
let instance;
return (dependencyContainer) => {
if (instance == undefined) {
instance = factoryFunc(dependencyContainer);
}
return instance;
};
}
@@ -0,0 +1,11 @@
export default function instancePerContainerCachingFactory(factoryFunc) {
const cache = new WeakMap();
return (dependencyContainer) => {
let instance = cache.get(dependencyContainer);
if (instance == undefined) {
instance = factoryFunc(dependencyContainer);
cache.set(dependencyContainer, instance);
}
return instance;
};
}
@@ -0,0 +1,16 @@
export default function predicateAwareClassFactory(predicate, trueConstructor, falseConstructor, useCaching = true) {
let instance;
let previousPredicate;
return (dependencyContainer) => {
const currentPredicate = predicate(dependencyContainer);
if (!useCaching || previousPredicate !== currentPredicate) {
if ((previousPredicate = currentPredicate)) {
instance = dependencyContainer.resolve(trueConstructor);
}
else {
instance = dependencyContainer.resolve(falseConstructor);
}
}
return instance;
};
}
+9
View File
@@ -0,0 +1,9 @@
if (typeof Reflect === "undefined" || !Reflect.getMetadata) {
throw new Error(`tsyringe requires a reflect polyfill. Please add 'import "reflect-metadata"' to the top of your entry point.`);
}
export { Lifecycle } from "./types";
export * from "./decorators";
export * from "./factories";
export * from "./providers";
export { delay } from "./lazy-helpers";
export { instance as container } from "./dependency-container";
+11
View File
@@ -0,0 +1,11 @@
import RegistryBase from "./registry-base";
export class PreResolutionInterceptors extends RegistryBase {
}
export class PostResolutionInterceptors extends RegistryBase {
}
export default class Interceptors {
constructor() {
this.preResolution = new PreResolutionInterceptors();
this.postResolution = new PostResolutionInterceptors();
}
}
+49
View File
@@ -0,0 +1,49 @@
export class DelayedConstructor {
constructor(wrap) {
this.wrap = wrap;
this.reflectMethods = [
"get",
"getPrototypeOf",
"setPrototypeOf",
"getOwnPropertyDescriptor",
"defineProperty",
"has",
"set",
"deleteProperty",
"apply",
"construct",
"ownKeys"
];
}
createProxy(createObject) {
const target = {};
let init = false;
let value;
const delayedObject = () => {
if (!init) {
value = createObject(this.wrap());
init = true;
}
return value;
};
return new Proxy(target, this.createHandler(delayedObject));
}
createHandler(delayedObject) {
const handler = {};
const install = (name) => {
handler[name] = (...args) => {
args[0] = delayedObject();
const method = Reflect[name];
return method(...args);
};
};
this.reflectMethods.forEach(install);
return handler;
}
}
export function delay(wrappedConstructor) {
if (typeof wrappedConstructor === "undefined") {
throw new Error("Attempt to `delay` undefined. Constructor must be wrapped in a callback");
}
return new DelayedConstructor(wrappedConstructor);
}
+3
View File
@@ -0,0 +1,3 @@
export function isClassProvider(provider) {
return !!provider.useClass;
}
+3
View File
@@ -0,0 +1,3 @@
export function isFactoryProvider(provider) {
return !!provider.useFactory;
}
+5
View File
@@ -0,0 +1,5 @@
export { isClassProvider } from "./class-provider";
export { isFactoryProvider } from "./factory-provider";
export { isNormalToken } from "./injection-token";
export { isTokenProvider } from "./token-provider";
export { isValueProvider } from "./value-provider";
+17
View File
@@ -0,0 +1,17 @@
import { DelayedConstructor } from "../lazy-helpers";
export function isNormalToken(token) {
return typeof token === "string" || typeof token === "symbol";
}
export function isTokenDescriptor(descriptor) {
return (typeof descriptor === "object" &&
"token" in descriptor &&
"multiple" in descriptor);
}
export function isTransformDescriptor(descriptor) {
return (typeof descriptor === "object" &&
"token" in descriptor &&
"transform" in descriptor);
}
export function isConstructorToken(token) {
return typeof token === "function" || token instanceof DelayedConstructor;
}
+10
View File
@@ -0,0 +1,10 @@
import { isClassProvider } from "./class-provider";
import { isValueProvider } from "./value-provider";
import { isTokenProvider } from "./token-provider";
import { isFactoryProvider } from "./factory-provider";
export function isProvider(provider) {
return (isClassProvider(provider) ||
isValueProvider(provider) ||
isTokenProvider(provider) ||
isFactoryProvider(provider));
}
+3
View File
@@ -0,0 +1,3 @@
export function isTokenProvider(provider) {
return !!provider.useToken;
}
+3
View File
@@ -0,0 +1,3 @@
export function isValueProvider(provider) {
return provider.useValue != undefined;
}
+22
View File
@@ -0,0 +1,22 @@
export const INJECTION_TOKEN_METADATA_KEY = "injectionTokens";
export function getParamInfo(target) {
const params = Reflect.getMetadata("design:paramtypes", target) || [];
const injectionTokens = Reflect.getOwnMetadata(INJECTION_TOKEN_METADATA_KEY, target) || {};
Object.keys(injectionTokens).forEach(key => {
params[+key] = injectionTokens[key];
});
return params;
}
export function defineInjectionTokenMetadata(data, transform) {
return function (target, _propertyKey, parameterIndex) {
const descriptors = Reflect.getOwnMetadata(INJECTION_TOKEN_METADATA_KEY, target) || {};
descriptors[parameterIndex] = transform
? {
token: data,
transform: transform.transformToken,
transformArgs: transform.args || []
}
: data;
Reflect.defineMetadata(INJECTION_TOKEN_METADATA_KEY, descriptors, target);
};
}
+36
View File
@@ -0,0 +1,36 @@
export default class RegistryBase {
constructor() {
this._registryMap = new Map();
}
entries() {
return this._registryMap.entries();
}
getAll(key) {
this.ensure(key);
return this._registryMap.get(key);
}
get(key) {
this.ensure(key);
const value = this._registryMap.get(key);
return value[value.length - 1] || null;
}
set(key, value) {
this.ensure(key);
this._registryMap.get(key).push(value);
}
setAll(key, value) {
this._registryMap.set(key, value);
}
has(key) {
this.ensure(key);
return this._registryMap.get(key).length > 0;
}
clear() {
this._registryMap.clear();
}
ensure(key) {
if (!this._registryMap.has(key)) {
this._registryMap.set(key, []);
}
}
}
+3
View File
@@ -0,0 +1,3 @@
import RegistryBase from "./registry-base";
export default class Registry extends RegistryBase {
}
+5
View File
@@ -0,0 +1,5 @@
export default class ResolutionContext {
constructor() {
this.scopedResolutions = new Map();
}
}
View File
View File
View File
+9
View File
@@ -0,0 +1,9 @@
export function isDisposable(value) {
if (typeof value.dispose !== "function")
return false;
const disposeFun = value.dispose;
if (disposeFun.length > 0) {
return false;
}
return true;
}
View File
+1
View File
@@ -0,0 +1 @@
export { default as Lifecycle } from "./lifecycle";
View File
+8
View File
@@ -0,0 +1,8 @@
var Lifecycle;
(function (Lifecycle) {
Lifecycle[Lifecycle["Transient"] = 0] = "Transient";
Lifecycle[Lifecycle["Singleton"] = 1] = "Singleton";
Lifecycle[Lifecycle["ResolutionScoped"] = 2] = "ResolutionScoped";
Lifecycle[Lifecycle["ContainerScoped"] = 3] = "ContainerScoped";
})(Lifecycle || (Lifecycle = {}));
export default Lifecycle;
View File
View File
+48
View File
@@ -0,0 +1,48 @@
import { __extends, __read, __spread } from "tslib";
import { getParamInfo } from "../reflection-helpers";
import { instance as globalContainer } from "../dependency-container";
import { isTokenDescriptor, isTransformDescriptor } from "../providers/injection-token";
import { formatErrorCtor } from "../error-helpers";
function autoInjectable() {
return function (target) {
var paramInfo = getParamInfo(target);
return (function (_super) {
__extends(class_1, _super);
function class_1() {
var args = [];
for (var _i = 0; _i < arguments.length; _i++) {
args[_i] = arguments[_i];
}
return _super.apply(this, __spread(args.concat(paramInfo.slice(args.length).map(function (type, index) {
var _a, _b, _c;
try {
if (isTokenDescriptor(type)) {
if (isTransformDescriptor(type)) {
return type.multiple
? (_a = globalContainer
.resolve(type.transform)).transform.apply(_a, __spread([globalContainer.resolveAll(type.token)], type.transformArgs)) : (_b = globalContainer
.resolve(type.transform)).transform.apply(_b, __spread([globalContainer.resolve(type.token)], type.transformArgs));
}
else {
return type.multiple
? globalContainer.resolveAll(type.token)
: globalContainer.resolve(type.token);
}
}
else if (isTransformDescriptor(type)) {
return (_c = globalContainer
.resolve(type.transform)).transform.apply(_c, __spread([globalContainer.resolve(type.token)], type.transformArgs));
}
return globalContainer.resolve(type);
}
catch (e) {
var argIndex = index + args.length;
throw new Error(formatErrorCtor(target, argIndex, e));
}
})))) || this;
}
return class_1;
}(target));
};
}
export default autoInjectable;
+9
View File
@@ -0,0 +1,9 @@
export { default as autoInjectable } from "./auto-injectable";
export { default as inject } from "./inject";
export { default as injectable } from "./injectable";
export { default as registry } from "./registry";
export { default as singleton } from "./singleton";
export { default as injectAll } from "./inject-all";
export { default as injectAllWithTransform } from "./inject-all-with-transform";
export { default as injectWithTransform } from "./inject-with-transform";
export { default as scoped } from "./scoped";
@@ -0,0 +1,15 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function injectAllWithTransform(token, transformer) {
var args = [];
for (var _i = 2; _i < arguments.length; _i++) {
args[_i - 2] = arguments[_i];
}
var data = {
token: token,
multiple: true,
transform: transformer,
transformArgs: args
};
return defineInjectionTokenMetadata(data);
}
export default injectAllWithTransform;
+10
View File
@@ -0,0 +1,10 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function injectAll(token, options) {
var data = {
token: token,
multiple: true,
isOptional: options && options.isOptional
};
return defineInjectionTokenMetadata(data);
}
export default injectAll;
+12
View File
@@ -0,0 +1,12 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function injectWithTransform(token, transformer) {
var args = [];
for (var _i = 2; _i < arguments.length; _i++) {
args[_i - 2] = arguments[_i];
}
return defineInjectionTokenMetadata(token, {
transformToken: transformer,
args: args
});
}
export default injectWithTransform;
+10
View File
@@ -0,0 +1,10 @@
import { defineInjectionTokenMetadata } from "../reflection-helpers";
function inject(token, options) {
var data = {
token: token,
multiple: false,
isOptional: options && options.isOptional
};
return defineInjectionTokenMetadata(data);
}
export default inject;
+19
View File
@@ -0,0 +1,19 @@
import { getParamInfo } from "../reflection-helpers";
import { typeInfo } from "../dependency-container";
import { instance as globalContainer } from "../dependency-container";
function injectable(options) {
return function (target) {
typeInfo.set(target, getParamInfo(target));
if (options && options.token) {
if (!Array.isArray(options.token)) {
globalContainer.register(options.token, target);
}
else {
options.token.forEach(function (token) {
globalContainer.register(token, target);
});
}
}
};
}
export default injectable;
+13
View File
@@ -0,0 +1,13 @@
import { __rest } from "tslib";
import { instance as globalContainer } from "../dependency-container";
function registry(registrations) {
if (registrations === void 0) { registrations = []; }
return function (target) {
registrations.forEach(function (_a) {
var token = _a.token, options = _a.options, provider = __rest(_a, ["token", "options"]);
return globalContainer.register(token, provider, options);
});
return target;
};
}
export default registry;
+10
View File
@@ -0,0 +1,10 @@
import injectable from "./injectable";
import { instance as globalContainer } from "../dependency-container";
export default function scoped(lifecycle, token) {
return function (target) {
injectable()(target);
globalContainer.register(token || target, target, {
lifecycle: lifecycle
});
};
}
+9
View File
@@ -0,0 +1,9 @@
import injectable from "./injectable";
import { instance as globalContainer } from "../dependency-container";
function singleton() {
return function (target) {
injectable()(target);
globalContainer.registerSingleton(target);
};
}
export default singleton;
+410
View File
@@ -0,0 +1,410 @@
import { __awaiter, __generator, __read, __spread, __values } from "tslib";
import { isClassProvider, isFactoryProvider, isNormalToken, isTokenProvider, isValueProvider } from "./providers";
import { isProvider } from "./providers/provider";
import { isConstructorToken, isTokenDescriptor, isTransformDescriptor } from "./providers/injection-token";
import Registry from "./registry";
import Lifecycle from "./types/lifecycle";
import ResolutionContext from "./resolution-context";
import { formatErrorCtor } from "./error-helpers";
import { DelayedConstructor } from "./lazy-helpers";
import { isDisposable } from "./types/disposable";
import Interceptors from "./interceptors";
export var typeInfo = new Map();
var InternalDependencyContainer = (function () {
function InternalDependencyContainer(parent) {
this.parent = parent;
this._registry = new Registry();
this.interceptors = new Interceptors();
this.disposed = false;
this.disposables = new Set();
}
InternalDependencyContainer.prototype.register = function (token, providerOrConstructor, options) {
if (options === void 0) { options = { lifecycle: Lifecycle.Transient }; }
this.ensureNotDisposed();
var provider;
if (!isProvider(providerOrConstructor)) {
provider = { useClass: providerOrConstructor };
}
else {
provider = providerOrConstructor;
}
if (isTokenProvider(provider)) {
var path = [token];
var tokenProvider = provider;
while (tokenProvider != null) {
var currentToken = tokenProvider.useToken;
if (path.includes(currentToken)) {
throw new Error("Token registration cycle detected! " + __spread(path, [currentToken]).join(" -> "));
}
path.push(currentToken);
var registration = this._registry.get(currentToken);
if (registration && isTokenProvider(registration.provider)) {
tokenProvider = registration.provider;
}
else {
tokenProvider = null;
}
}
}
if (options.lifecycle === Lifecycle.Singleton ||
options.lifecycle == Lifecycle.ContainerScoped ||
options.lifecycle == Lifecycle.ResolutionScoped) {
if (isValueProvider(provider) || isFactoryProvider(provider)) {
throw new Error("Cannot use lifecycle \"" + Lifecycle[options.lifecycle] + "\" with ValueProviders or FactoryProviders");
}
}
this._registry.set(token, { provider: provider, options: options });
return this;
};
InternalDependencyContainer.prototype.registerType = function (from, to) {
this.ensureNotDisposed();
if (isNormalToken(to)) {
return this.register(from, {
useToken: to
});
}
return this.register(from, {
useClass: to
});
};
InternalDependencyContainer.prototype.registerInstance = function (token, instance) {
this.ensureNotDisposed();
return this.register(token, {
useValue: instance
});
};
InternalDependencyContainer.prototype.registerSingleton = function (from, to) {
this.ensureNotDisposed();
if (isNormalToken(from)) {
if (isNormalToken(to)) {
return this.register(from, {
useToken: to
}, { lifecycle: Lifecycle.Singleton });
}
else if (to) {
return this.register(from, {
useClass: to
}, { lifecycle: Lifecycle.Singleton });
}
throw new Error('Cannot register a type name as a singleton without a "to" token');
}
var useClass = from;
if (to && !isNormalToken(to)) {
useClass = to;
}
return this.register(from, {
useClass: useClass
}, { lifecycle: Lifecycle.Singleton });
};
InternalDependencyContainer.prototype.resolve = function (token, context, isOptional) {
if (context === void 0) { context = new ResolutionContext(); }
if (isOptional === void 0) { isOptional = false; }
this.ensureNotDisposed();
var registration = this.getRegistration(token);
if (!registration && isNormalToken(token)) {
if (isOptional) {
return undefined;
}
throw new Error("Attempted to resolve unregistered dependency token: \"" + token.toString() + "\"");
}
this.executePreResolutionInterceptor(token, "Single");
if (registration) {
var result = this.resolveRegistration(registration, context);
this.executePostResolutionInterceptor(token, result, "Single");
return result;
}
if (isConstructorToken(token)) {
var result = this.construct(token, context);
this.executePostResolutionInterceptor(token, result, "Single");
return result;
}
throw new Error("Attempted to construct an undefined constructor. Could mean a circular dependency problem. Try using `delay` function.");
};
InternalDependencyContainer.prototype.executePreResolutionInterceptor = function (token, resolutionType) {
var e_1, _a;
if (this.interceptors.preResolution.has(token)) {
var remainingInterceptors = [];
try {
for (var _b = __values(this.interceptors.preResolution.getAll(token)), _c = _b.next(); !_c.done; _c = _b.next()) {
var interceptor = _c.value;
if (interceptor.options.frequency != "Once") {
remainingInterceptors.push(interceptor);
}
interceptor.callback(token, resolutionType);
}
}
catch (e_1_1) { e_1 = { error: e_1_1 }; }
finally {
try {
if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
}
finally { if (e_1) throw e_1.error; }
}
this.interceptors.preResolution.setAll(token, remainingInterceptors);
}
};
InternalDependencyContainer.prototype.executePostResolutionInterceptor = function (token, result, resolutionType) {
var e_2, _a;
if (this.interceptors.postResolution.has(token)) {
var remainingInterceptors = [];
try {
for (var _b = __values(this.interceptors.postResolution.getAll(token)), _c = _b.next(); !_c.done; _c = _b.next()) {
var interceptor = _c.value;
if (interceptor.options.frequency != "Once") {
remainingInterceptors.push(interceptor);
}
interceptor.callback(token, result, resolutionType);
}
}
catch (e_2_1) { e_2 = { error: e_2_1 }; }
finally {
try {
if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
}
finally { if (e_2) throw e_2.error; }
}
this.interceptors.postResolution.setAll(token, remainingInterceptors);
}
};
InternalDependencyContainer.prototype.resolveRegistration = function (registration, context) {
this.ensureNotDisposed();
if (registration.options.lifecycle === Lifecycle.ResolutionScoped &&
context.scopedResolutions.has(registration)) {
return context.scopedResolutions.get(registration);
}
var isSingleton = registration.options.lifecycle === Lifecycle.Singleton;
var isContainerScoped = registration.options.lifecycle === Lifecycle.ContainerScoped;
var returnInstance = isSingleton || isContainerScoped;
var resolved;
if (isValueProvider(registration.provider)) {
resolved = registration.provider.useValue;
}
else if (isTokenProvider(registration.provider)) {
resolved = returnInstance
? registration.instance ||
(registration.instance = this.resolve(registration.provider.useToken, context))
: this.resolve(registration.provider.useToken, context);
}
else if (isClassProvider(registration.provider)) {
resolved = returnInstance
? registration.instance ||
(registration.instance = this.construct(registration.provider.useClass, context))
: this.construct(registration.provider.useClass, context);
}
else if (isFactoryProvider(registration.provider)) {
resolved = registration.provider.useFactory(this);
}
else {
resolved = this.construct(registration.provider, context);
}
if (registration.options.lifecycle === Lifecycle.ResolutionScoped) {
context.scopedResolutions.set(registration, resolved);
}
return resolved;
};
InternalDependencyContainer.prototype.resolveAll = function (token, context, isOptional) {
var _this = this;
if (context === void 0) { context = new ResolutionContext(); }
if (isOptional === void 0) { isOptional = false; }
this.ensureNotDisposed();
var registrations = this.getAllRegistrations(token);
if (!registrations && isNormalToken(token)) {
if (isOptional) {
return [];
}
throw new Error("Attempted to resolve unregistered dependency token: \"" + token.toString() + "\"");
}
this.executePreResolutionInterceptor(token, "All");
if (registrations) {
var result_1 = registrations.map(function (item) {
return _this.resolveRegistration(item, context);
});
this.executePostResolutionInterceptor(token, result_1, "All");
return result_1;
}
var result = [this.construct(token, context)];
this.executePostResolutionInterceptor(token, result, "All");
return result;
};
InternalDependencyContainer.prototype.isRegistered = function (token, recursive) {
if (recursive === void 0) { recursive = false; }
this.ensureNotDisposed();
return (this._registry.has(token) ||
(recursive &&
(this.parent || false) &&
this.parent.isRegistered(token, true)));
};
InternalDependencyContainer.prototype.reset = function () {
this.ensureNotDisposed();
this._registry.clear();
this.interceptors.preResolution.clear();
this.interceptors.postResolution.clear();
};
InternalDependencyContainer.prototype.clearInstances = function () {
var e_3, _a;
this.ensureNotDisposed();
try {
for (var _b = __values(this._registry.entries()), _c = _b.next(); !_c.done; _c = _b.next()) {
var _d = __read(_c.value, 2), token = _d[0], registrations = _d[1];
this._registry.setAll(token, registrations
.filter(function (registration) { return !isValueProvider(registration.provider); })
.map(function (registration) {
registration.instance = undefined;
return registration;
}));
}
}
catch (e_3_1) { e_3 = { error: e_3_1 }; }
finally {
try {
if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
}
finally { if (e_3) throw e_3.error; }
}
};
InternalDependencyContainer.prototype.createChildContainer = function () {
var e_4, _a;
this.ensureNotDisposed();
var childContainer = new InternalDependencyContainer(this);
try {
for (var _b = __values(this._registry.entries()), _c = _b.next(); !_c.done; _c = _b.next()) {
var _d = __read(_c.value, 2), token = _d[0], registrations = _d[1];
if (registrations.some(function (_a) {
var options = _a.options;
return options.lifecycle === Lifecycle.ContainerScoped;
})) {
childContainer._registry.setAll(token, registrations.map(function (registration) {
if (registration.options.lifecycle === Lifecycle.ContainerScoped) {
return {
provider: registration.provider,
options: registration.options
};
}
return registration;
}));
}
}
}
catch (e_4_1) { e_4 = { error: e_4_1 }; }
finally {
try {
if (_c && !_c.done && (_a = _b.return)) _a.call(_b);
}
finally { if (e_4) throw e_4.error; }
}
return childContainer;
};
InternalDependencyContainer.prototype.beforeResolution = function (token, callback, options) {
if (options === void 0) { options = { frequency: "Always" }; }
this.interceptors.preResolution.set(token, {
callback: callback,
options: options
});
};
InternalDependencyContainer.prototype.afterResolution = function (token, callback, options) {
if (options === void 0) { options = { frequency: "Always" }; }
this.interceptors.postResolution.set(token, {
callback: callback,
options: options
});
};
InternalDependencyContainer.prototype.dispose = function () {
return __awaiter(this, void 0, void 0, function () {
var promises;
return __generator(this, function (_a) {
switch (_a.label) {
case 0:
this.disposed = true;
promises = [];
this.disposables.forEach(function (disposable) {
var maybePromise = disposable.dispose();
if (maybePromise) {
promises.push(maybePromise);
}
});
return [4, Promise.all(promises)];
case 1:
_a.sent();
return [2];
}
});
});
};
InternalDependencyContainer.prototype.getRegistration = function (token) {
if (this.isRegistered(token)) {
return this._registry.get(token);
}
if (this.parent) {
return this.parent.getRegistration(token);
}
return null;
};
InternalDependencyContainer.prototype.getAllRegistrations = function (token) {
if (this.isRegistered(token)) {
return this._registry.getAll(token);
}
if (this.parent) {
return this.parent.getAllRegistrations(token);
}
return null;
};
InternalDependencyContainer.prototype.construct = function (ctor, context) {
var _this = this;
if (ctor instanceof DelayedConstructor) {
return ctor.createProxy(function (target) {
return _this.resolve(target, context);
});
}
var instance = (function () {
var paramInfo = typeInfo.get(ctor);
if (!paramInfo || paramInfo.length === 0) {
if (ctor.length === 0) {
return new ctor();
}
else {
throw new Error("TypeInfo not known for \"" + ctor.name + "\"");
}
}
var params = paramInfo.map(_this.resolveParams(context, ctor));
return new (ctor.bind.apply(ctor, __spread([void 0], params)))();
})();
if (isDisposable(instance)) {
this.disposables.add(instance);
}
return instance;
};
InternalDependencyContainer.prototype.resolveParams = function (context, ctor) {
var _this = this;
return function (param, idx) {
var _a, _b, _c;
try {
if (isTokenDescriptor(param)) {
if (isTransformDescriptor(param)) {
return param.multiple
? (_a = _this.resolve(param.transform)).transform.apply(_a, __spread([_this.resolveAll(param.token, new ResolutionContext(), param.isOptional)], param.transformArgs)) : (_b = _this.resolve(param.transform)).transform.apply(_b, __spread([_this.resolve(param.token, context, param.isOptional)], param.transformArgs));
}
else {
return param.multiple
? _this.resolveAll(param.token, new ResolutionContext(), param.isOptional)
: _this.resolve(param.token, context, param.isOptional);
}
}
else if (isTransformDescriptor(param)) {
return (_c = _this.resolve(param.transform, context)).transform.apply(_c, __spread([_this.resolve(param.token, context)], param.transformArgs));
}
return _this.resolve(param, context);
}
catch (e) {
throw new Error(formatErrorCtor(ctor, idx, e));
}
};
};
InternalDependencyContainer.prototype.ensureNotDisposed = function () {
if (this.disposed) {
throw new Error("This container has been disposed, you cannot interact with a disposed container");
}
};
return InternalDependencyContainer;
}());
export var instance = new InternalDependencyContainer();
export default instance;
+17
View File
@@ -0,0 +1,17 @@
import { __read, __spread } from "tslib";
function formatDependency(params, idx) {
if (params === null) {
return "at position #" + idx;
}
var argName = params.split(",")[idx].trim();
return "\"" + argName + "\" at position #" + idx;
}
function composeErrorMessage(msg, e, indent) {
if (indent === void 0) { indent = " "; }
return __spread([msg], e.message.split("\n").map(function (l) { return indent + l; })).join("\n");
}
export function formatErrorCtor(ctor, paramIdx, error) {
var _a = __read(ctor.toString().match(/constructor\(([\w, ]+)\)/) || [], 2), _b = _a[1], params = _b === void 0 ? null : _b;
var dep = formatDependency(params, paramIdx);
return composeErrorMessage("Cannot inject the dependency " + dep + " of \"" + ctor.name + "\" constructor. Reason:", error);
}
View File
+3
View File
@@ -0,0 +1,3 @@
export { default as instanceCachingFactory } from "./instance-caching-factory";
export { default as instancePerContainerCachingFactory } from "./instance-per-container-caching-factory";
export { default as predicateAwareClassFactory } from "./predicate-aware-class-factory";
@@ -0,0 +1,9 @@
export default function instanceCachingFactory(factoryFunc) {
var instance;
return function (dependencyContainer) {
if (instance == undefined) {
instance = factoryFunc(dependencyContainer);
}
return instance;
};
}
@@ -0,0 +1,11 @@
export default function instancePerContainerCachingFactory(factoryFunc) {
var cache = new WeakMap();
return function (dependencyContainer) {
var instance = cache.get(dependencyContainer);
if (instance == undefined) {
instance = factoryFunc(dependencyContainer);
cache.set(dependencyContainer, instance);
}
return instance;
};
}
@@ -0,0 +1,17 @@
export default function predicateAwareClassFactory(predicate, trueConstructor, falseConstructor, useCaching) {
if (useCaching === void 0) { useCaching = true; }
var instance;
var previousPredicate;
return function (dependencyContainer) {
var currentPredicate = predicate(dependencyContainer);
if (!useCaching || previousPredicate !== currentPredicate) {
if ((previousPredicate = currentPredicate)) {
instance = dependencyContainer.resolve(trueConstructor);
}
else {
instance = dependencyContainer.resolve(falseConstructor);
}
}
return instance;
};
}
+9
View File
@@ -0,0 +1,9 @@
if (typeof Reflect === "undefined" || !Reflect.getMetadata) {
throw new Error("tsyringe requires a reflect polyfill. Please add 'import \"reflect-metadata\"' to the top of your entry point.");
}
export { Lifecycle } from "./types";
export * from "./decorators";
export * from "./factories";
export * from "./providers";
export { delay } from "./lazy-helpers";
export { instance as container } from "./dependency-container";

Some files were not shown because too many files have changed in this diff Show More