Hi,
My use-case is that I need to have a bunch of state which differs for each
(web) request but is accessible via a var. Specifically I need to allow
code to access the current transaction and register one or callbacks that
are executed if/after that transaction is committed.
In Java I would store these as thread locals as each web request comes in
as a new thread. In Clojure, the equivalent seems to be dynamic binding.
Am I right in thinking that the following infrastructure is correct,
specifically the use of thread-bound?. And when would I use bound? rather
than thread-bound?
To be clear, the outer 'service' will call 'do-in-tx', code evaluated as a
result of 'do-in-tx' will access the current tx by calling 'with-tx'.
(def ^:dynamic *tx*)
(def ^:dynamic *callbacks*)
(defn- execute-in-tx [db f]
(jdbc/with-db-transaction
[tx db]
(binding [*tx* tx]
(f tx))))
(defn- execute-callbacks []
(doseq [[id cb] @*callbacks*] (cb)))
(defn do-in-tx [db f]
(when (thread-bound? #'*tx*)
(throw (IllegalArgumentException. "Nested transactions are not
supported!.")))
(binding [*callbacks* (atom {})]
(execute-in-tx db f)
(execute-callbacks)))
(defn with-tx
"Call back the specified function providing the current transaction.
If there is no current transaction then an (IllegalArgument)Exception is
thrown. "
[f]
(when-not (thread-bound? #'*tx*)
(throw (IllegalArgumentException. "No transaction found!")))
(f *tx*))
(defn register-cb [id cb]
(when-not (thread-bound? #'*callbacks*)
(throw (IllegalArgumentException. "No transaction found!")))
(swap! *callbacks* assoc id cb))
--
You received this message because you are subscribed to the Google
Groups "Clojure" group.
To post to this group, send email to [email protected]
Note that posts from new members are moderated - please be patient with your
first post.
To unsubscribe from this group, send email to
[email protected]
For more options, visit this group at
http://groups.google.com/group/clojure?hl=en
---
You received this message because you are subscribed to the Google Groups
"Clojure" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.