diff --git a/ReactiveFeedback/SignalProducer+System.swift b/ReactiveFeedback/SignalProducer+System.swift index 4a49299..ebab0d9 100644 --- a/ReactiveFeedback/SignalProducer+System.swift +++ b/ReactiveFeedback/SignalProducer+System.swift @@ -29,8 +29,23 @@ extension SignalProducer where Error == NoError { return SignalProducer(Signal.merge(events)) .scan(initial, reduce) - .prefix(value: initial) .on(value: stateObserver.send(value:)) + .prefix(value: initial) + .on(started: { + // NOTE: Due to the nature of `prefix` lazily starting the producer being prefixed, we cannot rely + // on `on(value:)` to ignite the feedbacks with the initial state. + // + // At the time `prefix(value:)` calls `on(value:)` for the initial value, the events-reducer + // producer has not yet been started yet. Consequentially, it would lead to dropped events + // when the system is instantiated on a queue different from the queue used for + // serializing events. + // + // Having said that, `prefix(value:)` is guaranteed to have started the prefixed producer as + // part of the synchronous producer starting process. So we can addres the issue by applying + // `on(started:)` after `prefix(value:)` to ignite the system, while having `on(value:)` + // instead applied before `prefix(value:)` to keep the reducer-to-feedbacks path open. + stateObserver.send(value: initial) + }) } }