Advertisement
Guest User

Untitled

a guest
Sep 27th, 2016
68
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 1.47 KB | None | 0 0
  1. (defn- add-argument-last
  2. [form arg]
  3. `(~@form ~arg))
  4.  
  5. (defn- callback [sc fc]
  6. `(fn [err# res#]
  7. (cljs.core.async.macros/go
  8. (when err#
  9. (~'>! ~fc err#))
  10. (if (nil? res#) ;; Sometimes the result is nil
  11. (cljs.core.async/close! ~sc)
  12. (~'>! ~sc res#)))))
  13.  
  14. (defn- success-value-or-throw
  15. "Attempt to get the successful callback value and add it to the success channel (SC),
  16. or throw an exception and add it to the failure channel (FC)."
  17. [sc fc]
  18. `(let [[v# c#] (~'alts! [~sc ~fc])]
  19. (try
  20. (if (= c# ~sc)
  21. v#
  22. (let [err (js/Error. v#)]
  23. (cljs.core.async/put! ~fc err)
  24. err))
  25. (finally
  26. (cljs.core.async/close! ~sc)
  27. (cljs.core.async/close! ~fc)))))
  28.  
  29. (defn- transform
  30. "Transform FORMS to replace ... at the end of a form with a channel callback handler."
  31. [forms]
  32. (if (list? forms)
  33. (if (= (last forms) '...)
  34. (let [sc (gensym) fc (gensym)] ; sc -> success, fc -> fail
  35. `(let [~sc (cljs.core.async/chan)
  36. ~fc (cljs.core.async/chan)]
  37. (do
  38. ~(add-argument-last (map transform (butlast forms))
  39. (callback sc fc))
  40. ~(success-value-or-throw sc fc))))
  41. (map transform forms))
  42. forms))
  43.  
  44. (defmacro asynchronize
  45. "Asynchronize a standard JS callback. It will return an async channel or
  46. throw an exception on failure."
  47. [& forms]
  48. `(cljs.core.async.macros/go
  49. ~@(map transform forms)))
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement