I think the most important rule when using component is to only use local state like Timothy stated, i.e. nothings gets def-ed. You could write an application that a -main function that starts the system and you would never need a global reference to the system.
In practise however, you do make references to the current system to support working in the REPL (see README here <https://github.com/stuartsierra/component/#reloading>) and I also use references to the system to inspect db state etc in tests, but for that `let` blocks also work well. I would recommend to continue playing with the bare metal component for a while to get an understanding of the concept, after a while I think you will want something smarter. We're using system-graph <https://github.com/RedBrainLabs/system-graph> that helps to stop thinking and managing dependencies and recently we have a built a small layer on top of that so we even have flexible graphs in a convenient way. On Tue, Jun 9, 2015 at 8:33 AM, Atamert Ölçgen <mu...@muhuk.com> wrote: > > > On Tue, Jun 9, 2015 at 6:12 AM, Timothy Baldridge <tbaldri...@gmail.com> > wrote: > >> Stuart addresses two anti-patterns in your PRs. Perhaps I can help >> explain them. >> >> Let's say we have a system that looks like this: >> >> (defrecord DBConnection []) >> >> (defrecord DBLayer [db-connection]) >> >> (defrecord AppLayer [db-layer]) >> >> We can construct a system thusly: >> >> {:db-connection (->DBConnection ...) >> :db-layer (->DBLayer ...) >> :app-layer (->AppLayer ...)} >> >> And start it up: >> >> (def my-system (start-system system-map)) >> >> >> First of all, what you need to recognize is that every component now has >> it's dependencies assoc'ed into the component. So each component should >> only deal with it's local view of the system: >> >> (defrecord AppLayer [db-layer] >> IDoStuff >> (do-stuff [this] >> (print-data (get-data db-layer) >> (get-data2 (:db-layer this))) >> >> What should not happen is that the AppLayer should do this: >> >> (print-data (:db-layer my-system)) >> >> If a component does this it now has access to the entire system, and that >> circumvents one of the reasons component was created, to help improve >> separation of concerns. >> >> In your other example you're doing something like this: >> >> (defrecord AppLayer [db-layer] >> IDoStuff >> (do-stuff [this] >> (run-query (:db-conn db-layer) "select foo from bar"))) >> >> The problem with this is that AppLayer is assuming that the db-layer has >> a connection to the db. This also violates the separation of concerns. >> Instead AppLayer should include a db-connection as a dependency if it is >> needed by the app layer code. >> > > This is also known as The Law of Demeter. ( > http://en.wikipedia.org/wiki/Law_of_Demeter) > > - Each unit should have only limited knowledge about other units: only > units "closely" related to the current unit. > - Each unit should only talk to its friends; don't talk to strangers. > - Only talk to your immediate friends. > > >> >> So that sums up Stuart's two replies. a) don't touch the system from >> inside a component, the system map is only for starting and stopping the >> system, and to provide an entry point. b) don't reach into other components >> from a component >> >> >> Timothy >> >> On Mon, Jun 8, 2015 at 9:35 PM, James Reeves <ja...@booleanknot.com> >> wrote: >> >>> My recommendation is to use a closure. So I'd write your example as: >>> >>> (defn username-endpoint [{:keys [db]}] >>> (routes >>> (GET "/:username" [username] >>> (let [user (users/get-user db username)] >>> (str "<h1>Hello " (:name user) "</h1>"))))) >>> >>> So you pass your configuration map into the endpoint function, which >>> returns a handler. >>> >>> You can then wrap this in a component: >>> >>> (defrecord EndpointComponent [build-routes] >>> component/Lifecycle >>> (start [component] >>> (if (:routes component) >>> component >>> (assoc component :routes (build-routes component)))) >>> (stop [component] >>> (dissoc component :routes))) >>> >>> Incidentally, the above code is taken directly from Duct >>> <https://github.com/weavejester/duct>, a template and small supporting >>> library I've written for building component-based web apps. >>> >>> I've also written a blog article >>> <https://www.booleanknot.com/blog/2015/05/22/structuring-clojure-web-apps.html> >>> around >>> general best practice for this type of style. >>> >>> - James >>> >>> >>> On 8 June 2015 at 22:51, Dru Sellers <d...@drusellers.com> wrote: >>> >>>> So, I guess I am a bit lost, how does someone actually use component? I >>>> have an application all set up with it and it seems to be working as I >>>> would expect but Stuart seems to be steering me in a different direction. >>>> >>>> https://github.com/stuartsierra/component/pull/35 >>>> >>>> https://github.com/stuartsierra/component/issues/34 >>>> >>>> So I'll try and paint a full picture. >>>> https://gist.github.com/drusellers/8109dce4b9fb19c14ebb >>>> >>>> I know compojure and component / reloaded may not play well, but I'm >>>> trying to figure out how to best use the system var. Am I close, I'd love >>>> to give back a decent PR to the README.md of the component repo to help >>>> others as they come along. >>>> >>>> -d >>>> >>>> -- >>>> You received this message because you are subscribed to the Google >>>> Groups "Clojure" group. >>>> To post to this group, send email to clojure@googlegroups.com >>>> Note that posts from new members are moderated - please be patient with >>>> your first post. >>>> To unsubscribe from this group, send email to >>>> clojure+unsubscr...@googlegroups.com >>>> 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 clojure+unsubscr...@googlegroups.com. >>>> For more options, visit https://groups.google.com/d/optout. >>>> >>> >>> -- >>> You received this message because you are subscribed to the Google >>> Groups "Clojure" group. >>> To post to this group, send email to clojure@googlegroups.com >>> Note that posts from new members are moderated - please be patient with >>> your first post. >>> To unsubscribe from this group, send email to >>> clojure+unsubscr...@googlegroups.com >>> 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 clojure+unsubscr...@googlegroups.com. >>> For more options, visit https://groups.google.com/d/optout. >>> >> >> >> >> -- >> “One of the main causes of the fall of the Roman Empire was that–lacking >> zero–they had no way to indicate successful termination of their C >> programs.” >> (Robert Firth) >> >> -- >> You received this message because you are subscribed to the Google >> Groups "Clojure" group. >> To post to this group, send email to clojure@googlegroups.com >> Note that posts from new members are moderated - please be patient with >> your first post. >> To unsubscribe from this group, send email to >> clojure+unsubscr...@googlegroups.com >> 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 clojure+unsubscr...@googlegroups.com. >> For more options, visit https://groups.google.com/d/optout. >> > > > > -- > Kind Regards, > Atamert Ölçgen > > ◻◼◻ > ◻◻◼ > ◼◼◼ > > www.muhuk.com > www.olcgen.com > > -- > You received this message because you are subscribed to the Google > Groups "Clojure" group. > To post to this group, send email to clojure@googlegroups.com > Note that posts from new members are moderated - please be patient with > your first post. > To unsubscribe from this group, send email to > clojure+unsubscr...@googlegroups.com > 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 clojure+unsubscr...@googlegroups.com. > For more options, visit https://groups.google.com/d/optout. > -- You received this message because you are subscribed to the Google Groups "Clojure" group. To post to this group, send email to clojure@googlegroups.com Note that posts from new members are moderated - please be patient with your first post. To unsubscribe from this group, send email to clojure+unsubscr...@googlegroups.com 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 clojure+unsubscr...@googlegroups.com. For more options, visit https://groups.google.com/d/optout.