Сбой теста httpinterceptor - PullRequest
       6

Сбой теста httpinterceptor

0 голосов
/ 25 сентября 2018

Я использую Angular 6 и пишу модульный тест, чтобы проверить, когда HTTP-запрос получает ошибку, отличную от 401 или 404.

При отладке теста в карма-бегунке я могу получить строку кода с надписью this.router.navigate(['/genericErrorPage']) для выполнения из-за настройки теста, но не могу пройти тест, и я не уверенпочему тест провалился, так как router.navigate () был фактически вызван во время выполнения теста.

Я пытался шпионить за объектом router в тесте и объектом mockRouter в тесте, но ни один из них не заставил тест пройти.При использовании любого шпиона я получаю сообщение «СБОЙ: Ожидается, что шпионская навигация была вызвана».

export class ErrorInterceptor implements HttpInterceptor {
  constructor(private router: Router) {}

  intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
return next.handle(request).pipe(
  catchError(err => {
    if (err.status !== 404 || err.status !== 401) {
      this.router.navigate(['/genericErrorPage']);
    }
    const error = err.statusText;
    return throwError(error);
  })
);

}}

fdescribe('ErrorInterceptor', () => {
  class MockRouter {
  navigate = function() {};
}
let router: Router;
let interceptor: ErrorInterceptor;
const mockRouter: MockRouter = new MockRouter();

beforeEach(() => {
TestBed.configureTestingModule({
  imports: [HttpClientTestingModule],
  providers: [
    {
      provide: HTTP_INTERCEPTORS,
      useClass: ErrorInterceptor,
      multi: true
    },
    { provide: Router, useClass: MockRouter }
  ]
});

router = TestBed.get(Router);
interceptor = new ErrorInterceptor(router);
});

fit('should use router to navigate to error page on error', done => {
  spyOn(router, 'navigate');
   expect((interceptor as any) instanceof ErrorInterceptor).toBeTruthy();
  const next: any = {
    handle: (request: HttpRequest<any>) => {
    expect(router.navigate).toHaveBeenCalled();
    return Observable.create({ hello: 'world' });
  }
 };
   const req = new HttpRequest<any>('GET', 'http://localhost/any/api');
   interceptor.intercept(req, next).subscribe(obj => done());
  });
});

1 Ответ

0 голосов
/ 27 сентября 2018

вот что я в итоге сделал:

import { Injectable } from '@angular/core';
import { HttpRequest, HttpHandler, HttpEvent, HttpInterceptor } from 
'@angular/common/http';
import { Observable, throwError } from 'rxjs';
import { catchError } from 'rxjs/operators';
import { Router } from '@angular/router';

@Injectable()
export class ErrorInterceptor implements HttpInterceptor {
   constructor(private router: Router) {}

   intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
     return next.handle(request).pipe(
        catchError(err => {
          if (err.status === 401) {
          }
          if (err.status === 404) {
          } else {
              this.router.navigate(['/genericErrorPage']);
          }

         return throwError(err);
        })
      );
     }
    }


import { ErrorInterceptor } from './error-interceptor';
import { Router } from '@angular/router';
import { mock } from 'ts-mockito/lib/ts-mockito';

import { HTTP_INTERCEPTORS } from '@angular/common/http';
import { TestBed } from '@angular/core/testing';
import { HttpClientTestingModule, HttpTestingController } from '@angular/common/http/testing';
import { EmployeeHomeService } from '../../services/employee/employee-home/employee-home.service';
import { USER_PROFILE_API_LOCATION } from '../../constants';

describe('ErrorInterceptor', () => {
   class MockRouter {
    navigate = function() {};
   }
  let employeeHomeService: EmployeeHomeService; //still need to make this generic/mock in case the EmployeeHomeService changes
  let httpMock: HttpTestingController;
  let mockRouter: MockRouter;
  beforeEach(() => {
    TestBed.configureTestingModule({
      imports: [HttpClientTestingModule],
       providers: [
        EmployeeHomeService,
        {
           provide: HTTP_INTERCEPTORS,
           useClass: ErrorInterceptor,
           multi: true
        },
         { provide: Router, useClass: MockRouter }
       ]
     });
    mockRouter = TestBed.get(Router);
    employeeHomeService = TestBed.get(EmployeeHomeService);
    httpMock = TestBed.get(HttpTestingController);
   });

  it('should have router redirect to error page on HTTP 500', done => {
    spyOn(mockRouter, 'navigate');
    employeeHomeService.retrieveEmployee().subscribe(
      res => {
        expect(false).toEqual(true); //should not hit here, but if it does, test will fail
        done();
      },
      err => {
     expect(mockRouter.navigate).toHaveBeenCalledWith(['/genericErrorPage']);
         done();
      }
    );

    httpMock.expectOne(USER_PROFILE_API_LOCATION).error(new ErrorEvent('500 
error'), {
       status: 500
     });
     httpMock.verify();
   });
 });



 import { Injectable } from '@angular/core';
 import { HttpClient } from '@angular/common/http';
 import { Observable } from 'rxjs';
 import { Employee } from '../../../containers/employee/models/employee';
 import { USER_PROFILE_API_LOCATION } from '../../../constants';

 @Injectable({
   providedIn: 'root'
})
 export class EmployeeHomeService {
   constructor(private http: HttpClient) {}

  retrieveEmployee(): Observable<Employee> {
    return this.http.get<Employee>(USER_PROFILE_API_LOCATION);
  }
 }
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...