angular - 如何解决这个问题(“this.http.post(...).map(...).concatMap 不是函数”)?
问题描述
升级我的角度项目后出现此错误
this.http.post(...).map(...).concatMap 不是函数
这是我的导致错误的代码
return this.http.post(apiURL, body, options)
.map(response => response.json())
.concatMap(response => {
// Check if the API_TOKEN is expired.
if (response.error.code == APIErrorCode.API_TOKEN_EXPIRED || response.error.code == 499) {
// Expired! Check max attempts.
if (attempts < MAX_REQUEST_ATTEMPT) {
console.log("API_TOKEN expired.");
return this.requestAPIToken().delay(500)
.concatMap(response => this.doPost(api, body, attempts + 1));
}
console.log("API_TOKEN expired, request attempt limit reached!");
}
return Observable.of(response);
})
.catch((err, caught) => {
// Check if the session authentication token is expired.
if (authToken && err.status == 403) {
try {
var response = JSON.parse(err._body);
if (response.error && response.error.code == APIErrorCode.SESSION_AUTH_TOKEN_EXPIRED) {
// Login session expired!
return Observable.of(response);
}
} catch (e) { }
}
// Check incidental bad request.
if (err.status == 400 && err.statusText == "Bad Request") {
try {
var response = JSON.parse(err._body);
if (response.error && response.error.code == 400 && response.error.message
&& [ "access denied", "bad" ].includes(response.error.message.toLowerCase())) {
// Check max attempts.
if (attempts < MAX_REQUEST_ATTEMPT) {
return this.requestAPIToken().delay(100)
.concatMap(response => this.doPost(api, body, attempts + 1));
}
console.log("Bad Request, request attempt limit reached!");
}
} catch (e) { }
}
return Observable.throw(err);
});
在我升级我的角度项目之前它工作正常,我不知道现在该怎么做
解决方案
如果你刚刚升级了 Angular,你可能正在使用 RxJS v6。如果是这样,您需要重构以使用可管道操作符
另请注意,您应该使用它,HttpClient
而不是Http
现在已弃用很长时间。然后您也可以使用 删除第一张地图response.json()
,就像HttpClient
自动为您所做的那样。
请记住,您需要重构代码中的所有可观察对象,不仅是 from 的HttpClient
那个,还包括带有delay
operator 的那些。
在这里查看更多信息:
https://rxjs-dev.firebaseapp.com/guide/v6/migration
import { of, throwError } from 'rxjs';
import { concatMap, catchError, delay } from 'rxjs/operators';
return this.httpClient.post(apiURL, body, options)
.pipe(
concatMap(response => {
// Check if the API_TOKEN is expired.
if (response.error.code == APIErrorCode.API_TOKEN_EXPIRED || response.error.code == 499) {
// Expired! Check max attempts.
if (attempts < MAX_REQUEST_ATTEMPT) {
console.log("API_TOKEN expired.");
return this.requestAPIToken().pipe(
delay(500),
concatMap(response => this.doPost(api, body, attempts + 1)
);
}
console.log("API_TOKEN expired, request attempt limit reached!");
}
return of(response);
}),
catchError((err, caught) => {
// Check if the session authentication token is expired.
if (authToken && err.status == 403) {
try {
var response = JSON.parse(err._body);
if (response.error && response.error.code == APIErrorCode.SESSION_AUTH_TOKEN_EXPIRED) {
// Login session expired!
return of(response);
}
} catch (e) { }
}
// Check incidental bad request.
if (err.status == 400 && err.statusText == "Bad Request") {
try {
var response = JSON.parse(err._body);
if (response.error && response.error.code == 400 && response.error.message
&& [ "access denied", "bad" ].includes(response.error.message.toLowerCase())) {
// Check max attempts.
if (attempts < MAX_REQUEST_ATTEMPT) {
return this.requestAPIToken().pipe(
delay(100),
concatMap(response => this.doPost(api, body, attempts + 1)
);
}
console.log("Bad Request, request attempt limit reached!");
}
} catch (e) { }
}
return throwError(err);
})
);
如果您使用的是 v5.5,那么我的回答也应该会有所帮助,但您的问题在于concatMap
准确地说缺少运算符导入。要么重构为可管道操作符,要么只是添加import 'rxjs/add/operator/concatMap';
Observable
此导入将使用运算符对对象进行猴子修补concatMap
- 默认情况下不存在。
更多关于在 RxJS v5 中导入操作符的信息:
推荐阅读
- typescript - 无法获取未定义或空引用的属性“消息”
- javascript - 带有点符号的 MongoDB find() 不起作用
- python - GraphRbacManagementClient.applications.create() 返回访问令牌丢失或格式错误
- java - Android Studio 错误:按钮不止一次
- ruby-on-rails - Postgres db 无法在 Heroku 上运行
- font-awesome - 无法再下载 Font Awesome 4.7?
- audiokit - AKFFTTap 在 IOS 应用程序中不同步,如何解决?
- angularjs - IIS 缓存控制和 Angular JS
- javascript - javascript上的多个自动幻灯片问题
- c++ - 在c ++中解码大量以base64编码的数据