Redux-Observable 测试只读史诗
Posted
技术标签:
【中文标题】Redux-Observable 测试只读史诗【英文标题】:Redux-Observable testing readonly epics 【发布时间】:2021-11-13 22:17:21 【问题描述】:我想测试以下史诗:
authEpics.logoutEpic = function (action$, _, deps)
return action$.pipe(
ofType(authActions.logout),
tap(() =>
const history, browser = deps;
browser.localStorage.removeItem('user');
history.push(ROUTES.LOGIN);
),
ignoreElements()
);
;
这是测试用例:
describe('Logout Epic', () =>
test('should remove user from localStorage', (done) =>
scheduler.run((helpers) =>
const hot, expectObservable = helpers;
const action$ = hot('a',
a: authActions.logout(),
);
const deps = testUtils.mockEpicDependencies();
const output$ = authEpics.logoutEpic(action$, null, deps);
// Statement 1.
expectObservable(output$).toBe('');
// Statement 2.
output$.subscribe(
complete: () =>
expect(deps.browser.localStorage.removeItem).toHaveBeenCalledWith('user');
expect(deps.history.push).toHaveBeenCalledWith(ROUTES.LOGIN);
done();
);
);
);
根据ignoreElements 的定义,我无法理解以下观察结果:
-
在声明 1 中,我认为
expectObservable(output$).toBe('|')
应该可以工作,但事实并非如此。相反,expectObservable(output$).toBe('')
有效。
在语句 2 中,complete
函数永远不会被调用。
【问题讨论】:
【参考方案1】:为了使测试用例工作,我必须刷新承诺队列(而不是使用expectObservable
)。这是修改后的测试用例:
describe('Logout Epic', () =>
test('should remove user from localStorage', (done) =>
scheduler.run(async (helpers) =>
const hot = helpers;
const action$ = hot('a',
a: authActions.logout(),
);
const deps = testUtils.mockEpicDependencies();
const output$ = authEpics.logoutEpic(action$, null, deps);
// *** Flush the promise queue ***
await new Promise((resolve) => resolve());
expect(deps.browser.localStorage.removeItem).toHaveBeenCalledWith('user');
expect(deps.history.push).toHaveBeenCalledWith(ROUTES.LOGIN);
done();
);
);
【讨论】:
【参考方案2】:这太痛苦了,对我不起作用。
const pingAuthEpic = (action$: any) => action$.pipe(
ofType(SET_ONLINE),
mergeMap(() => interval(PING_AUTH_INTERVAL).pipe(
mergeMap(() => of( type: 'PING_AUTH' )),
takeUntil(action$.ofType(SET_OFFLINE)),
)),
);
任何想法为什么它只是挂起并开玩笑超时欢迎......
【讨论】:
你能不能试着把takeUntil
改成这样:takeUntil(action$.pipe(ofType(SET_OFFLINE)))
如果不行,你能把测试用例代码贴在这里吗?
嘿,谢谢 Anup - 我决定改为测试整个商店并只传递我想要测试的减速器和史诗......这要好得多,因为我不需要了解弹珠或任何东西我使用测试库的方式有问题。此外,如果我们远离未维护的 redux-observable,测试仍然可以工作。以上是关于Redux-Observable 测试只读史诗的主要内容,如果未能解决你的问题,请参考以下文章
从 redux-observable 的史诗有条件地调度额外的动作
redux-observable - 在单个史诗中调度多个 redux 操作
React redux-observable:以史诗般的方式进行顺序 API 调用
如何在 redux-observable 史诗中链接 RxJS 可观察?