Fork me on GitHub
#re-frame
<
2018-01-25
>
kenny01:01:21

FYI: Adding re-frame-trace to my project adds this warning to the initial build:

WARNING: Protocol IFn implements method -invoke with variadic signature (&) at line 61 /home/kenny/.boot/cache/tmp/home/kenny/ui-frontend/8zs/-yzsmxk/ui.out/mranderson047/reagent/v0v6v0/reagent/impl/util.cljs

danielcompton01:01:39

I've noticed that, what version of reagent do you use?

danielcompton01:01:52

I think we need to update it to 0.7.0 or later

kenny01:01:43

We use 0.7.0. Excluding reagent from the re-frame-trace dep doesn't help either.

danielcompton01:01:07

Yeah it's a source bundled version, I'll get a fix out soon, either today or tomorrow

cmal06:01:58

Hi, If I dispatch a reg-event-db/reg-event-fx event that will result exactly the same db value as before, what will re-frame do exactly? Will reg-sub functions run? If so, (it must returns the same value as before)will react lifecycle functions (update, render) run? Thanks!

mikethompson06:01:53

@cmal depends on what you mean by exactly the same db value as before

mikethompson06:01:16

Do you mean the prior db and he new db test identical? to each other? Or do you means they only test = to each other?

mikethompson06:01:39

If identical? then re-frame won't even put a new value into app-db, which, in turn, means that no subs will run (because app-db was not perturbed in any way` If = then the new value will be put into app-db and all layer 2 subscriptions will run (which should be designed to be trivial). And that will be an end to the propogations because the values extracted will all test = to previous values.

mikethompson06:01:37

I just wrote this explanation for re-frame-trace which is kinda related, sorta. It may help: https://github.com/Day8/re-frame-trace/blob/master/docs/HyperlinkedInformation/UnchangedLayer2.md

cmal07:01:41

Thank you very much, @mikethompson, that is exactly what I want to know.

cmal07:01:01

Hi, I also have a question about the todomvc example: https://github.com/Day8/re-frame/blob/5ec86689cc1c22aeca796f6ddb40eef832b23ef0/examples/todomvc/src/todomvc/subs.cljs#L60 The second function in reg-sub :todos takes THREE parameter but the second function in reg-sub :visible-todos takes TWO parameter. Where does the query-v go in the second function of :visible-todos?

danielcompton07:01:11

@cmal if you’re talking about https://github.com/Day8/re-frame/blob/5ec86689cc1c22aeca796f6ddb40eef832b23ef0/examples/todomvc/src/todomvc/subs.cljs#L100

;; Computation Function
  (fn [[todos showing] _]   ;; that 1st parameter is a 2-vector of values
    (let [filter-fn (case showing
the _ is query-v

cmal08:01:04

@danielcompton Is it matter that the function is defined as (fn [[todos showing] _] ... instead of (fn [[todos showing] _ _]...? I found in Line 82 (fn [sorted-todos query-v _] (vals sorted-todos)) it has three parameters. I am not sure, does cljs support variable parameter numbers, or is this a feature provided by re-frame? Sorry have I describe the question clearly?

danielcompton08:01:28

I'll do that now, thanks

carkh09:01:40

re-frame-trace, is it in the same space as re-frisk ?

carkh09:01:02

mhh looks nice i wonder how they compare... will have to try that i guess =)

cmal10:01:29

@mikethompson Hi, mike. If I have some raw js object in db, can I make layer 3 subscriptions not update when db values are equal? It seems = cannot compare raw js objects. cljs.user=> (= #js {:a 1} #js {:a 1}) ;;=>false

mikethompson10:01:43

If there are (mutable) js objects in app-db, then ... I dunno what will happen

cmal10:01:08

sorry for that, it seems there are also functions in db (= (fn []) (fn [])) ;;=> false

cmal10:01:20

We store echarts options in db, those options have functions in their object.

cmal10:01:11

It seems we should change our db design.

cmal10:01:00

Thanks, mike!

p-himik10:01:14

What is the general advice to deal with JS libraries that offer their own data management? E.g. I'm integrating Bokeh and re-frame. Bokeh has its own models that can talk to a server, and these models can store a significant amount of data efficiently. This data can be changed often (and the models notify anyone interested about it), so I don't want to use js->clj for all the data - just for the data that I need. Would something like storing an update counter in app-db for each Bokeh model help?

danielcompton11:01:25

@kenny re-frame-trace 0.1.16-20180125.112049-1 is out with your fixes

danielcompton11:01:56

@carkh I'd say they're broadly in the same space of debugging/inspecting/profiling tools for re-frame

carkh11:01:53

@danielcompton i'll be sure to check it out. competition is good =D

manuel11:01:38

just chiming in to thank the re-frame crew for re-frame-trace. Just added it to my project and it's really awesome.

tomaas13:01:26

Hi, I [recom/v-box :children [(map-indexed (fn[]) data)]] and i'm getting the warning Warning: Every element in a seq should have a unique

tomaas13:01:15

with divs I use (into [:div] (map-indexed...)

tomaas13:01:48

How can I solve this? Adding ^{:key i} does not work

p-himik13:01:52

@tomaas Where do you add it? Also, don't use an element's index as a key - there's plenty written about its shortcomings.

tomaas13:01:15

I add on map-index argument - (fn [] ^{:key i} [comp])

p-himik13:01:38

Is comp some function, or is it a keyword like :div>a?

tomaas13:01:38

it's whatever component or plain html structure

tomaas13:01:57

I use ids instead of indexes, I pasted just an example

p-himik13:01:38

Can you show the complete code that uses map-indexed?

tomaas13:01:33

oh, i think I see what im doing wrong. Should pass :children: (vec (map-indexed....))

tomaas13:01:59

as it receives [[comp1][comp2]] in this from

p-himik14:01:20

vec causes lazy seq materialization, which removes the need for :key. Are you sure that (:id item) returns unique :id each time?

p-himik14:01:22

Ah, I see that you wrapped map-indexed in another vector. You can just pass (map-indexed ...) to :children. With unique :keys it should work without warnings.

sggdfgf15:01:50

Hi , how to make this to work - works on Firefox only. I suppose it should need to have a callback on onChange, but I cannot reffere "this" on the outer Hiccup tag :thinking_face: `(defn phone-chooser [] [:select (map (fn [phone] [:option {:on-click (fn [e] (re-frame/dispatch [:switch-phone phone]))} (:phone-name phone)]) devices)])`

p-himik15:01:20

@faxa I think it's better to use :select's :on-change

p-himik15:01:14

Also, if you really, really need to have access to the element inside some callback, you can use refs: https://reactjs.org/docs/refs-and-the-dom.html

sggdfgf15:01:17

@p-himik how would you use :selects's :on-change ? this is what I try to achieve... In particular how to pass the the selected data into callback?

p-himik16:01:00

@faxa

[:select
  {:on-change #(js/console.log "Changed" (.. % -target -value))}
  (for [[id label] {1 "one", 2 "two", 3 "three"}]
    ^{:key id} [:option {:value id}
                 label])]

sggdfgf16:01:20

@p-himik thank you! You are tremendous! 🙂

stvnmllr218:01:18

Anyone come up with a standardized way to prevent double clicking a button? Thinking now to make button a component with local state that changes on click, and resets itself with a setTimout. Still doesn't seem right though.

kkruit18:01:27

Hey all, I'm having an issue wrapping my head around how i would show a loading bar or something while a computation layer subscription is running.

kkruit18:01:42

I have a large data-set and a filter with a subscription listening to both. I want to show a loading bar while the filtering is happening.

Ivan18:01:44

@stvnmllr2 I am not familiar with re-frame (yet!) but the canonical solution is to disable the button until the action is sent/confirmed/done

Ivan18:01:25

disable may mean to actually disable it, or make it disappear and show a spinner, etc

Ivan18:01:46

ie, give feedback that something is happening behind the scenes

stvnmllr218:01:36

Thanks @ivan.kanak_clojurians, Yeah, just wondering specifics of what others have done. My state var would change and disable the button while it's running.

stvnmllr218:01:28

I also have a loading div like @kkruit needs. Basically, i send an event that sets a var in appdb, and then my loading div component is subscribed to that, so when "showLoading" entry is true, the div is visible. Then when request is don, I set entry in db back to false.

kkruit18:01:38

I guess maybe i should do the "computation" as a coeffect instead of a computation...

kurt-o-sys20:01:45

I have problems to make the repl (and cider) work properly using the reframe template from https://github.com/Day8/re-frame-template:

(defproject [...]
[...]
:plugins [[lein-environ "1.0.2"]
[lein-cljsbuild "1.1.5"]
[lein-shell "0.4.0"]
[cider/cider-nrepl "0.16.0"]
[lein-asset-minifier "0.2.7" :exclusions [org.clojure/clojure]]]
[...]
:figwheel {:http-server-root "public"
:server-port 3449
:nrepl-port 7002
:nrepl-middleware ["cemerick.piggieback/wrap-cljs-repl"]
:css-dirs ["resources/public/css"]
:ring-handler ui-app.handler/app}
[...]
when trying to run a repl:
$ lein repl
[...]
#error {
:cause Unable to resolve symbol: wrap-file-info in this context
:via
[{:type clojure.lang.Compiler$CompilerException
:message java.lang.RuntimeException: Unable to resolve symbol: wrap-file-info in this context, compiling:(ui_app/repl.clj:19:7)
:at [clojure.lang.Compiler analyze Compiler.java 6792]}
{:type java.lang.RuntimeException
:message Unable to resolve symbol: wrap-file-info in this context
:at [clojure.lang.Util runtimeException Util.java 221]}]
:trace
[[clojure.lang.Util runtimeException Util.java 221]
[clojure.lang.Compiler resolveIn Compiler.java 7299]
What am I doing wrong? (Or rather, how can I make cider work?)

gadfly36120:01:08

@kurt-o-sys are you sure you're using re-frame-template .. i see a bunch of deps that the template doesn't include. I'd recommend starting fresh with lein new re-frame foo +cider

kurt-o-sys20:01:50

ok... let me try.

kurt-o-sys21:01:50

still having issues, will check again tomorrow...

souenzzo23:01:21

(defn todo
  [{:keys [id]}]
  (let [{:keys [todo/label]} @(rf/subscribe [:todo-by-id id])]
    [:div label]))
(defn app
  []
  (let [{:keys [user/name
                user/todo-ids]} @(rf/subscribe [:current-user])]
    [:div
     [:p name]
     (for [id todo-ids]
       [todo {:id id}])]))
(defn todo
  [{:keys [todo/label]}]
  [:div label])
(defn app
  []
  (let [{:keys [user/name
                user/todos]} @(rf/subscribe [:current-user])]
    [:div
     [:p name]
     (for [td todos]
       [todo td])]))
I know, both works. But one of these can be considered better then the other? By your experience, on larger apps, one of these fit's better then the other?

mikerod00:01:12

@U2J4FRT2T I think there are tradeoffs in those two approaches. In the first approach, I think that the todo component is potentially less reusable. In some cases that is fine. However, since it directly embeds its subs, that may specialize it somewhat to a certain subs when others could want to use it for different data sources (probably doesn’t make a lot of sense in the “todo example”, but thinking more generally).

mikerod00:01:21

One potential advantage I see to this approach though is that it frees up app from needing to have any understanding of what data details todo needs to know about the todos

mikerod00:01:30

The id just conveys which one to build in context to, whatever todo needs to do.

mikerod00:01:38

Also, it is possible that if the object for td was harder slow to compare with =, then the rendering may be slower if you pass the entire object td to todo rather than just an id. id is faster to compare and may be a benefit for the Reagent change-detection used for re-rendering components.

mikerod00:01:46

In the second approach, I think the tradeoffs are just the reverse of what I’ve already said.

souenzzo00:01:49

So, probably I will have both in a larger app, and it's not a problem, right? There is some other "solution" to this "problem"?

mlatu02:01:44

when you would like to filter todos, how would you do in the first approach?

mikerod04:01:00

@U0NK6SBJ5 You could return nil from todo right?

mikerod04:01:32

@U2J4FRT2T it is a pretty small example. I don’t know that I see the particular problem you are wanting to address.

mikerod04:01:43

I think both sorts of cases come up for me at least though.