Fork me on GitHub

Hi, I have the following core.async code:

(def in (chan 10))
(def inpub (pub out :msg-type))

(def out (chan 10))
(sub inpub :a out)
(sub inpub :b out)
(sub inpub :c out)

(go (>! in {:msg-type :a})
    (>! in {:msg-type :b})
    (>! in {:msg-type :c}))

(go-loop [i 0]
  (println i (<! out))
  (recur (inc i)))
Each time the go block that puts is run, messages are not always arriving in order (:a, 😛, :c) and I would like to understand at which point the ordering is being lost. The messages are put in a single go block, so second message is not put until first is taken by the channel where publication is created, and because in is buffered, I assume they enter the buffer in order. I think the order is being lost when the publication is taking the messages from in and putting them into the subs of out, but I’d like a deeper understanding of this, and how to ensure ordering, if possible? can someone help?


a pub is a go block pulling from one channel and feeding it in to a mult (one per sub'ed topic), and a mult is a go block pulling from one channel and writing to multiple channels


multiple go blocks mean their actions can be interleaved


if you write a version of pub (using the Pub protocol) which only uses a single go block, or if you stop the pub go block until it gets feedback that the mult go block has finished, then you will eliminate the interleaving