Fork me on GitHub

What would be the re-frame way of enforcing updates based on the result of a calculation, not data itself changing. Let's say I have a date in my app-db: {:started-at (js/Date.)} and I want to display time passed from the started-at Is there a way to form a subscription that as an input takes a calculation: (- (js/Date.) started-at)? Is that a good idea at all? If I wanted to make the UI truly react to data changes, I could create a handler that changes writes to :ms-passed ... every second, and subscribe to that - would that be a route and why? An alternative would be force updates of a component every second and do the calculations in the component itself, but that is limiting and hacky.

(defn ticking-component
  "Updates every second."
  (let [!interval (atom nil)]
     {:component-did-mount (fn [this]
                             (reset! !interval
                                     (js/setInterval #(r/force-update this true) 1000)))
      :component-will-unmount #(js/clearInterval @!interval)
      :reagent-render f})))

(defn time-passed [started-at]
  [ticking-component (fn []
                       (- (js/Date.) started-at))])


If you consider current time a part of your application state, then store it in the DB. If not, then just compute the delta in the components.


That's the puzzle I'm having. I do not consider it a part of my data - I think the started-at is everything I need to calculate all the UI needs. However I have quite a few places where the result of that calculation is used, which means if I keep it in the UI then I move a lot of logic there. Ideally, I'd be able to create subscriptions based on the calculated time passed.


> then I move a lot of logic there Personally, I wouldn't consider this "a lot" or even "logic". A matter of taste, perhaps. This calculation that you need is just a simple (x) -> x function, akin to inc for example. Would you want to create a sub specifically to avoid using inc in a view? Subscriptions are cached functions of the application state. If something is not a state, don't use a sub for that.


Although I guess that (x) -> x can be viewed as (x, x) -> x if you make it referentially transparent so it accepts the current time as one of the arguments. Doesn't really change the reasoning though.


Fair enough, thanks for sharing your thoughts 👍


Hmm, I can also force re-calculation of a subscription by passing an arbitraty argument (ie (js/Date.) ) from that hacky ticking-component above.


@U0C10BTPA I do something similar by creating a subscription for the current time that updates on some set cadence.


Very cool @UFJCSRT2M - thanks for sharing