Fork me on GitHub
#re-frame
<
2019-06-06
>
hendore00:06:08

(rf/reg-sub
 :project
 (fn [db] (db :project)))

(rf/reg-sub
 :project/name
 :<- [:project]
 (fn [project] (project :name)))

(rf/reg-sub
 :project/author
 :<- [:project]
 (fn [project] (project :author)))

(rf/reg-sub
 :project/identifier
 :<- [:project/author]
 :<- [:project/name]
 (fn [[authors-name project-name]]
   (projects/project-identifier authors-name project-name)))

hendore00:06:11

Does it make sense to have the :project/name and :project/author subs or should I just let the :project/identifier sub subscribe to :project and pluck out the name and author in there?

hendore00:06:59

I do use the :project/name in the ui along with the :project/identifier

hendore00:06:36

(defn view
  "Top level application view to render all the things"
  []
  (let [project-name (rf/subscribe [:project/name])
        project-identifier (rf/subscribe [:project/identifier])]
    (fn [] ...)))

hendore00:06:35

Another quick question, why wouldn’t I want to just subscribe to :project in this view and pluck out the name and author in the view which i can then pass into project-identifier within the view function?

manutter5111:06:17

The main function of subscriptions is to support re-rendering of components if (and only if) there is a change in the data it depends on. If you have a component that lets you change, say, the project name, then it makes sense to have a :project/name sub so that your UI will re-render the name as needed, without over-re-rendering. If, on the other hand, your UI lets you switch between different projects but does not support editing the project name, author, etc, then the :project sub is all you really need (though it wouldn’t be wrong to go ahead and add subs for name and author, if you like).

hendore17:06:08

Sorry for the late response, thank you very much for taking the time to provide an answer. From what you describe, it sounds as though plucking fields from a map returned from a subscription is ok to do in the view (if I wasn’t editing the name, author or description)

(defn project-info
  []
  (let [project-info (rf/subscribe [:project])
        name (@project-info :name)
        author (@project-info :author)]
        description (@project-info :description)
    [:div
      [:h1 name]
      [:h2 author]
      [markdown description]]))

hendore17:06:49

without having to create separate level 2 subscriptions for each field.

hendore17:06:07

But, if the project map changes in any way ( key/value added/removed or updated) then project-info will re-render (even if name, author and description didn’t change)?

manutter5117:06:10

I haven’t tried adding new keys to the map, but I expect that any change to the project-info map would trigger a re-render, yes.

hendore17:06:51

Thanks 🙂

Jacob Haag15:06:23

Hey all, does anyone know how and if it's possible to have a :dispatch and :dispatch-later in a reg-event-fx map?

(re-frame/reg-event-fx
 ::on-foo-buzz
 (fn [{:keys [db]} _]
   {:dispatch       [::foo]
    :dispatch-later [{:ms 200 :dispatch [::buzz]}]}))
That's the way I have it currently but it seems it's not calling the :dispatch-later's ::buzz

manutter5115:06:40

Hmm, looks correct, maybe insert a deliberate typo in ::buzz and see if you get a “No handler for event :some-ns/buzzz” error in the console?

danielneal15:06:25

@jacobhaag17 yep, combining dispatch and dispatch-later should be absolutely fine

Jacob Haag16:06:53

Okay, after looking at the code it as an issue with our ::foo function, thanks for the clarification @manutter51 and @danieleneal