javascript – Angular 4 http响应混合在一起

我正在使用Angular 4.此问题已在safari,chrome和Firefox中找到.

我的Angular 4应用程序使用httpclient将XHR请求发送到REST服务.通信是JSON.

存在潜在的CORS问题,因此浏览器发送飞行前OPTIONS请求.

该请求以JSON格式返回用户的详细信息.

有时(可能是五分之一),我看到响应结合在一起:

例如,如果快速成功发送两个请求(相同的URL),我看到:
选项请求已发送
选项请求已发送
已发送GET请求(无响应)
发送GET请求(结果与最后一次GET结合返回)

所以对于最后的GET,我会收到:

    {"username":"Dave Smith","badge":"12345", "lockPollTime":61000}{"username":"Dave Smith","badge":"12345", "lockPollTime":61000}

(即:两个JSON对象共同加入,这是一个JSON语法错误,因此应用程序中断)
..而我希望这两个GET分别获得其中一个:

{"username":"Dave Smith","badge":"12345", "lockPollTime":61000}

我也看到了其他请求,URL不同(相同的服务器和REST服务,不同的操作).

从authService服务获取登录信息的调用是这样的:

login(username: string, password: string): Observable<LoginResponse|boolean> {
    return this.http.get(ApiRoutes.auth.login, this.loginHeaders(username, password)).map((response: Response) => {
        if(response.headers.get('Content-Type').indexOf('text/html') !== -1) {
            return false;
        }

        return new LoginResponse(response);
    });
}

对它的调用是这样的:

this.authService.login(username, password).subscribe(
    (user: LoginResponse|boolean) => { .. etc etc } )

用户凭据通过n拦截器提供:

intercept(request: HttpRequest<any>, next: HttpHandler): Observable<HttpEvent<any>> {
    if(this.authService.getAuthToken()) {
        request = request.clone({
            setHeaders: {
                Authorization: `Basic ${this.authService.getAuthToken()}`
            }
        });
    }

    return next.handle(request);
}

如果我在浏览器窗口中尝试其中一个REST服务URL并多次按F5,我就无法重现该问题.似乎只是有角度的http请求,虽然我不知道这是否是一个公平的测试.

我不确定这是不是..

> Angular订阅问题
>一个httpclient错误
>服务器端的问题(很难想象)

如果有人能说清楚这一点,我会非常感激,并会在街道上漫游,通过扬声器吟唱你的用户ID.

我唯一的线索是有时发送异步请求(例如心跳’ping’),这些有时似乎与用户发起的请求冲突(例如保存,使用POST请求或GET来获取其他信息) .

任何帮助或建议感激不尽.

最佳答案 只需用switchmap替换map,它将自动取消除最后一个请求之外的所有请求.

更多信息:Search with switchmap

编辑:例如,如果您有2个不同的功能

     http.get(API_URL1).switchmap(...)
     http.get(API_URL2).map(...) 

switchmap只能取消来自API_URL1的旧请求.或者即使你有这样的东西:

     http.get(API_URL1).switchmap(...)
     http.get(API_URL2).switchmap(...)

同时来自URL1和URL2的请求很好,因为每个switchmap只能从其URL中取消旧请求.

希望这可以解决你的困惑.

点赞