9
votes

In Clojure core.async, are channels and ports the same thing? If not what's the difference? In watching the video Timothy Baldridge - Core.Async, he creates a channel

(def c (chan))

Then later

(<!! c)

c is channel yet the docs for <!! state (emphasis added)

Usage: (<!! port) takes a val from port. Will return nil if closed. Will block if nothing is available.

It's not clear looking at the core.async docs.

1

1 Answers

13
votes

Yes, chans are ports.

port is in the name of the protocol that these implement

(defprotocol ReadPort
  (take! [port fn1-handler] "derefable val if taken, nil if take was enqueued"))

which is used by impl/take in:

(defn <!!
  "takes a val from port. Will return nil if closed. Will block if nothing is available."
  [port]
  (let [p (promise)
        ret (impl/take! port (fn-handler (fn [v] (deliver p v))))]
    (if ret
      @ret
      (deref p))))

and the name port is used very consistently throughout async.clj. Conceptually this is useful because not everything that core.async works on will be a channel. other things can implement ReadPort and WritePort and therefore play nicely with core.async.