Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Integrating http-kit and sente #14

Closed
yatesco opened this issue Feb 20, 2015 · 9 comments
Closed

Integrating http-kit and sente #14

yatesco opened this issue Feb 20, 2015 · 9 comments

Comments

@yatesco
Copy link
Contributor

yatesco commented Feb 20, 2015

Hi,

I am struggling to see how to use the sentes and http-kit components. Specifically where does my (ring) handler go?

An upgrade to avoid confusion might also be to change the name of the event-msg-handler that the sente component expects - it is currently 'handler' so I naively passed it my ring handler expecting it to add routes for /chsk. A 10 second perusal of the source code made it clear of course, but a different name might be wise.

I am creating the sente component but then I need to pass that to my ring (defroutes ..) handler, but where do I do that? Should I create a synthetic component which wraps my defroutes so it can access the sente component?

Help :)

@danielsz
Copy link
Owner

Here's how I do it:

My system setup is like this:

(ns front-end.systems
  (:require [system.core :refer [defsystem]]
            (system.components 
             [http-kit :refer [new-web-server]]
             [repl-server :refer [new-repl-server]]
             [sente :refer [new-channel-sockets]])
            [environ.core :refer [env]]
            [front-end.webapp.handler :refer [event-msg-handler app]]))

(defsystem dev-system
  [:sente (new-channel-sockets event-msg-handler)
   :web (new-web-server (Integer. (env :http-port)) app)])


(defsystem prod-system 
  [:sente (new-channel-sockets event-msg-handler)
   :web (new-web-server (Integer. (env :http-port)) app)
   :repl-server (new-repl-server (Integer. (env :repl-port)))])

In the front-end.webapp.handler namespace I define all three routes, app and event-msg-handler vars. Routes may look like this:

(defroutes routes
  (GET "/" [] (html/index))
  (GET  "/chsk" req ((:ring-ajax-get-or-ws-handshake (:sente system)) req))
  (POST "/chsk" req ((:ring-ajax-post (:sente system)) req))
  (route/not-found (html/404)))

App may look like this:

(def app
  (-> routes
      (wrap-defaults site)))

And event-msg-handler may look like this:

(defn event-msg-handler
  [{:as ev-msg :keys [event id ?data ring-req ?reply-fn send-fn]}]
  (let [session (:session ring-req)
        headers (:headers ring-req)
        uid     (:uid session)
        [id data :as ev] event]

       (match [id data]
          ;; your logic
         )))

I hope this helps.

Regarding your suggestions to make things clearer, PR welcome.

@yatesco
Copy link
Contributor Author

yatesco commented Feb 20, 2015

I am still missing how the handler gets provided the 'system' from which to extract the sente plumbing..

(PR to follow tomorrow after some sleep)

@yatesco
Copy link
Contributor Author

yatesco commented Feb 21, 2015

PR issued at #15 for minor rewordings

@danielsz
Copy link
Owner

The system can be referred in any namespace by requiring it:

(ns front-end.webapp.handler
 (:require [reloaded.repl :refer [system]]))

If this clears it up for you, would you consider adding a note to that effect in the README with #15.

Thank you!

@yatesco
Copy link
Contributor Author

yatesco commented Feb 21, 2015

Oh I see - so the system is accessible as a global. Got it.

On 21 February 2015 at 14:14, Daniel Szmulewicz notifications@github.com
wrote:

The system can be referred in any namespace by requiring it:

(ns front-end.webapp.handler
(:require [reloaded.repl :refer [system]]))

If this clears it up for you, would you consider adding a note to that
effect in the README with #15 #15
.

Thank you!


Reply to this email directly or view it on GitHub
#14 (comment).

@yatesco
Copy link
Contributor Author

yatesco commented Feb 21, 2015

Updated readme.org in the PR.

On 21 February 2015 at 14:30, Colin Yates colin.yates@gmail.com wrote:

Oh I see - so the system is accessible as a global. Got it.

On 21 February 2015 at 14:14, Daniel Szmulewicz notifications@github.com
wrote:

The system can be referred in any namespace by requiring it:

(ns front-end.webapp.handler
(:require [reloaded.repl :refer [system]]))

If this clears it up for you, would you consider adding a note to that
effect in the README with #15
#15.

Thank you!


Reply to this email directly or view it on GitHub
#14 (comment).

@danielsz
Copy link
Owner

#15 merged. Thank you for your contribution!

@yatesco
Copy link
Contributor Author

yatesco commented Feb 21, 2015

My pleasure, and thanks for system!
On 21 Feb 2015 20:45, "Daniel Szmulewicz" notifications@github.com wrote:

PR merged. Thanks for contributing!


Reply to this email directly or view it on GitHub
#14 (comment).

@robjens
Copy link

robjens commented May 5, 2015

I've got a slightly different approach, that is, I pass keyword version identities to pull out the desired routes from a map of multiple route (but also webdriver action and some other) definitions. Those components that do use it, expect a version parameter to the constructor to select the correct kv entry. Not that hard to come by though, as soon as you need a few configurations. I used macro's first to be allowed and pass them as arguments in the system component but found them hard to debug and harder to reason about. Also had to do to be allowed and define routes, vars, symbols basically that didn't exist yet or to which the current namespace didn't have a reference about (yet). Currently I store the predefined routes and other bits in the component namespace, but I guess that isn't really the 'right' place either although the easiest one in this case. Another option would be to store them per edn build configuration file. Anyway... details...

Thanks for the system global though... I hadn't figured that one yet and was using component dependencies to pass along information from one result to the next while, in essence, this wasn't strictly required.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

3 participants