Skip to content

Commit

Permalink
fix(): use class reference as injection token
Browse files Browse the repository at this point in the history
For class providers use a class reference instead of a class name as an injection token to address dependency injection conflicts when two classes share the same name.

resolve #5591
  • Loading branch information
tooleks committed Oct 28, 2020
1 parent d33f4a6 commit c58036c
Show file tree
Hide file tree
Showing 4 changed files with 13 additions and 15 deletions.
6 changes: 2 additions & 4 deletions packages/common/decorators/core/inject.decorator.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@ import {
PROPERTY_DEPS_METADATA,
SELF_DECLARED_DEPS_METADATA,
} from '../../constants';
import { isFunction, isUndefined } from '../../utils/shared.utils';
import { isUndefined } from '../../utils/shared.utils';

/**
* Decorator that marks a constructor parameter as a target for
Expand Down Expand Up @@ -35,9 +35,7 @@ import { isFunction, isUndefined } from '../../utils/shared.utils';
*/
export function Inject<T = any>(token?: T) {
return (target: object, key: string | symbol, index?: number) => {
token = token || Reflect.getMetadata('design:type', target, key);
const type =
token && isFunction(token) ? ((token as any) as Function).name : token;
const type = token || Reflect.getMetadata('design:type', target, key);

if (!isUndefined(index)) {
let dependencies =
Expand Down
2 changes: 1 addition & 1 deletion packages/common/test/decorators/inject.decorator.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ describe('@Inject', () => {
const metadata = Reflect.getMetadata(SELF_DECLARED_DEPS_METADATA, Test);

const expectedMetadata = [
{ index: 2, param: opaqueToken.name },
{ index: 2, param: opaqueToken },
{ index: 1, param: 'test2' },
{ index: 0, param: 'test' },
];
Expand Down
11 changes: 5 additions & 6 deletions packages/core/injector/injector.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,6 @@ import { Controller } from '@nestjs/common/interfaces/controllers/controller.int
import { Injectable } from '@nestjs/common/interfaces/injectable.interface';
import { Type } from '@nestjs/common/interfaces/type.interface';
import {
isFunction,
isNil,
isObject,
isString,
Expand Down Expand Up @@ -54,9 +53,9 @@ export interface InjectorDependencyContext {
*/
key?: string | symbol;
/**
* The name of the function or injection token
* The function itself, the name of the function, or injection token.
*/
name?: string | symbol;
name?: Function | string | symbol;
/**
* The index of the dependency which gets injected
* from the dependencies array
Expand Down Expand Up @@ -322,7 +321,7 @@ export class Injector {
const token = this.resolveParamToken(wrapper, param);
return this.resolveComponentInstance<T>(
moduleRef,
isFunction(token) ? (token as Type<any>).name : token,
token,
dependencyContext,
wrapper,
contextId,
Expand Down Expand Up @@ -412,7 +411,7 @@ export class Injector {
}

public async lookupComponent<T = any>(
providers: Map<string | symbol, InstanceWrapper>,
providers: Map<Function | string | symbol, InstanceWrapper>,
moduleRef: Module,
dependencyContext: InjectorDependencyContext,
wrapper: InstanceWrapper<T>,
Expand Down Expand Up @@ -557,7 +556,7 @@ export class Injector {
try {
const dependencyContext = {
key: item.key,
name: item.name as string,
name: item.name as Function | string | symbol,
};
if (this.isInquirer(item.name, parentInquirer)) {
return parentInquirer && parentInquirer.instance;
Expand Down
9 changes: 5 additions & 4 deletions packages/core/test/injector/injector.spec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -44,20 +44,20 @@ describe('Injector', () => {
isResolved: false,
});
depOne = new InstanceWrapper({
name: 'DependencyOne',
name: DependencyOne,
metatype: DependencyOne,
instance: Object.create(DependencyOne.prototype),
isResolved: false,
});
depTwo = new InstanceWrapper({
name: 'DependencyTwo',
name: DependencyTwo,
metatype: DependencyTwo,
instance: Object.create(DependencyOne.prototype),
isResolved: false,
});
moduleDeps.providers.set('MainTest', mainTest);
moduleDeps.providers.set('DependencyOne', depOne);
moduleDeps.providers.set('DependencyTwo', depTwo);
moduleDeps.providers.set(DependencyOne, depOne);
moduleDeps.providers.set(DependencyTwo, depTwo);
moduleDeps.providers.set('MainTestResolved', {
...mainTest,
isResolved: true,
Expand Down Expand Up @@ -616,6 +616,7 @@ describe('Injector', () => {
});
});
});

describe('applyProperties', () => {
describe('when instance is not an object', () => {
it('should return undefined', () => {
Expand Down

0 comments on commit c58036c

Please sign in to comment.