Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/unit-testing/4.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/visual-studio/7.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Unit testing 如何在rxjs中对retryWhen操作符进行单元测试?_Unit Testing_Rxjs_Retrywhen - Fatal编程技术网

Unit testing 如何在rxjs中对retryWhen操作符进行单元测试?

Unit testing 如何在rxjs中对retryWhen操作符进行单元测试?,unit-testing,rxjs,retrywhen,Unit Testing,Rxjs,Retrywhen,我正在尝试对一个自定义RxJS操作符进行单元测试。该操作符非常简单,它使用RetryWhen重试失败的HTTP请求,但有一个延迟,只有在HTTP错误在500范围内时才会重试。使用茉莉花,这是在一个角度的应用 我已经看过了: 不幸的是,更新SpyOn调用似乎不会改变连续重试时返回的可观测值。每次重试时,它都会使用原始spyon值重试 我还看了一些rxjs大理石的例子,它们似乎都不起作用。我不确定在这里是否可以使用rxjs大理石,因为(AFAIK)无法模拟这样一种情况:首先提交一个错误的观测值,然

我正在尝试对一个自定义RxJS操作符进行单元测试。该操作符非常简单,它使用RetryWhen重试失败的HTTP请求,但有一个延迟,只有在HTTP错误在500范围内时才会重试。使用茉莉花,这是在一个角度的应用

我已经看过了:

不幸的是,更新SpyOn调用似乎不会改变连续重试时返回的可观测值。每次重试时,它都会使用原始spyon值重试

我还看了一些rxjs大理石的例子,它们似乎都不起作用。我不确定在这里是否可以使用rxjs大理石,因为(AFAIK)无法模拟这样一种情况:首先提交一个错误的观测值,然后在随后的尝试中提交一个成功的观测值

该代码基本上是以下代码的克隆:

导出函数delayedRetry(delayMS:number,maxRetry){
让retries=maxRetry;
回报率(src:可观察)=>
钢骨混凝土管(
retryWhen((错误:可观察)=>errors.pipe(
延迟(延迟毫秒),
合并映射(错误=>
(重试-->0&&error.status>=500)?(错误):抛出者错误(错误))
))
);
}
我希望能够证明它可以订阅一个在第一次尝试时返回错误,但随后返回成功响应的可观察对象。最终订阅应该显示可观测到的成功值


提前感谢您提供的任何见解。

尝试使用此可观察对象作为源可观察对象进行测试

const source = (called,successAt)=>{
  return defer(()=>{
  if(called<successAt){
    called++
  return throwError({status:500})
  }
  else return of(true)
  })
  }

在前面的答案的基础上,我一直在使用这个,它可以让您更好地控制返回的内容

const source = (observables) => {
  let count = 0;
  return defer(() => {
    return observables[count++];
  });
};
然后可以这样使用

const obsA = source([
  throwError({status: 500}),
  of(1),
]);
或者可以与rxjs大理石一起使用,比如

const obsA = source([
  cold('--#', null, { status: 500 }),
  cold('--(a|)', { a: 1 }),
]);

要测试重试功能,您需要一个observable,它在每次调用时都会发出不同的事件。例如:

let alreadyCalled = false;
const spy = spyOn<any>(TestBed.inject(MyService), 'getObservable').and.returnValue(
  new Observable((observer) => {
    if (alreadyCalled) {
      observer.next(message);
    }
    alreadyCalled = true;
    observer.error('error message');
  })
);
让alreadyCalled=false;
constspy=spyOn(TestBed.inject(MyService),'getObservable')。和.returnValue(
新可观察((观察者)=>{
如果(已调用){
观察员:下一个(信息);
}
alreadyCalled=true;
observer.error(“错误消息”);
})
);
此可观察对象将首先发出错误,然后发出下一个事件

您可以检查,如果您的可观察对象得到如下信息:

it('should retry on error', async(done) => {
    let alreadyCalled = false;
    const spy = spyOn<any>(TestBed.inject(MyDependencyService), 'getObservable').and.returnValue(
      new Observable((observer) => {
        if (alreadyCalled) {
          observer.next(message);
        }
        alreadyCalled = true;
        observer.error('error message');
      })
    );
    const observer = {
      next: (result) => {
        expect(result.value).toBe(expectedResult);
        done();
      }
    }

    subscription = service.methodUnderTest(observer);
    expect(spy).toHaveBeenCalledTimes(1);
}
it('should retry on error',async(done)=>{
设alreadyCalled=false;
const spy=spyOn(TestBed.inject(MyDependencyService)、'getObservable')和.returnValue(
新可观察((观察者)=>{
如果(已调用){
观察员:下一个(信息);
}
alreadyCalled=true;
observer.error(“错误消息”);
})
);
常量观察者={
下一步:(结果)=>{
expect(result.value).toBe(expectedResult);
完成();
}
}
订阅=service.methodUnderTest(观察者);
期望(间谍)。被催促的时间(1);
}

这帮了我的忙,我不知道你能用源代码做到这一点,很酷。
let alreadyCalled = false;
const spy = spyOn<any>(TestBed.inject(MyService), 'getObservable').and.returnValue(
  new Observable((observer) => {
    if (alreadyCalled) {
      observer.next(message);
    }
    alreadyCalled = true;
    observer.error('error message');
  })
);
it('should retry on error', async(done) => {
    let alreadyCalled = false;
    const spy = spyOn<any>(TestBed.inject(MyDependencyService), 'getObservable').and.returnValue(
      new Observable((observer) => {
        if (alreadyCalled) {
          observer.next(message);
        }
        alreadyCalled = true;
        observer.error('error message');
      })
    );
    const observer = {
      next: (result) => {
        expect(result.value).toBe(expectedResult);
        done();
      }
    }

    subscription = service.methodUnderTest(observer);
    expect(spy).toHaveBeenCalledTimes(1);
}