I want to test a service that uses internally a BehaviorSubject to hold the state and exposes Observables with a distinctUntilChanged() in the pipe. When I run the following test, than the actual steam that is compared with my expectations only 'contains' the last value. What do I have to understand to fix that?
import { BehaviorSubject } from 'rxjs';
import { distinctUntilChanged } from 'rxjs/operators';
import { TestScheduler } from 'rxjs/testing';
describe('My exposed stream', () => {
let testScheduler;
beforeEach(() => {
testScheduler = new TestScheduler((actual, expected) => {
expect(actual).toEqual(expected);
});
});
it('does not propagate if the current value equals the last one', () => {
testScheduler.run(({ expectObservable }) => {
const internalStream$ = new BehaviorSubject<string>(null);
const exposedStream$ = internalStream$.pipe(distinctUntilChanged());
expectObservable(exposedStream$).toBe('012', [null, 'foo', 'bar']);
internalStream$.next('foo');
internalStream$.next('foo');
internalStream$.next('bar');
});
});
});
Result:
Expected $.length = 1 to equal 3.
Expected $[0].notification.value = 'bar' to equal null.
Expected $[1] = undefined to equal Object({ frame: 1, notification: Notification({ kind: 'N', value: 'foo', error: undefined, hasValue: true }) }).
Expected $[2] = undefined to equal Object({ frame: 2, notification: Notification({ kind: 'N', value: 'bar', error: undefined, hasValue: true }) }).
You can run and modify the code here: https://stackblitz.com/edit/typescript-moydq7?file=test.ts
My code had 2 issues:
ReplySubject(Thank you, @AliF50)(012)instead if012, because the 3 events are sent within the same time frame synchronously.Here is my solution. Still very cumbersome and if you are aware of better ways, please let me know.
You can play around with it here: https://stackblitz.com/edit/typescript-sa1n8v?file=test.ts