Skip to content

Instantly share code, notes, and snippets.

@SBub
Last active September 17, 2021 13:30
Show Gist options
  • Select an option

  • Save SBub/2cc7368308e25bdf896fb62588c50d98 to your computer and use it in GitHub Desktop.

Select an option

Save SBub/2cc7368308e25bdf896fb62588c50d98 to your computer and use it in GitHub Desktop.
Inversify like container
/*
* register IDepA with no dependencies
*/
@Register('IDepA', [])
class ConcreteA implements IDepA {
doA(): void {
console.log('Doing A');
}
}
@Register('IDepC', ['IDepA'])
class ConcreteC implements IDepC {
constructor(private _concreteA: IDepA) {}
doC(): void {
this._concreteA.doA()
console.log('Doing C');
}
}
/*
* inversify like container
*/
export class IoCContainer {
private _dependencies: {[key: string]: Object} = {}
private constructor() {
if(IoCContainer._instance) {
throw new Error('Singleton class. Cannot instantiate using new')
}
IoCContainer._instance = this
}
private static _instance: IoCContainer = new IoCContainer()
public static get instance() {
return IoCContainer._instance
}
register(name: string, dependencies: string[], implementation: any) {
if(this._dependencies[name]) {
throw new Error('Dependency already registered')
}
let dependenciesImplementations = this.getDependenciesImplementations(dependencies)
this._dependencies[name] = new implementation(...dependenciesImplementations)
}
resolve<T>(name: string): T {
if(!this._dependencies[name]) {
throw new Error(`Unresolved dependency ${name}`)
}
return this._dependencies[name] as T
}
private getDependenciesImplementations(names: string[]): Object[] {
return names.map(name => this.resolve(name))
}
}
/*
* TS decorator that registers dependency
*/
export function Register(name: string, dependencies: string[]): Function {
let container = IoCContainer.instance
return function<T extends {new (...args: any[]): {}}>(constructor: T) {
container.register(name, dependencies, constructor)
}
}
interface IDepA {
doA(): void
}
interface IDepC {
doC(): void
}
let container = IoCContainer.instance // Singleton pattern
let a = container.resolve<IDepA>('IDepA')
a.doA()
let c = container.resolve<IDepC>('IDepC')
c.doC()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment