title: ring anti-forgery token is unbound in rendered html
body: <p>I need a CSRF token in order for my websockets client to connect to my server. In order to get the token to my client, I embed the token from <code>ring.middleware.anti-forgery/*anti-forgery-token*</code> in a <code>&lt;meta&gt;</code> tag, like so:</p>
  <pre><code>(defn head []
    [:head
     ...
     (let [csrf-token (force ring.middleware.anti-forgery/*anti-forgery-token*)]
       [:meta {:name &quot;csrf-token&quot;
               :content csrf-token}])
     ...])
  </code></pre>
  <p>However, instead of getting an actual token back (i.e. a 60-character-long random base64 string) in the rendered tag, it renders as</p>
  <pre><code>&lt;meta content=&quot;Unbound: #'ring.middleware.anti-forgery/*anti-forgery-token*&quot; name=&quot;csrf-token&quot;&gt;
  </code></pre>
  <p>I also have <code>ring-default</code>'s <code>site-defaults</code> wrapped around the routes as middleware, which includes <code>ring.middleware.anti-forgery</code>.</p>
  <p>Here is the relevant file, handler.clj:</p>
  <pre><code>(ns spotify-client.handler
    (:require
      [ring.middleware.defaults :refer [wrap-defaults site-defaults]]
      [hiccup.page :refer [include-js html5]]
      [ring.middleware.anti-forgery]
      [compojure.core :refer :all]))
  
  (defn head []
    [:head
     ...
     (let [csrf-token (force ring.middleware.anti-forgery/*anti-forgery-token*)]
       [:meta {:name &quot;csrf-token&quot;
               :content csrf-token}])
     ...])
  
  (defn loading-page []
    (html5
     (head)
     [:body {:class &quot;body-container&quot;}
      [:div#app]
      (include-js &quot;/js/app.js&quot;)
      [:script &quot;spotify_client.core.init_BANG_()&quot;]]))
  
  (defn index-handler [_]
    {:status 200
     :headers {&quot;Content-Type&quot; &quot;text/html&quot;}
     :body (loading-page)
  
  (defroutes main-routes
    (GET &quot;/&quot; [] index-handler)
    ...
  )
  
  (def app (wrap-defaults main-routes site-defaults))
  
  </code></pre>
  <p>I'm also running all of this using <code>lein run</code>.</p>
  <p>Now, according to <a href="https://stackoverflow.com/questions/43285188/when-is-the-ring-anti-forgery-token-inserted">this</a> link, the anti-forgery token var would become bound in the context of whatever the current request was, and the ring-anti-forgery middleware is what binds it. When my project was brand new and I had just added wrap-defaults (on the initial ten or so calls to start/reload the server), the token var was bound and rendered correctly. However, after no signficant changes, the token var will not bind and it renders as the &quot;Unbound&quot; string. Once the ring-anti-forgery middleware stopped being called(?) and stopped binding <code>*anti-forgery-token*</code> to an actual value, the var was never bound again. I've tried making a new project a couple of times already and the token var stops being bound after 5-10 server reloads. What could cause the ring-anti-forgery middleware within ring-defaults to stop working even though wrap-defaults is in my code?</p>