This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2015-07-24
Channels
- # admin-announcements (21)
- # announcements (1)
- # beginners (36)
- # boot (48)
- # cider (21)
- # clojure (61)
- # clojure-italy (4)
- # clojure-japan (5)
- # clojure-norway (2)
- # clojure-russia (2)
- # clojure-sg (2)
- # clojure-uk (3)
- # clojurescript (33)
- # core-async (5)
- # core-typed (1)
- # cursive (13)
- # datomic (34)
- # devops (38)
- # editors (24)
- # events (10)
- # ldnclj (14)
- # off-topic (31)
- # onyx (4)
- # re-frame (84)
hi all - just a recommendation for https://github.com/Day8/re-frame/wiki/Debugging if you haven’t seen it already.
and a tip which caused pretty much my entire page to re-render everytime, for anything: (= (fn [] {}) (fn [] {})) is false
Hey! That's still a top secret work in progress
if anybody wants to answer (my post at) https://groups.google.com/d/msg/clojurescript/Hzv0m4Zag_4/w2q0YYIl3lcJ then I will put it into a wiki doc as I think it is a common use-case which I can’t see an obvious answer to.
@colin.yates: How would you compare functions? If you give pure functions arguments and compare the result, sure, but otherwise? 😄
my point was not to include anonymous fns in a map. I often want to pass callback handlers to generic components (generic-comp {:handler #(println “woot”)}). This will cause it to always be evaluated as the data is never equal.
the answer is (defn handler [_] (println “woot”)) (generic-comp {:handler handler})) as (= handler handler) is true
(is that what you were referring to?)
yes, exactly. I don’t understand why inline fns aren’t - some deep internal compiler quirk maybe?
I wouldn't be doing this:
(defn table-row [_]
(fn [raw-row]
(let [decorated-row (subscribe [:decorated-row (row)]
[:tr [:td (:manager-desc @row)]])))
@colin.yates: (let [f1 (fn [] "asd")] (= f1 f1))
is true
That creates a subscritpion on every renender
@profil sure - but you are comparing symbols not inline fns then
@profil - I think we are in agreement
thanks @mikethompson - what would be your alternative?
The readme says: "subscriptions can only be used in Form-2 components and the subscription must be in the outer setup function and not in the inner render function. So the following is wrong (compare to the correct version above)"
(defn table-row [row-id]
(let [row (subscribe [:row-for row-id])]
(fn []
[:tr {:key row-id} [:td (:manager-desc @row)]]))
Something like that
the returned function will be used as the render function, which will call subscribe on each render
ah OK - I had mistakenly thought form 2 fns were only called once regardless of data, not once per instance of data!
1. pass in the id
2. subscribe based on the id
3. make sure you put on a :key
I mistakenly interpreted "called once to initialise the component”. I see. Yes, all makes sense now.
thanks both - you won’t believe how much angst I have had over this!
Be sure to go over: https://github.com/Day8/re-frame/wiki/Creating-Reagent-Components#form-2--a-function-returning-a-function
is “called once to initialise each instance of the component” more accurate?
the other part that misled me is "Remember, that outer function is only called once. So its parameters hold the initial set of parameter values. "
I took “initial set of parameter values” to mean the very first set of parameters it was ever called with (so the very first row-id in Mike’s example).
@mikethompson: would you mind a PR?
Sure. Or even something in the FAQ?
I will do both - thanks a bunch guys, really.
Or amendments to the "Creating Reagent Components" Wiki
Note point 3, above ... :key
is important
because that defines an instance of a component?
Hmm. I'm sitting here puzzling about how to explain this
The answer is yes ... the key will link the component with the particular row id
(I am under the weather with a temperature so it may well be me being a numpty ;-))
@colin.yates: See the dynamic-children part from react http://facebook.github.io/react/docs/multiple-components.html#dynamic-children
Notice that the subscribe is for a certain id.
We then want to make sure that same id is put on the component (via the :key
)
right. My brain is still used to thinking in terms of Java classes which I think is insufficient to model the various lifecycles and relationships going on here.
I think about subscriptions like I do a database select
I pass in the "parameters" for the select
select from managers where id=12
I see this as (subscribe [:manager 12])
Kinda, sorta
I have to head off
Before I go ... useful tip ....
(defn table-row [row-id]
(let [row (subscribe [:row-for row-id])]
(fn []
[:tr {:key row-id} [:td (:manager-desc @row) (edn->hiccup @row)]])) ;; <-------
See that (edn->hiccup @row)
bit that I added
oh that is nice.
Thanks @yogthos (library) and @escherize (concept for using it)
Continuing the discussion about subscriptions and stitching together data I have created https://github.com/yatesco/re-frame-stiching-together
Thoughts, feedback etc. most welcome (I have a bit of a virus at the moment so go gentle :))
Attempting so subscribe to a keyword with more than one slash seems to be throwing: clojure.lang.ExceptionInfo: Invalid token: :materials/load/response
. I presume this is cljs limitation?
@petrus I think that is a problem with namespacing; :a/b is a keyword 😛 in namespace :a.
I work around this by :a/b_c
@colin.yates: That's a useful repo, thanks! I don't have enough time to properly comment. Under the pump. But I added an assert below ... just to check on something.
(defn style-4-row [fruit-id]
(let [decorated-row (re-frame/subscribe [:style-four/decorated-row fruit-id])]
(fn [new-fruit-id]
(assert (= new-fruit-id fruit-id)) ;; <-- added
(.log js/console "style-4-row for " (clj->js @decorated-row))
[table-row @decorated-row])))
my understanding/assumption is that that equality will always be true - is that your intention?
I'm thinking more about the time that someone deletes the first fruit, and all the components shuffle "up" by one
ah ok, in my example they are domain ids not indexes so that shouldn’t be a problem?
Being paranoid
Remember the subscription is based on the INITIAL value of fruit-id
(in value in the outer
)
But thereafter, on each render, a new value could be supplied EXCEPT you supply a :key
on the component. So the id in the inner render should always match the outer
This is more likely a concern when the list of fruit is more dynamic, or reordered.
Uggh. Head full. Not explaining very well sorry.
np, I think I see what you mean. I can see this working only if that id never changes, hence the domain id not ordinal id. The {:key} is necessary to maintain that association?
Yeah. Let me put it this way:
1. We subscribe based on the INITIAL id passed in
2. So we'd better make sure that later, on each render, we think we are still rendering that same id.
3. We believe we will be because we supply a :key
on each row component.
4. But that assert is me being paranoid.
yep, understood. I think I should add that explanation to the various edits on the wiki I made earlier and update my repo as well.
will do that tomorrow (got to run now).
Thanks!
np and my pleasure. I feel bad I don’t have more time to contribute to open source, so no need to thank me at all