You are on page 1of 6

Create an HTTP Interceptor

Now we will create an HTTP Interceptor to globally intercept and modify


calls. Create a new file httpConfig.interceptor.ts and replace below code
in it.
Interceptors implements HttpInterceptor service to override
the intercept method taking two parameters HttpRequest and HttpHandler.

1 //httpConfig.interceptor.ts
2 import {
3 HttpRequest,
4 HttpHandler,
5 HttpEvent,
6 HttpInterceptor,
7 HttpResponse,
8 HttpErrorResponse
9 } from '@angular/common/http';
10 import { Observable, throwError } from 'rxjs';
11 import { map, catchError } from 'rxjs/operators';
12 import { Injectable } from '@angular/core';
13
14 @Injectable()
15 export class HttpConfigInterceptor implements HttpInterceptor {
16
17 constructor() { }
18
19
20 intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
21
22 const token = "my-token-string-from-server";
23
24 //Authentication by setting header with token value
25 if (token) {
26 request = request.clone({
27 setHeaders: {
28 'Authorization': token
29 }
30 });
31 }
32
33 if (!request.headers.has('Content-Type')) {
34 request = request.clone({
35 setHeaders: {
36 'content-type': 'application/json'
37 }
38 });
39 }
40
41 request = request.clone({
42 headers: request.headers.set('Accept', 'application/json')
43 });
44
45 return next.handle(request).pipe(
46 map((event: HttpEvent<any>) => {
47 if (event instanceof HttpResponse) {
48 console.log('event--->>>', event);
49 }
50 return event;
51 }),
52 catchError((error: HttpErrorResponse) => {
53 console.error(error);
54 return throwError(error);
55 }));
56 }
57
58
59 }
60
As we can’t directly change headers of the request so we make
a clone of request.
To use this interceptor globally we need to import this in
the app.module.ts file and also add in providers array as shown below.

1 //app.module.ts
2 import { NgModule } from '@angular/core';
3 import { BrowserModule } from '@angular/platform-browser';
4 import { RouteReuseStrategy } from '@angular/router';
5
6 import { IonicModule, IonicRouteStrategy } from '@ionic/angular';
7 import { SplashScreen } from '@ionic-native/splash-screen/ngx';
8 import { StatusBar } from '@ionic-native/status-bar/ngx';
9
10 import { AppComponent } from './app.component';
11 import { AppRoutingModule } from './app-routing.module';
12
13 import {
14 HTTP_INTERCEPTORS,
15 HttpClientModule
16 } from '@angular/common/http';
17 import { HttpConfigInterceptor } from './httpConfig.interceptor';
18
19
20 @NgModule({
21 declarations: [AppComponent],
22 entryComponents: [],
23 imports: [
24 BrowserModule,
25 IonicModule.forRoot(),
26 AppRoutingModule,
27 HttpClientModule
28 ],
29 providers: [
30 StatusBar,
31 SplashScreen,
32 { provide: RouteReuseStrategy, useClass: IonicRouteStrategy },
33 {
34 provide: HTTP_INTERCEPTORS,
35 useClass: HttpConfigInterceptor,
36 multi: true
37 }
38 ],
39 bootstrap: [AppComponent]
40 })
41 export class AppModule {}
42

Show Ionic Loader Spinner on HTTP request

Using Interceptors we can easily show/ hide Ionic Spinner loader at one
place. We will import LoadingController and use it show/hide in the
interceptor callbacks. You can check more details on loaders here
Starting a Blog? Find Cheap and Best Hosting Offers

1 //httpConfig.interceptor.ts
2 import {
3 HttpRequest,
4 HttpHandler,
5 HttpEvent,
6 HttpInterceptor,
7 HttpResponse,
8 HttpErrorResponse
9 } from '@angular/common/http';
10 import { Observable, throwError } from 'rxjs';
11 import { map, catchError } from 'rxjs/operators';
12 import { Injectable } from '@angular/core';
13 import { LoadingController } from '@ionic/angular';
14
15 @Injectable()
16 export class HttpConfigInterceptor implements HttpInterceptor {
17 loaderToShow: any;
18 constructor(
19 public loadingController: LoadingController
20 ){}
21
22
23 intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
24
25 const token = "my-token-string-from-server";
26
27 //Authentication by setting header with token value
28 if (token) {
29 request = request.clone({
30 setHeaders: {
31 'Authorization': token
32 }
33 });
34 }
35
36 if (!request.headers.has('Content-Type')) {
37 request = request.clone({
38 setHeaders: {
39 'content-type': 'application/json'
40 }
41 });
42 }
43
44 request = request.clone({
45 headers: request.headers.set('Accept', 'application/json')
46 });
47 this.showLoader();
48 return next.handle(request).pipe(
49 map((event: HttpEvent<any>) => {
50 if (event instanceof HttpResponse) {
51 console.log('event--->>>', event);
52 }
53 this.hideLoader();
54 return event;
55 }),
56 catchError((error: HttpErrorResponse) => {
57 console.error(error);
58 this.hideLoader();
59 return throwError(error);
60 }));
61 }
62
63 showLoader() {
64 this.loaderToShow = this.loadingController.create({
65 message: 'Processing Server Request'
66 }).then((res) => {
67 res.present();
68
69 res.onDidDismiss().then((dis) => {
70 console.log('Loading dismissed!');
71 });
72 });
73 this.hideLoader();
74 }
75
76 hideLoader() {
77 this.loadingController.dismiss();
78 }
79
80
81 }
82

Create a service HttpService

After adding the Interceptor, we will create a new service which will method
to make an HTTP call to test our Interceptor response handling.

Create new service HttpService and replace the below code:


1 // http.service.ts
2 import { Injectable } from '@angular/core';
3 import { HttpClient } from '@angular/common/http';
4 import { Observable, of } from 'rxjs';
5 import { catchError, tap } from 'rxjs/operators';
6
7 @Injectable({
8 providedIn: 'root'
9 })
10 export class HttpService {
11
12 apiUrl = 'https://localhost:8080/api/getdetails';
13
14 constructor(private http: HttpClient) { }
15
16 getDetails(): Observable<any> {
17 return this.http.get(this.apiUrl)
18 .pipe(
19 tap(_ => this.log('response received')),
20 catchError(this.handleError('getDetails', []))
21 );
22 }
23
24 private handleError<T>(operation = 'operation', result?: T) {
25 return (error: any): Observable<T> => {
26
27 // TODO: send the error to remote logging infrastructure
28 console.error(error); // log to console instead
29
30 // TODO: better job of transforming error for user consumption
31 this.log(`${operation} failed: ${error.message}`);
32
33 // Let the app keep running by returning an empty result.
34 return of(result as T);
35 };
36 }
37
38 /** Log a HeroService message with the MessageService */
39 private log(message: string) {
40 console.log(message);
41 }
42 }
43
Finally, in Home component replace following class and template code:

home.page.html

1 <ion-header>
2 <ion-toolbar>
3 <ion-title>
4 Ionic HTTP
5 </ion-title>
6 </ion-toolbar>
7 </ion-header>
8
9 <ion-content>
10
11 <ion-button (click)="employeeDetails()">
12 Click me
13 </ion-button>
14
15 </ion-content>
16

home.page.ts

1 // home.page.ts
2 import { Component } from '@angular/core';
3 import { HttpService } from '../http.service';
4
5 @Component({
6 selector: 'app-home',
7 templateUrl: 'home.page.html',
8 styleUrls: ['home.page.scss'],
9 })
10 export class HomePage {
11
12 constructor(private httpService:HttpService) { }
13
14 employeeDetails(){
15 this.httpService.getDetails().subscribe(books => {
16 console.log(books);
17 });
18 }
19 }
20

So now we have an Interceptor in Ionic 4 application which is helping in


modifying get requests by changing headers and also setting token in
Authentication key. We are also handling errors in Interceptors which can
be logged for debugging purposes.

You might also like