You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Angular 13中this.interceptor.intercept不是函数问题及403需求

Angular HTTP拦截器报错:this.interceptor.intercept is not a function 解决方案

报错信息

TypeError: this.interceptor.intercept is not a function
    Angular 5
    RxJS 12
    onSubmit panel.component.ts:87
    PanelComponent_Template_form_ngSubmit_3_listener panel.component.html:7
    Angular 2
    RxJS 5
    Angular 14

问题原因

你的拦截器服务同时通过@Injectable({ providedIn: 'root' })和app.module.ts的providers数组进行注册,导致Angular实例化时出现冲突,无法正确识别intercept方法。

修复步骤

1. 修正拦截器服务注册

移除HttperrorinterceptorService中的providedIn: 'root'配置,仅保留模块中的拦截器注册:

httperrorinterceptor.service.ts

import { Injectable } from '@angular/core';
import { HttpEvent, HttpInterceptor, HttpHandler, HttpRequest, HttpErrorResponse } from '@angular/common/http';
import { Observable, throwError } from 'rxjs';
import { catchError } from 'rxjs/operators';
import { ErrorNotificationService } from './error-notification.service';

@Injectable() // 移除providedIn: 'root'
export class HttperrorinterceptorService implements HttpInterceptor {
  constructor(private errorService: ErrorNotificationService) { }

  intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    return next.handle(request)
      .pipe(
        catchError((error: HttpErrorResponse) => {
          let errorMsg = '';
          if (error.error instanceof ErrorEvent) {
            console.log('客户端错误');
            errorMsg = `错误: ${error.error.message}`;
          } else {
            console.log('服务端错误');
            errorMsg = `错误码: ${error.status}, 信息: ${error.message}`;
            
            // 识别403状态并通知组件
            if (error.status === 403) {
              this.errorService.emitForbiddenError('参考编号已存在,无法创建房间');
            }
          }
          console.log(errorMsg);
          return throwError(() => new Error(errorMsg));
        })
      );
  }
}

2. 创建错误通知共享服务

用于在拦截器和组件之间传递错误事件:

error-notification.service.ts

import { Injectable } from '@angular/core';
import { Subject } from 'rxjs';

@Injectable({ providedIn: 'root' })
export class ErrorNotificationService {
  private forbiddenErrorSubject = new Subject<string>();
  forbiddenError$ = this.forbiddenErrorSubject.asObservable();

  emitForbiddenError(message: string): void {
    this.forbiddenErrorSubject.next(message);
  }
}

3. 更新房间创建组件处理403错误

在负责房间创建的组件中订阅错误通知,显示模态框(以Angular Material为例):

room-create.component.ts

import { Component, OnInit } from '@angular/core';
import { ErrorNotificationService } from '../services/error-notification.service';
import { MatDialog } from '@angular/material/dialog';
import { ErrorDialogComponent } from '../error-dialog/error-dialog.component';

@Component({
  selector: 'app-room-create',
  templateUrl: './room-create.component.html',
  styleUrls: ['./room-create.component.scss']
})
export class RoomCreateComponent implements OnInit {
  constructor(
    private errorNotificationService: ErrorNotificationService,
    private dialog: MatDialog
  ) {}

  ngOnInit(): void {
    // 订阅403错误事件,触发模态框
    this.errorNotificationService.forbiddenError$.subscribe(message => {
      this.dialog.open(ErrorDialogComponent, {
        data: { message: message }
      });
    });
  }

  // 房间创建提交逻辑...
}

4. 确认模块配置正确

确保app.module.ts中已注册拦截器和必要依赖:

app.module.ts

import { HttpClientModule, HTTP_INTERCEPTORS } from '@angular/common/http';
import { HttperrorinterceptorService } from './services/httperrorinterceptor.service';
import { ErrorNotificationService } from './services/error-notification.service';
import { MatDialogModule } from '@angular/material/dialog';
import { ErrorDialogComponent } from './error-dialog/error-dialog.component';

@NgModule({
  imports: [
    HttpClientModule,
    MatDialogModule,
    // 其他模块...
  ],
  declarations: [
    ErrorDialogComponent,
    // 其他组件...
  ],
  providers: [
    UserService,
    RoomService,
    UserGuard,
    NoIdentityGuard,
    LanguageService,
    ErrorNotificationService,
    {
      provide: HTTP_INTERCEPTORS,
      useClass: HttperrorinterceptorService,
      multi: true
    }
  ]
})
export class AppModule { }

关键说明

  • 拦截器必须通过HTTP_INTERCEPTORS令牌注册,且设置multi: true以支持多个拦截器共存。
  • 使用共享服务传递错误事件,可让多个组件响应同一错误类型,避免代码重复。
  • 确保后端在参考编号重复时返回403 Forbidden状态码,以便拦截器准确识别。

内容的提问来源于stack exchange,提问作者Rafael Hernández

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 08:05:55