typescript - RxJs SwitchIfEmpty 自定义 pipable 操作符
问题描述
我创建了一个新的 RxJs(6) 运算符 switchIfEmpty(other),它会other
在源为空时切换。
我是大理石测试的新手,我创建了一些测试来验证我的操作员,所有测试都通过了,除了一个。我不知道错误是来自操作员还是来自测试!
import { Observable } from 'rxjs';
export const switchIfEmpty = <T, R>(emptySource: Observable<R>) =>
(source: Observable<T>) => {
return new Observable<T | R>(subscriber => {
let empty = true;
const subscription = source.subscribe(
e => {
empty = false;
subscriber.next(e);
},
error => subscriber.error(error),
() => {
if (empty) {
const innerSub = emptySource.subscribe(
innerE => subscriber.next(innerE),
error => subscriber.error(error),
() => subscriber.complete()
);
subscription.add(innerSub);
} else {
subscriber.complete();
}
}
);
return subscription;
});
};
测试规范:
import { TestScheduler } from 'rxjs/testing';
import { of, throwError } from 'rxjs';
import { switchIfEmpty } from './switch-empty';
import { delay } from 'rxjs/operators';
describe('SWITCH IF EMPTY OPERATOR', () => {
let scheduler: TestScheduler;
beforeEach(() => {
scheduler = new TestScheduler((actual, expected) => {
expect(actual).toEqual(expected);
});
});
it('switchIfEmpty : source not empty', () => {
const source = '-x-y-z|';
const expected = '-x-y-z|';
scheduler.run(helper => {
const source$ = scheduler.createColdObservable(source);
helper.expectObservable(source$.pipe(switchIfEmpty(of(1)))).toBe(expected);
});
});
it('switchIfEmpty : source empty', () => {
const source = '|';
const expected = '(1 a|)';
scheduler.run(helper => {
const source$ = scheduler.createColdObservable(source);
helper.expectObservable(source$.pipe(switchIfEmpty(of('1', 'a')))).toBe(expected);
});
});
it('switchIfEmpty : source error', () => {
const source = '-x#';
const expected = '-x#';
scheduler.run(helper => {
const source$ = scheduler.createColdObservable(source);
helper.expectObservable(source$.pipe(switchIfEmpty(of(1)))).toBe(expected);
});
});
it('switchIfEmpty : empty source switched to error', () => {
const source = '|';
const expected = '#';
scheduler.run(helper => {
const source$ = scheduler.createColdObservable(source);
helper.expectObservable(source$.pipe(switchIfEmpty(throwError('error')))).toBe(expected);
});
});
it('switchIfEmpty : empty source switched to delay', () => {
const source = '|';
const expected = '--x|'; // tried '--(x|)' not work
scheduler.run(helper => {
const source$ = scheduler.createColdObservable(source);
const switchedSource = of(1).pipe(delay(20));
helper.expectObservable(source$.pipe(switchIfEmpty(switchedSource))).toBe(expected, {x: 1});
});
});
});
只有最后一个不起作用:
it('switchIfEmpty : empty source switched to delay', () => {
const source = '|';
const expected = '--x|'; // tried '--(x|)' not work
scheduler.run(helper => {
const source$ = scheduler.createColdObservable(source);
const switchedSource = of(1).pipe(delay(20));
helper.expectObservable(source$.pipe(switchIfEmpty(switchedSource))).toBe(expected, {x: 1});
});
});
错误信息
SWITCH IF EMPTY OPERATOR switchIfEmpty : empty source switched to delay FAILED
Expected $.length = 0 to equal 2.
Expected $[0] = undefined to equal Object({ frame: 2, notification: Notification({ kind: 'N', value: 1, error: undefined, hasValue: true }) }).
Expected $[1] = undefined to equal Object({ frame: 3, notification: Notification({ kind: 'C', value: undefined, error: undefined, hasValue: false }) }).
at TestScheduler.assertDeepEqual (http://localhost:9876/src/switch-empty.spec.ts?:12:22)
at http://localhost:9876/node_modules/rxjs/_esm5/internal/testing/TestScheduler.js?:122:1
at Array.filter (<anonymous>)
at TestScheduler.push../node_modules/rxjs/_esm5/internal/testing/TestScheduler.js.TestScheduler.flush (http://localhost:9876/node_modules/rxjs/_esm5/internal/testing/TestScheduler.js?:120:1)
解决方案
推荐阅读
- json - EF Core 和 Pomelo 5.0 - 如何查询 json 列
- python - 为什么 tensorflow 和 pytorch 中的 Resnet 模型给出不同的特征长度?
- reactjs - 材料表覆盖分页组件导致警告
- python - 如何在 python 中对齐替换的文本文件?
- mailkit - 关于 Mailkit 的查询
- flutter - Flutter ADS:为什么插页式广告在测试模式下有效,但在 Play Market 中无效?
- autohotkey - 如何在 If Else 中使用 GetKeyState 命令?
- tailwind-css - 在 TailWind CSS 中使用颜色
- python-3.x - 划分 range(len(dataframe[column])) 而不是值?
- r - mgcv 中的 GAM 错误:theta 估计中的步骤失败