问题
According to rxjs marbles documentation the current behaviour for the sync groupings is the following:
'(ab)-(cd)': on frame 0, emits a and b then on frame 50, emits c and d
From the docs:
While it can be unintuitive at first, after all the values have synchronously emitted time will progress a number of frames equal to the number of ASCII characters in the group, including the parentheses
Ok, but how do I test an observable like this (using marbles or any other technique):
const observable$ = of(1, 2).concat(of(3, 4).delay(20));
Are there any workarounds?
There is a similar question on Stack Overflow but there is no answer on 'How to actually work around it and test this kind of observable'.
Thanks!
回答1:
I don't know what version of RxJS you're using because you're mixing prototypical and pipable operators but it looks like RxJS 5.5.
In RxJS 5.X it's a bit clumsy. You could rewrite your test like this:
import { of } from 'rxjs/observable/of';
import { TestScheduler } from 'rxjs/testing/TestScheduler';
import { assert } from 'chai';
import 'rxjs/add/operator/concat';
import 'rxjs/add/operator/delay';
const scheduler = new TestScheduler((actual, expected) => {
console.log(actual, expected);
return assert.deepEqual(actual, expected);
});
const observable$ = of('a', 'b').concat(of('c', 'd').delay(50, scheduler));
scheduler
.expectObservable(observable$)
.toBe('(ab)-(cd|)');
scheduler.flush();
See live demo (open console): https://stackblitz.com/edit/rxjs5-marble-test?file=index.ts
You know this test passes because it doesn't throw any error. Try changing any of the delays or values of next
emissions and it'll throw an error.
Also have a look at this answer: How do I test a function that returns an observable using timed intervals in rxjs 5?
However, I'd strongly recommend upgrading to RxJS 6 because it makes everything much easier with cold
and hot
"creation" functions where you could just use const observable$ = cold('(ab)-(cd|)')
to create the same sequence as you're doing with of(...).concat(...)
.
Testing in RxJS 6:
https://github.com/ReactiveX/rxjs/blob/master/doc/marble-testing.md
https://github.com/ReactiveX/rxjs/blob/master/doc/internal-marble-tests.md
回答2:
For my project I migrated to rx-sanbox where sync grouping works correct and it solved my problem.
So, in rx-sandbox this is correct:
'(ab)-(cd)': on frame 0, emits a and b then on frame 20, emits c and d
来源:https://stackoverflow.com/questions/50406951/how-to-test-observables-which-emit-grouped-events-with-rxjs-marbles