测试具有抽象类依赖关系的Angular服务时出现问题
我有一个服务,它需要依赖于另一个服务,而另一个服务又需要依赖于两个抽象类测试具有抽象类依赖关系的Angular服务时出现问题,angular,typescript,unit-testing,karma-jasmine,Angular,Typescript,Unit Testing,Karma Jasmine,我有一个服务,它需要依赖于另一个服务,而另一个服务又需要依赖于两个抽象类 (ThemeConfigService -> (SettingsService -> SettingsLoader, NavigationLoader)) 我已经让测试失败了,因为它找不到通过抽象类公开的方法(不是函数异常) 我不知道我怎么才能通过这个考试,网上的各种搜索都没有什么帮助 下面是主题配置服务,我正试图为其充实一个测试“theme-config.service.ts” @可注入({ provide
(ThemeConfigService -> (SettingsService -> SettingsLoader, NavigationLoader))
我已经让测试失败了,因为它找不到通过抽象类公开的方法(不是函数异常)
我不知道我怎么才能通过这个考试,网上的各种搜索都没有什么帮助
下面是主题配置服务,我正试图为其充实一个测试“theme-config.service.ts
”
@可注入({
providedIn:'根'
})
导出类ThemeConfigService{
建造师(
私有平台:平台,
专用路由器:路由器,
私人设置:设置服务
) {
//为简洁起见,删除了代码
}
}
下面是正在测试的服务“settings.service.ts
”
@Injectable()
导出类设置服务{
构造函数(公共设置加载程序:设置加载程序,
公共navigationLoader:navigationLoader){}
公共设置():可观察{
返回此.settingsLoader.retrieveSettings();
}
公共导航():可观察{
返回此.navigationLoader.retrieveNavigation();
}
}
这是设置加载程序
类,导航加载程序看起来完全一样。从设计角度来看,它们必须是独立的类:
导出抽象类设置加载程序{
抽象检索设置():可观察;
}
我的单元测试如下所示:
description('ThemeConfigService',()=>{
让服务:ThemeConfigService;
让路由器:路由器;
在每个之前(()=>{
TestBed.configureTestingModule({
进口:[
RouterTestingModule.withRoutes([])
],
供应商:[
平台,
设置服务,
设置加载程序,
导航加载器
]
});
路由器=试验台。注入(路由器);
service=TestBed.inject(ThemeConfigService);
});
它('应该创建'),异步(注入([平台、路由器、设置服务、设置加载程序、导航加载程序],
(平台:平台,路由器:路由器,设置:设置服务,设置加载程序:设置加载程序,导航加载程序:导航加载程序)=>{
expect(service.toBeTruthy();
})));
});
Karma返回的错误是:
TypeError: this.settingsLoader.retrieveSettings is not a function
which to me proves that it cannot resolve the abstract classes.
出于这个原因,我继续创作了这样的作品:
导出类设置MakeLoader扩展设置Loader{
retrieveSettings():可观察{
归还({});
}
}
并尝试使用这些更改设置加载程序
和导航加载程序
类的注入,然后Karma响应:
NullInjectorError: R3InjectorError(DynamicTestModule)[ThemeConfigService -> SettingsService -> SettingsLoader -> SettingsLoader]:
NullInjectorError: No provider for SettingsLoader!
对于主题配置.service.spec.ts
文件,在每个之前修改的:
beforeach(()=>{
TestBed.configureTestingModule({
进口:[
路由模块,
RouterTestingModule.withRoutes([])
],
供应商:[
平台,
设置服务,
设置MakeLoader,
导航装载机
]
});
路由器=试验台。注入(路由器);
service=TestBed.inject(ThemeConfigService);
});
通常,我不会尝试测试我认为如此复杂的东西。也许我只是没有看到“解决方案”
任何帮助都将不胜感激,因为在这个应用程序的开发过程中,我将有一个类似的场景需要解决。我选择了实例化路线,而不是依赖依赖依赖项注入。这可能不是一个可行的解决方案,并且仍然希望有人能以更好的方式回答最初的问题
更新的主题配置.service.spe.ts
文件的描述
:
description('ThemeConfigService',()=>{
让服务:ThemeConfigService;
let sLoader:设置sLoader;
让nLoader:NavigationLoader;
让服务:设置服务;
在每个之前(()=>{
TestBed.configureTestingModule({
进口:[
RouterTestingModule.withRoutes([])
],
供应商:[
经济服务,
设置服务,
设置加载程序,
导航加载器
]
});
let platform=TestBed.inject(平台);
let router=TestBed.inject(路由器);
sLoader=新设置MakeLoader();
nLoader=新导航fakeloader();
S服务=新设置服务(sLoader、nLoader);
服务=新ThemeSeconService(平台、路由器、sService);
});
它('应该创建',()=>{
expect(service.toBeTruthy();
});
});
我选择了实例化路线,而不是依赖依赖依赖项注入。这可能不是一个可行的解决方案,并且仍然希望有人能以更好的方式回答最初的问题
更新的主题配置.service.spe.ts
文件的描述
:
description('ThemeConfigService',()=>{
让服务:ThemeConfigService;
let sLoader:设置sLoader;
让nLoader:NavigationLoader;
让服务:设置服务;
在每个之前(()=>{
TestBed.configureTestingModule({
进口:[
RouterTestingModule.withRoutes([])
],
供应商:[
经济服务,
设置服务,
设置加载程序,
导航加载器
]
});
let platform=TestBed.inject(平台);
let router=TestBed.inject(路由器);
sLoader=新设置MakeLoader();
nLoader=新导航fakeloader();
S服务=新设置服务(sLoader、nLoader);
服务=新ThemeSeconService(平台、路由器、sService);
});
它('应该创建',()=>{
expect(service.toBeTruthy();
});
});
下面是一个很好的例子,说明了您在
您可以创建实现服务的公共API的任何类的实例,然后在配置测试模块时为该实例提供useValue
。
beforeEach(() => {
// stub UserService for test purposes
userServiceStub = {
isLoggedIn: true,
user: { name: 'Test User' },
};
TestBed.configureTestingModule({
declarations: [ WelcomeComponent ],
providers: [ { provide: UserService, useValue: userServiceStub } ],
// ^^^^^^ Note use of `useValue` ^^^^^^
});
fixture = TestBed.createComponent(WelcomeComponent);
comp = fixture.componentInstance;
// UserService from the root injector
userService = TestBed.inject(UserService);
// get the "welcome" element by CSS selector (e.g., by class name)
el = fixture.nativeElement.querySelector('.welcome');
});