##// END OF EJS Templates
Fixed container interfaces, separated ServiceContainer
Fixed container interfaces, separated ServiceContainer

File last commit:

r144:f97a113c3209 v1.4.0-rc4 default
r144:f97a113c3209 v1.4.0-rc4 default
Show More
LifetimeManager.ts
197 lines | 5.4 KiB | video/mp2t | TypeScriptLexer
/ src / main / ts / di / LifetimeManager.ts
cin
working on lifetime management
r129 import { IDestroyable, MapOf } from "../interfaces";
cin
Fixed container interfaces, separated ServiceContainer
r144 import { argumentNotNull, isDestroyable, argumentNotEmptyString } from "../safe";
import { ILifetime, ServiceContainer } from "./interfaces";
cin
working on services lifetime
r130 import { ActivationContext } from "./ActivationContext";
cin
working on lifetime management
r129
function safeCall(item: () => void) {
try {
item();
} catch {
cin
Refactoring, working on services lifetime
r131 // silence!
cin
working on lifetime management
r129 }
}
cin
Completely removed IoC annotations...
r135 const emptyLifetime: ILifetime = Object.freeze({
cin
Refactoring, working on services lifetime
r131 has() {
return false;
},
cin
working on fluent configuration, di annotations removed
r134 initialize() {
cin
Refactoring, working on services lifetime
r131
},
get() {
throw new Error("The specified item isn't registered with this lifetime manager");
},
store() {
// does nothing
}
cin
Completely removed IoC annotations...
r135 });
cin
Refactoring, working on services lifetime
r131
cin
Completely removed IoC annotations...
r135 const unknownLifetime: ILifetime = Object.freeze({
cin
working on fluent configuration, di annotations removed
r134 has() {
cin
Completely removed IoC annotations...
r135 return false;
cin
working on fluent configuration, di annotations removed
r134 },
initialize() {
throw new Error("Can't call initialize on the unknown lifetime object");
},
get() {
throw new Error("The lifetime object isn't initialized");
},
store() {
throw new Error("Can't store a value in the unknown lifetime object");
}
cin
Completely removed IoC annotations...
r135 });
cin
working on fluent configuration, di annotations removed
r134
cin
working on fluent configuration
r133 let nextId = 0;
cin
Fixed container interfaces, separated ServiceContainer
r144 const singletons: any = {};
cin
Completely removed IoC annotations...
r135
export class LifetimeManager implements IDestroyable {
cin
working on lifetime management
r129 private _cleanup: (() => void)[] = [];
private _cache: MapOf<any> = {};
private _destroyed = false;
cin
working on fluent configuration
r132 private _pending: MapOf<boolean> = {};
cin
working on fluent configuration, di annotations removed
r134 create(): ILifetime {
cin
working on services lifetime
r130 const self = this;
cin
working on fluent configuration
r133 const id = ++nextId;
cin
working on services lifetime
r130 return {
has() {
return (id in self._cache);
},
get() {
const t = self._cache[id];
if (t === undefined)
throw new Error(`The item with with the key ${id} isn't found`);
return t;
},
cin
working on lifetime management
r129
cin
working on fluent configuration, di annotations removed
r134 initialize() {
cin
working on fluent configuration
r132 if (self._pending[id])
cin
working on services lifetime
r130 throw Error(`Cyclic reference detected: the item with the key ${id} is already activating.`);
cin
working on fluent configuration
r132 self._pending[id] = true;
cin
working on services lifetime
r130 },
store(item: any, cleanup?: (item: any) => void) {
argumentNotNull(id, "id");
argumentNotNull(item, "item");
if (this.has())
throw new Error(`The item with with the key ${id} already registered with this lifetime manager`);
cin
working on fluent configuration
r132 delete self._pending[id];
cin
working on services lifetime
r130
self._cache[id] = item;
if (self._destroyed)
throw new Error("Lifetime manager is destroyed");
if (cleanup) {
self._cleanup.push(() => cleanup(item));
} else if (isDestroyable(item)) {
self._cleanup.push(() => item.destroy());
}
}
};
cin
working on lifetime management
r129 }
destroy() {
if (!this._destroyed) {
this._destroyed = true;
this._cleanup.forEach(safeCall);
this._cleanup.length = 0;
}
}
cin
working on fluent configuration, di annotations removed
r134 static empty(): ILifetime {
return emptyLifetime;
}
static hierarchyLifetime(): ILifetime {
let _lifetime = unknownLifetime;
return {
initialize(context: ActivationContext<any>) {
if (_lifetime !== unknownLifetime)
throw new Error("Cyclic reference activation detected");
cin
Refactoring, working on services lifetime
r131
cin
Completely removed IoC annotations...
r135 _lifetime = context.getContainer().getLifetimeManager().create();
cin
working on fluent configuration, di annotations removed
r134 },
get() {
return _lifetime.get();
},
has() {
return _lifetime.has();
},
store(item: any, cleanup?: (item: any) => void) {
return _lifetime.store(item, cleanup);
}
};
}
cin
working on lifetime management
r129
cin
working on fluent configuration, di annotations removed
r134 static contextLifetime(): ILifetime {
let _lifetime = unknownLifetime;
return {
initialize(context: ActivationContext<any>) {
if (_lifetime !== unknownLifetime)
throw new Error("Cyclic reference detected");
_lifetime = context.createLifetime();
},
get() {
return _lifetime.get();
},
has() {
return _lifetime.has();
},
store(item: any) {
_lifetime.store(item);
}
};
}
cin
working on fluent configuration
r133
cin
working on fluent configuration, di annotations removed
r134 static singletonLifetime(typeId: string): ILifetime {
cin
Completely removed IoC annotations...
r135 argumentNotEmptyString(typeId, "typeId");
let pending = false;
return {
has() {
return typeId in singletons;
},
get() {
if (!this.has())
throw new Error(`The instance ${typeId} doesn't exists`);
return singletons[typeId];
},
initialize() {
if (pending)
throw new Error("Cyclic reference detected");
pending = true;
},
store(item: any) {
singletons[typeId] = item;
pending = false;
}
};
cin
working on fluent configuration, di annotations removed
r134 }
cin
Fixed container interfaces, separated ServiceContainer
r144 static containerLifetime(container: ServiceContainer<any>) {
cin
working on fluent configuration, di annotations removed
r134 let _lifetime = unknownLifetime;
cin
working on fluent configuration
r133 return {
cin
working on fluent configuration, di annotations removed
r134 initialize(context: ActivationContext<any>) {
if (_lifetime !== unknownLifetime)
throw new Error("Cyclic reference detected");
cin
Completely removed IoC annotations...
r135 _lifetime = container.getLifetimeManager().create();
cin
working on fluent configuration, di annotations removed
r134 },
get() {
return _lifetime.get();
},
has() {
return _lifetime.has();
},
store(item: any) {
_lifetime.store(item);
cin
working on fluent configuration
r133 }
};
}
cin
working on lifetime management
r129 }