1

I have set a HttpInterceptor for setting an api key in the request headers:

export const authInterceptor: HttpInterceptorFn = (req, next) => {
  console.log('authInterceptor');
  console.log('request', req.method, req.url);

  req = req.clone({
    setHeaders: {
      ApiToken: '*****************************',
    },
  });

  return next(req);
};

And included it in the app.config:

export const appConfig: ApplicationConfig = {
  providers: [
    provideRouter(routes),
    provideHttpClient(withInterceptors([authInterceptor])),
    {
      provide: ApiConfiguration,
      useValue: { rootUrl: 'http://localhost:5042' }
    },
    provideServiceWorker('ngsw-worker.js', {
      enabled: !isDevMode(),
      registrationStrategy: 'registerWhenStable:30000',
    }),
  ],
};

And then bootstrap the application in main.ts. All in the new angular standalone fashion:

bootstrapApplication(AppComponent, appConfig)
  .catch((err) => console.error(err));

The problem is that HttpClient now calls api twice. The first time with no ApiKey header and the second one with the header. It seems like HttpClient is calling the first time without interceptor and the second one with it. If I replace

provideHttpClient(withInterceptors([authInterceptor]))

with

provideHttpClient()

The interceptor doesn't get called and the api is called only once, so I supose the problem is in the interceptor or in the way angular calls the interceptor. Any sugestion? Thanks

mattinsalto
  • 2,146
  • 1
  • 25
  • 27

2 Answers2

0

Try to provide an http interceptor as shown below:

import { HTTP_INTERCEPTORS } from '@angular/common/http';

@NgModule({
  ....
  providers: [
    ...
      { provide: HTTP_INTERCEPTORS, useClass: authInterceptor, multi: true },
    ]
}
iamaword
  • 1,327
  • 8
  • 17
  • Thanks @iamaword, I had it this way until I have discovered through this issue the new way of declaring interceptors. Not exactly this way because I have no modules I'm doing all standalone way. But I have try this way in app.config.ts using: provideHttpClient(withInterceptorsFromDi()) with the same result. – mattinsalto Jul 26 '23 at 12:57
  • I don't think this would work as he's currently using a function instead of a class. – Leccho Jul 26 '23 at 12:58
  • But I have tried it with an injectable class with provideHttpClient(withInterceptorsFromDi()) with the same result – mattinsalto Jul 26 '23 at 13:00
0

If you'd type your stuff, you'd see that you can't do next(req), you need to to do next.handle(req). Maybe you should look to use a class instead of a function too.

@Injectable()
export class AuthInterceptor implements HttpInterceptor {

  public constructor(private translateService: TranslateService) { }

  public intercept(req: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {

    let cloned = req.clone();

    cloned = cloned.clone({
      headers: cloned.headers.set('ApiToken', '*****')
    });

    return next.handle(cloned);
  }
}

I would also try this in you app.module if it still does not work after that:

providers: [{
  provide: HTTP_INTERCEPTORS,
  useClass: AuthInterceptor,
  multi: true
}],
Leccho
  • 467
  • 5
  • 23
  • Thanks @Leccho, but the sintax is correct, is the new way of doing since version 15. Now, next parameter is an HttpHandlerFn, you can call next(req). There is no handle now. The problem is not that interceptor is not working, the problem is httpclient calls the api twice, one without the interceptor or not including the header and the other with the header – mattinsalto Jul 26 '23 at 13:04
  • I'm at V16 and it does not work, you should try – Leccho Jul 27 '23 at 14:41
  • I'm using what's above and it works just saying – Leccho Jul 27 '23 at 14:50