微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何测试有延迟的递归 http 请求?

如何解决如何测试有延迟的递归 http 请求?

我有一个有点复杂的情况,在后端实现中,我需要轮询后端直到

  1. 我从 BE 获得了成功状态
  2. 我从 BE 获得失败状态
  3. 我的持续时间超过了我的重试次数(客户端 TO)

代码有效,并且在所有三种情况下对后端的测试都成功了。我也成功地测试了第一种和第二种情况,如果结果是即时的(立即模拟完成/失败的响应,而不会在中间得到 onGoing)。但是,我无法测试第三种情况。每次尝试都会遇到不同的错误,所以现在我转向 S.O.寻求帮助:-)

ts 文件

doAction(content): Observable<resPasstype> {
    return this.postAction(content) // private function that just calls HTTP Post at url1,and returns an actionId for polling
      .pipe(concatMap(action => this.poll(action))); // see below
}

private poll(action,retryCount = config.retryCount): Observable<resPasstype>{
    return time(config.retryTime).pipe(switchMap(() =>
      this.getActionStatus(action) // private function that calls HTTP get at url2/action.id
      .pipe(concatMap ( res=> {
        retryCount--;
        if(retryCount < 0)
            return throwError('Action Timed Out'); // this is essentially what I want to test
        switch(res.action.state.toLowerCase()) {
            case 'completed':
                return of(resPasstypeData);//taken from within res.action. Successfully tested
            case 'Failed':
                return throwError('Action Failed'); // successfully tested
            case 'ongoing':
                return this.poll(res.action,retryCount)
            default':
                return throwError('unexpeceted action state');
            }
        }))));
}

看到成功的测试可能对你有帮助,所以这里包括失败的测试

it('should throw error if action Failed`,fakeAsync(()=>{
    const mockGetActionResponse = {'action' : {'id' : mockActionId,state: 'Failed' }};
    
    service.doAction(mockContent).subscribe(
        () => {},err => expect(err).toEqual('Action Failed');
    );

    const postCall = httpTestingController.expectOne(url1);
    expect(postCall.request.method).toEqual('POST');
    expect(postCall.request.body).toEqual(mockContent);

    postCall.flush(mockPostActionResponse);

    tick(config.retryTime);

    const getCall = httpTestingController.expectOne(url2/mockActionId);
    expect(getCall .request.method).toEqual('Get');

    getCall.flush(mockGetActionResponse );
}));

此测试有效。如何编写案例 3 的测试?编写相同的测试并将状态更改为 'onGoing' 并更改错误期望使我遇到错误

错误预期未找到打开的请求 1

我的预感是这与递归或延迟或其他事情有关,因为这是唯一一个 poll 被多次调用的测试用例。任何线索将不胜感激:-)

编辑 由于@Andrei 的评论和改进,代码已更新。问题依旧

解决方法

@Andrei 在评论中找到的答案。

工作代码现在看起来像这样:

it('should throw error if action timed out',()=>{
    const mockGetActionResponse = {'action' : {'id' : mockActionId,state: 'onGoing' }};

    service.doAction(mockContent).subscribe(
        () => {},err => expect(err).toEqual('Action Timed Out');
    );

    const postCall = httpTestingController.expectOne(url1);
    expect(postCall.request.method).toEqual('POST');
    expect(postCall.request.body).toEqual(mockContent);

    postCall.flush(mockPostActionResponse);

    for( let i=0; i<config.retryCount; i++) {
        tick(config.delayTime);
        const getCall = httpTestingController.expectOne(url2);
        expect(getCall.request.method).toEqual('GET');
        getCall.flush(mockGetActionResponse)
    }
})

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 dio@foxmail.com 举报,一经查实,本站将立刻删除。

相关推荐


Selenium Web驱动程序和Java。元素在(x,y)点处不可单击。其他元素将获得点击?
Python-如何使用点“。” 访问字典成员?
Java 字符串是不可变的。到底是什么意思?
Java中的“ final”关键字如何工作?(我仍然可以修改对象。)
“loop:”在Java代码中。这是什么,为什么要编译?
java.lang.ClassNotFoundException:sun.jdbc.odbc.JdbcOdbcDriver发生异常。为什么?
这是用Java进行XML解析的最佳库。
Java的PriorityQueue的内置迭代器不会以任何特定顺序遍历数据结构。为什么?
如何在Java中聆听按键时移动图像。
Java“Program to an interface”。这是什么意思?