Fetch Client Interceptor for au2

I think the interceptor fetch client documentation for au2 at docs.aurelia.io is incomplete or something is wrong here.

http-client-interceptor.ts in root folder:

export class HttpClientInterceptor implements ICustomElementViewModel {    
    constructor(@newInstanceOf(IHttpClient) readonly http: IHttpClient) {
      http.configure(config =>
        config
        .withBaseUrl('api/')
        .withDefaults({
          credentials: 'same-origin',
          headers: {
            'Accept': 'application/json',
            'X-Requested-With': 'Fetch'
          }
        })
        .withInterceptor({
          request(request) {
            const authenticationBearerToken = 'TTTTTT';
            if (authenticationBearerToken) {
              request.headers.append('Authorization', `Bearer ${authenticationBearerToken}`);
            }
            console.log(`Requesting ${request.method} ${request.url} ::: ${request.headers}`);
            return request;
          },
.................

API Service (api-service.ts in root) ::

import { IHttpClient } from '@aurelia/fetch-client';
import { inject, newInstanceOf } from '@aurelia/kernel';
import { HttpClientInterceptor } from './http-client-interceptor';


export class ApiService {
    constructor(@newInstanceOf(IHttpClient) readonly http: IHttpClient) {
    }

    async getNothin(){
        const request = await this.http.fetch(`/products`);
        console.log(`nothing :: ${request.headers.get('Authorization')}`); // undefined
        const responsestatus = await request.status;
        console.log(`nothing2 :: ${responsestatus}`);
        return null;
    }

Component ( components/articles-component.ts):

import { ApiService } from '../api-service';
...
import { bindable, HttpClient, inject, Params, useShadowDOM } from 'aurelia';
import { IRouter, IRouteViewModel } from 'aurelia';
import { ApiService } from '../api-service';


@useShadowDOM()
export class ArticlesComponent implements IRouteViewModel {
    @bindable path;
    private apiService: ApiService;
    public static readonly inject = [ApiService];
    constructor(apiService: ApiService){
        this.apiService = apiService;
    }

    async load(params: Params) {
        console.log(params);
        //let api_product = await api.getProduct(77);
        let api_product = await this.apiService.getNothin();
        //console.log(`API Service :: ${api_product} `);

getNothin() returns 200 but it’s still using the brand new HttpClient, without the interceptor.’

Also a curious warning (this goes away if you remove apiService):

index.dev.mjs?4599:1761 'articles-component' did not match any configured route or registered component name - did you forget to add the component 'articles-component' to the dependencies or to register it as a global dependency?

I’m thinking the documentation isn’t very clear on how to inject it into a component.

Should i be registering it in a container or something? I thought @newInstanceOf would be good enough. I even tried new HttpClient()

1 Like

It seems that you simply need to set the interceptor inside the ApiService#ctor. And then you can inject the ApiService elsewhere, ensuring that the http client injected in the ApiService has the interceptor configured.