I have written a wrapper for httpclient which sets the config from the observable and also uses toastr in case of error. It doesn't fail when the other two constructor injections are removed.
In case I mock RestService, I cant use HttpTestingController which provides other useful methods for httpclient testing
rest.service.ts
@Injectable()
export class RestService {
public baseUrl = null;
constructor(
private http: HttpClient,
private appConfigService: AppConfigService,
private toast: ToastNotificationService,
) {
this.getConfig();
}
get<T>(url, showError = true): Observable<any> {
return this.http.get<T>(this.baseUrl + url).pipe(
catchError((error: HttpErrorResponse) => {
return this.showError(error, showError);
}),
);
}
private getConfig() {
this.appConfigService.appConfig$.subscribe(env => {
this.baseUrl = env.backendUrl + API_PREFIX;
});
}
private showError(error: HttpErrorResponse, showError) {
let message = Helpers.getErrorMessageFromObject(error);
if (showError && message) this.toast.showError(message);
return throwError(error);
}
}
rest.service.spec.ts
import { HttpClientTestingModule, HttpTestingController } from '@angular/common/http/testing';
import { TestBed } from '@angular/core/testing';
import { of } from 'rxjs';
import { AppConfigService } from './app-config.service';
import { RestService } from './rest.service';
import { ToastNotificationService } from './toast-notification.service';
describe('RestService', () => {
let service: RestService;
let httpMock: HttpTestingController;
const testData = { name: 'Test Data' };
beforeEach(() => {
TestBed.configureTestingModule({
imports: [HttpClientTestingModule],
providers: [
RestService,
{
provide: AppConfigService,
useValue: jasmine.createSpyObj({
appConfig$: of(),
}),
},
{
provide: ToastNotificationService,
useValue: jasmine.createSpyObj({
showError: function () { },
}),
},
],
});
service = TestBed.get(RestService);
httpMock = TestBed.get(HttpTestingController);
});
afterEach(() => {
httpMock.verify();
});
it('should be created', () => {
expect(service).toBeTruthy();
});
it('should get the data successful', () => {
service.baseUrl = '';
const endpoint = '/api/v1/features/1';
service.get(endpoint).subscribe((data: any) => {
expect(data).toEqual(testData);
expect(service.get).toHaveBeenCalled();
expect(service.get).toHaveBeenCalledWith(endpoint);
});
const req = httpMock.expectOne(endpoint);
expect(req.request.method).toBe('GET');
req.flush(testData);
});
});