##// END OF EJS Templates
working on IoC configuration
working on IoC configuration

File last commit:

r114:475b8ce3e850 ioc ts support
r114:475b8ce3e850 ioc ts support
Show More
Container.ts
138 lines | 4.3 KiB | video/mp2t | TypeScriptLexer
/ src / main / ts / di / Container.ts
cin
changed the project structure
r49 import { ActivationContext } from "./ActivationContext";
import { ValueDescriptor } from "./ValueDescriptor";
import { ActivationError } from "./ActivationError";
cin
working on IoC configuration
r114 import { isDescriptor, ServiceMap, Descriptor } from "./interfaces";
cin
changed the project structure
r49 import { TraceSource } from "../log/TraceSource";
import { Configuration } from "./Configuration";
import { Cancellation } from "../Cancellation";
cin
working on IoC configuration
r114 import { MapOf } from "../interfaces";
cin
changed the project structure
r49
const trace = TraceSource.get("@implab/core/di/ActivationContext");
cin
working on IoC configuration
r114 export class Container<S extends { container?: Container<S> }> {
readonly _services: ServiceMap<S>;
cin
changed the project structure
r49
cin
working on IoC configuration
r114 readonly _cache: MapOf<any>;
readonly _cleanup: (() => void)[];
cin
changed the project structure
r49
cin
working on IoC configuration
r114 readonly _root: Container<S>;
cin
changed the project structure
r49
cin
working on IoC configuration
r114 readonly _parent?: Container<S>;
cin
changed the project structure
r49
cin
working on IoC configuration
r114 _disposed: boolean;
cin
changed the project structure
r49
cin
working on IoC configuration
r114 constructor(parent?: Container<S>) {
cin
changed the project structure
r49 this._parent = parent;
this._services = parent ? Object.create(parent._services) : {};
this._cache = {};
this._cleanup = [];
this._root = parent ? parent.getRootContainer() : this;
this._services.container = new ValueDescriptor(this);
cin
working on IoC configuration
r114 this._disposed = false;
cin
changed the project structure
r49 }
getRootContainer() {
return this._root;
}
getParent() {
return this._parent;
}
cin
working on IoC configuration
r114 resolve<K extends keyof S, T extends S[K] = S[K]>(name: K, def?: T) {
cin
changed the project structure
r49 trace.debug("resolve {0}", name);
const d = this._services[name];
if (d === undefined) {
cin
working on IoC configuration
r114 if (def !== undefined)
cin
changed the project structure
r49 return def;
else
throw new Error("Service '" + name + "' isn't found");
cin
working on IoC configuration
r114 } else {
cin
changed the project structure
r49
cin
working on IoC configuration
r114 const context = new ActivationContext<S>(this, this._services);
try {
return context.activate(d as Descriptor<T>, name.toString());
} catch (error) {
throw new ActivationError(name.toString(), context.getStack(), error);
}
cin
changed the project structure
r49 }
}
/**
* @deprecated use resolve() method
*/
cin
working on IoC configuration
r114 getService<K extends keyof S>(name: K, def?: S[K]) {
return this.resolve(name, def);
cin
changed the project structure
r49 }
cin
working on IoC configuration
r114 register<K extends keyof S>(name: K, service: Descriptor<S[K]>): this;
register(services: ServiceMap<S>): this;
register<K extends keyof S>(nameOrCollection: K | ServiceMap<S>, service?: Descriptor<S[K]>) {
cin
changed the project structure
r49 if (arguments.length === 1) {
cin
working on IoC configuration
r114 const data = nameOrCollection as ServiceMap<S>;
for (const name in data) {
if (Object.prototype.hasOwnProperty.call(data, name)) {
this.register(name, data[name] as Descriptor<S[keyof S]>);
}
}
cin
changed the project structure
r49 } else {
if (!isDescriptor(service))
throw new Error("The service parameter must be a descriptor");
cin
working on IoC configuration
r114 this._services[nameOrCollection as K] = service;
cin
changed the project structure
r49 }
return this;
}
cin
working on IoC configuration
r114 onDispose(callback: () => void) {
cin
changed the project structure
r49 if (!(callback instanceof Function))
throw new Error("The callback must be a function");
this._cleanup.push(callback);
}
dispose() {
cin
working on IoC configuration
r114 if (this._disposed)
return;
this._disposed = true;
for (const f of this._cleanup)
f();
cin
changed the project structure
r49 }
/**
* @param{String|Object} config
* The configuration of the contaier. Can be either a string or an object,
* if the configuration is an object it's treated as a collection of
* services which will be registed in the contaier.
*
* @param{Function} opts.contextRequire
* The function which will be used to load a configuration or types for services.
*
*/
cin
working on support commonjs modules format
r59 async configure(config: string | object, opts?: any, ct = Cancellation.none) {
cin
changed the project structure
r49 const c = new Configuration(this);
if (typeof (config) === "string") {
cin
working on support commonjs modules format
r59 return c.loadConfiguration(config, opts && opts.contextRequire, ct);
cin
changed the project structure
r49 } else {
return c.applyConfiguration(config, opts && opts.contextRequire, ct);
}
}
cin
working on IoC configuration
r114 createChildContainer<S2 extends { container?: Container<S & S2> } = S>(): Container<S & S2> {
return new Container<S & S2>(this as any);
cin
changed the project structure
r49 }
cin
Initial work on typescript support for the container configuration
r107 has(id: string | number) {
cin
changed the project structure
r49 return id in this._cache;
}
cin
Initial work on typescript support for the container configuration
r107 get(id: string | number) {
cin
changed the project structure
r49 return this._cache[id];
}
cin
Initial work on typescript support for the container configuration
r107 store(id: string | number, value: any) {
cin
changed the project structure
r49 return (this._cache[id] = value);
}
}