1
votes

I have two BehaviorSubjects $A and $B with default values. Both of them are getting updated with values at different times using .next(value). Much later in the code I am trying to pull the values like so

 Observable.combineLatest($A, $B)
  .take(1)
  .map(([$a, $b]) => {
    return {
      // stuff
    }
  })
  .subscribe(fn)

The behavior I'm seeing is odd. I was expecting the Observable to wait for either subject to emit a value and then give me one emitted value that I could pass to the subscribe function. But it only emits values with $B emits a new value. It will take the new value from $A when $B emits, but it won't do the reverse. What am I doing wrong?

1

1 Answers

3
votes

The combineLatest operator emits when all source Observables emit at least one item and then on every emission from any source Observable.

So if you want eg. $A to emit even when $B hasn't emitted anything you can prepend each source with startWith. In the resulting array you can check which index is filled with a value and thus tell what was the source Observable.

const a = $A.pipe(startWith(undefined));
const b = $B.pipe(startWith(undefined));

Observable.combineLatest(a, b)
  ...

I guess you're doing this because you want to know which source Observable emitted first. You could achieve the same with using just merge chained with take(1) where instead of startWith you could map each value to something uniquely distinguishable.