角度单元测试 + SignalR - 错误:无法完成与服务器的协商:错误:未找到'



我有一个使用SignalR的Asp.Net核心的Angular 9项目。一切都很好,但我正试图弄清楚如何对Angular内部使用信号服务的组件进行适当的单元测试。

前端使用的库:"@aspnet/signer":"1.1.4";

这种情况只发生在单元测试中。我得到的错误是

Error: Failed to complete negotiation with the server: Error'
Chrome 91.0.4472 (Windows 10.0.0): Executed 1 of 1 SUCCESS (0.304 secs / 0.274 secs)
Error: Failed to start the connection: Error'
Chrome 91.0.4472 (Windows 10.0.0): Executed 1 of 1 SUCCESS (0.304 secs / 0.274 secs)
ERROR: 'Error'
Chrome 91.0.4472 (Windows 10.0.0): Executed 1 of 1 SUCCESS (0.304 secs / 0.274 secs)
ERROR: 'Error'
Chrome 91.0.4472 (Windows 10.0.0): Executed 0 of 1 SUCCESS (0 secs / 0 secs)
Chrome 91.0.4472 (Windows 10.0.0): Executed 1 of 1 SUCCESS (0.3 secs / 0.271 secs)

我的信号服务.ts

import { Injectable } from '@angular/core';
import { HttpClient } from '@angular/common/http';
import { HubConnection } from '@aspnet/signalr';
import * as signalR from '@aspnet/signalr';
import { Observable } from 'rxjs';
import { SignalRConnectionInfo } from './signalr-connection-info.model';
import { Subject } from 'rxjs';
import { ApiService } from '../../api.service';
@Injectable()
export class SignalRService {

private hubConnection: HubConnection;
private apiHubConnection: HubConnection;
modelChange: Subject<any> = new Subject();
change: Subject<any> = new Subject();
constructor(private http: HttpClient, private apiService: ApiService, private authService: AuthenticationService) {}

private getConnectionInfo(): Observable<SignalRConnectionInfo> {
return this.http.get<SignalRConnectionInfo>(this.apiService.functionUrl + 'negotiate');
}

init() {
this.initApiHub();
this.getConnectionInfo().subscribe(info => {
const options = {
accessTokenFactory: () => info.accessToken
};

this.hubConnection = new signalR.HubConnectionBuilder()
.withUrl(info.url, options)
.configureLogging(signalR.LogLevel.Information)
.build();

this.hubConnection.start().catch(err => console.error(err.toString())); // this is the error where it happens. 

this.hubConnection.on('NotifyModelRunStatus', (data: any) => {
this.modelChange.next(data);
});

this.hubConnection.on('NotifyMoveOrderStatus', (data: any) => {
this.modelChange.next(data);
this.change.next(data);
});
});
}
initApi() {
const options = {
accessTokenFactory: () => this.authService.getAccessToken()
};
this.apiHubConnection = new signalR.HubConnectionBuilder()
.withUrl(this.apiService.apiBaseUrl, options)
.configureLogging(signalR.LogLevel.Error)
.build();
this.apiHubConnection.start()
.catch(err => console.error(err ? err.toString() : err));

// Add different SignalR methods from API signalR below
this.apiHubConnection.on('Some change', (data: any) => {
this.change.next(data);
});

this.apiHubConnection.on('Some change', (data: any) => {
this.change.next(data);
});
}
}

显示错误的组件单元测试:

describe('MyComponent', () => {
let component: MyComponent;
let fixture: ComponentFixture<MyComponent>;
let signalRService: SignalRService;

beforeEach(async(() => {
TestBed.configureTestingModule({
imports: [
RouterTestingModule,
CommonModule,
HttpClientTestingModule,
HttpClientModule,
ReactiveFormsModule,
FormsModule,
BrowserAnimationsModule,
],
declarations: [MyComponent],
providers: [
SignalRService,
ApiService,
HttpClient,
],
}).compileComponents();

apiService = TestBed.inject(ApiService);
}));
beforeEach(() => {
fixture = TestBed.createComponent(MyComponent);
component = fixture.componentInstance;
fixture.detectChanges();
},
};
});
it('should create', () => {
expect(component).toBeTruthy();
});
});

我想问题是我没有嘲笑测试组件中的信号器服务。

单元测试的概念意味着您只在测试中测试组件,而不是其他服务。因此,您只需要断言服务中的方法已被调用。

在您的情况下;提供者";在您的测试配置中应该是一个mock对象,而不是一个真正的服务。

describe('MyComponent', () => {
let component: MyComponent;
let fixture: ComponentFixture<MyComponent>;
let signalRServiceSpy: jasmine.SpyObj<SignalRService>; // changed
beforeEach(() => { // changed
signalRServiceSpy = jasmine.createSpyObj('SignalRService', ['yourMethodInService']); // added
TestBed.configureTestingModule({
imports: [
RouterTestingModule,
CommonModule,
HttpClientTestingModule,
HttpClientModule,
ReactiveFormsModule,
FormsModule,
BrowserAnimationsModule,
],
declarations: [MyComponent],
providers: [
{ provide: SignalRService, useValue: signalRServiceSpy }, // changed
ApiService, // this should also use a spy object
HttpClient, // you might not need this
],
}).compileComponents();

apiService = TestBed.inject(ApiService);
});
beforeEach(() => {
fixture = TestBed.createComponent(MyComponent);
component = fixture.componentInstance;
fixture.detectChanges();
});
});

相关内容

最新更新