Angular中pipe map内获取HttpResponse.body数据时报TS2740错误如何解决
问题根源
你给HttpClient.post传入的泛型参数错误,导致TS类型推断出错:
当你配置{observe: 'response'}时,HttpClient.post的返回值会自动被包裹为Observable<HttpResponse<T>>,其中泛型T是响应体的实际类型。你之前传入的泛型是HttpResponse<User>,相当于告诉TS:接口返回的响应体本身是HttpResponse<User>类型,所以最终resp的类型被推断为HttpResponse<HttpResponse<User>>,resp.body的类型自然就是HttpResponse<User>,和你声明的u: User类型不匹配,就抛出了TS2740错误。
你强行写resp.body.body时,TS认为HttpResponse<User>的body属性是User类型,所以编译通过,但实际接口返回的响应体就是User类型,没有第二层body,所以运行时拿到的是undefined。
修复方案
把post的泛型参数从HttpResponse<User>改为User即可,修正后的代码如下:
login(username, password) { // 泛型改为<User>,对应响应体的实际类型,observe: 'response'会自动包裹为HttpResponse<User> return this.http.post<User>(`${environment.apiEndPoint}/users/authenticate`, { username, password }, {observe: 'response'}) .pipe(map(resp => { const u: User = resp.body!; // 加!是告诉TS resp.body非空,如果你做好了空值判断可以不加 // 这里可以正常获取响应头,比如 const token = resp.headers.get('Authorization'); localStorage.setItem('currentUser', JSON.stringify(u)); return u; })); }
如果需要处理resp.body可能为空的边界情况,也可以补充空值判断:
.pipe(map(resp => { const u = resp.body; if (!u) { throw new Error('响应体为空'); } localStorage.setItem('currentUser', JSON.stringify(u)); return u; }))
内容的提问来源于stack exchange,提问作者Sergio Prats
相关产品推荐
相关产品推荐

