Reputation: 10838
I have a literal type as a constructor parameter on my service:
export type MyType = 'val1' | 'val2';
@Injectable()
export class MyService {
myType: MyType;
constructor(private appService: AppService, private myType: MyType = 'val2') {
this.myType = myType;
}
}
I have an error on build time
Nest can't resolve dependencies of the MyService (AppService, ?). Please make sure that the argument String at index [1] is available in the AppModule context.
Potential solutions:
- If String is a provider, is it part of the current AppModule?
- If String is exported from a separate @Module, is that module imported within AppModule?
@Module({
imports: [ /* the Module containing String */ ]
})
How would you fix that?
that is my AppModule:
@Module({
imports: [HttpModule],
controllers: [AppController],
providers: [AppService, MyService, HttpClient],
})
export class AppModule {}
Upvotes: 4
Views: 4105
Reputation: 11
this problem is caused by @Injectable()
Decorator, this decorator makes the class gets injected by nestjs in the start of the application, if you are planning to instantiate your class with different parameters it's better to use the new Class()
statement.
One use of it it in the Logger
[class][1], this class is not an injectable and needs to be instantiated every time when you need to use it.
Example:
export type MyType = 'val1' | 'val2';
export class MyService {
myType: MyType;
constructor(private appService: AppService, private myType: MyType = 'val2') {
this.myType = myType;
}
}
and then, inside another class.
#import the appService, Myservice and MyType
export class MyClass {
myService = new MyService(appservice, myType)
}
Hoping that helps!
Upvotes: -1
Reputation: 70570
With NestJS, you need to provide constructor arguments via providers
. Nest uses classes
usually to know what injection token to work with, as classes persist in both Typescript and JavaScript. However, you can use the @Inject()
decorator with your own injection token and custom value to ensure that Nest injects the value properly. This will look something like this:
@Module({
providers: [
MyService,
{
provide: 'MyToken', // this can be a symbol or a string
useValue: 'val2',
}
AppService,
],
})
export class AppModule {}
export type MyType = 'val1' | 'val2';
@Injectable()
export class MyService {
constructor(
private appService: AppService,
// this token MUST match exactly to the one in the `provide` property of the custom provider
@Inject('MyToken') private myType: MyType
) {}
}
If you want to add other dependencies, just make sure they are available to the module.
The other option is to mark myType
as @Optional()
which will allow Nest to bypass the injection if it is unresolvable, then you can easily still use the default value as you were before
Upvotes: 5