我正在使用Angular 6,并且我有一项服务,该服务尝试通过发出POST请求在后端数据库中创建记录。我在这样的服务中实现此请求:
... usual imports and other Angular boiler plate omitted for brevity ...
export class SitesService {
constructor(private http: HttpClient) {}
addSite(siteName){
const url = environment.apiUrl + '/api/v1/spi/sites/';
const body = { 'name': siteName };
const header = new HttpHeaders({'Content-Type': 'application/json' });
return this.http.post(url, body, { headers: header }).pipe(map ( res => <Site>res ));
}
我在组件代码中使用了上述服务:
... usual imports and Angular boiler plate omitted for brevity ...
export class SitesComponent implements OnInit {
... local variable declaration omitted ...
constructor(private service: SitesService) {
... more unrelated code omitted ...
addSite(siteName) {
this.showLoader = true;
this.service.addSite(this.siteName).subscribe(
data => this.postSuccess(data),
error => this.postError(error)
);
}
private postError(error) {
console.log('ERROR IS');
console.log(error);
... omitted ...
}
当API响应BAD REQUEST 400时,我知道它会提供一条消息以及状态编号400。正如我在浏览器开发者控制台中看到的那样:
但是我所有的postError()
方法所做的都是这样写入控制台:
ERROR IS
Bad Request
我希望能够输出name: This field is required.
。
这是一个屏幕截图,显示我得到的响应代码为400,而不是200。
更新
事实证明,我们团队中有人已经实施了拦截器。这是它的代码:(我添加了console.log's
)。
import { Injectable } from '@angular/core';
import { HttpRequest, HttpHandler, HttpEvent, HttpInterceptor } from '@angular/common/http';
import { Observable, throwError } from 'rxjs';
import { catchError } from 'rxjs/operators';
import {LoginService} from '../login/login.service'
@Injectable()
export class ErrorInterceptor implements HttpInterceptor {
constructor(private authenticationService: LoginService) {}
intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
return next.handle(request).pipe(catchError(err => {
console.log('ErrirInterceptor err is:');
console.log(err);
if (err.status === 401) {
// auto logout if 401 response returned from api
this.authenticationService.logout();
}
const error = err.error.message || err.statusText;
return throwError(error);
}))
}
}
当我访问麻烦的api时,console.log的输出:
ErrirInterceptor err is:
error:
name: Array(1)
0: "This field is required."
...
但是我仍然不明白如何将错误消息发送给我
SitesComponent
或SitesService
类。
UPDATE II
事实证明,先前编写的拦截器无法处理Django Generic Views生成的错误响应,因此我通过更改此行来对其进行了更新...
const error = err.error.message || err.statusText;
...对此:
const error = err.error.message || err.error.name || err.statusText;
答案 0 :(得分:1)
使用拦截器创建文件
import { HttpEvent, HttpInterceptor, HttpHandler, HttpRequest, HttpErrorResponse, HttpResponse } from '@angular/common/http';
import { Injectable } from '@angular/core';
import { Observable } from 'rxjs';
import 'rxjs/add/operator/do';
@Injectable( {
providedIn: 'root'
} )
export class YourInterceptor implements HttpInterceptor {
constructor () { }
intercept ( request: HttpRequest<any>, next: HttpHandler ): Observable<HttpEvent<any>> {
return next.handle( request )
.do( ( response: HttpEvent<any> ) => {
if ( response instanceof HttpResponse ) {
for ( const key of response.headers.keys() ) {
console.log(key); // ***** The message should come out here ******
}
}
}, ( error: any ) => {
if ( error instanceof HttpErrorResponse ) {
console.error( error );
console.error( error.status );
}
} );
}
}
然后将其导入到应用程序的主模块中
import {
YourInterceptor
} from './interceptors/.yourInterceptor';
@NgModule( {
declarations: [ . . . ],
imports: [ . . . ],
providers: [
{
provide: HTTP_INTERCEPTORS,
useClass: YourInterceptor,
multi: true
}
],
bootstrap: [ . . . ]
} )