Clojurians
#om
<
2016-12-11
>

This page is not created by, affiliated with, or supported by Slack Technologies, Inc.

tobiash11:12:24

is there a way to pass through IQuery and IQueryParams? I'd like to write a higher-order-component to re-use some functionality

anmonteiro11:12:38

@tobiash you can write "pure" components without queries

anmonteiro11:12:44

not sure if it's what you're looking for

tobiash11:12:47

i want to refactor code that subscribes to events in componentDidMount and then unsubscribes accordingly in componentWillUnmount

tobiash11:12:42

mh, ok instead of wrapping the "higher-order component" around my component, i could wrap my child components with it. But I think hoc is a nice pattern

tobiash11:12:01

maybe that would be a nice addition to om.next?

tobiash12:12:56

it might be that I'm looking at these things too much from a React perspective, but I keep running into these issues: I have navigation bar that also displays some action buttons, depending on the current route. How do get the button presses to the current route? Currently I use a core.async channel, but that means that every route component has to subscribe/unsubscribe to it

tobiash12:12:47

maybe it would be nicer if the route component implemented some protocol to receive the events and then I would not need the sub/unsub boilerplate

nha14:12:29

I am trying to make server-side rendering in om,next, and have an exception creating the server reconciler, if someone has a clue: http://stackoverflow.com/q/41082153/1327651

anmonteiro14:12:49

@nha that's because stuff in the reconciler has circular references to it

nha14:12:21

Oh ok - but can I work around it?

anmonteiro14:12:56

yeah, with remove-method and prefer-method

anmonteiro14:12:05

the problem is just about the printing

nha14:12:05

I am trying something like that right now: (prefer-method print-method om.next.Reconciler clojure.lang.IRecord) (does not work - never used prefer-method before)

nha14:12:31

(prefer-method print-method om.next.Reconciler clojure.lang.IDeref) does not throw, but then does not seem to change anything

nha14:12:14

Anyway, since this only printing putting it in a var is fine.

nha15:12:09

So far I tried:

(prefer-method print-method om.next.Reconciler clojure.lang.IRecord)
(prefer-method print-method om.next.Reconciler clojure.lang.IDeref)
(prefer-method print-method rethinkdb.core.Connection clojure.lang.IPersistentMap)
(defmethod print-method om.next.Reconciler [r writer]
  (print-method {:config (:config r)
                                    :state (:state r)} writer))
but none of these seem to work

nha15:12:46

Am I barking at the wrong tree?

anmonteiro15:12:15

I've gotten that to work before, but I don't quite remember how

anmonteiro15:12:29

I remember also using remove-method

nha15:12:51

I'll try that, thanks

nha16:12:10

Ok that will be for another day. How can I render-to-str a CompassusApplication. (in clojure)?

anmonteiro16:12:39

@nha hrm, I don't think I've ever tried it :slightly_smiling_face:

anmonteiro16:12:48

but you should be able to compassus.core/mount!

anmonteiro16:12:52

with a nil target

anmonteiro16:12:05

then pass the return of that to render-to-str

nha16:12:16

Thanks, will try :slightly_smiling_face:

anmonteiro16:12:45

@nha PR welcome adding a test for it, even if it works

anmonteiro16:12:57

the Compassus tests run in Clojure too

nha16:12:17

yes I saw that - hence I assumed it worked server-side as well

nha16:12:50

hmm it seems to throw (compassus/mount! app nil):

Unhandled java.lang.ClassCastException
   clojure.lang.PersistentHashMap cannot be cast to java.io.PushbackReader

anmonteiro16:12:02

@nha the whole stacktrace would be more helpful

anmonteiro16:12:15

looks like either: 1) a problem with your parser function 2) a bug in Compassus :slightly_smiling_face:

nha16:12:03

could be my parser to be honest

nha16:12:20

migrating from cljs to cljc - I may have things lying around

nha16:12:34

I'll try doing that in the compassus repo

anmonteiro16:12:45

right, there are a few hurdles you may have to go through

anmonteiro16:12:57

in any case, I'm happy to know you're using Compassus!

nha16:12:59

Well I'm just experimenting :slightly_smiling_face:

nha16:12:29

(I am not sure I understand the different tradeoffs of the different routing approaches)

anmonteiro16:12:50

Compassus is just a library around the union query approach

nha16:12:52

But yes I am trying to get server-side + compassus + bidi althogether

anmonteiro16:12:00

not much else there tbqh

nha16:12:34

Yes I saw that. previously I had a transact! in a key :app/route. looks similar

nha16:12:49

Something like that:

(componentDidUpdate [this _ _]
                      "Sync state -> url"
                      (let [{:keys [current-route]} (om/props this)]
                        (when (not= current-route (url->route js/location.pathname))
                          (pushy/set-token! history (route->url current-route)))))
  (componentDidMount [this]
                     "Sync url -> state"
                     (let [listener (pushy/pushy #(om/transact! this `[(route/update {:value ~%}) :route])
                                                 url->route)]
                       (pushy/start! listener)
                       (set! history listener)))
  (componentWillUnmount [_]
                        (pushy/stop! history))
I made it work but now completely sure how now to be honest :confused:

nha16:12:40

By the way, I see you do not use componentDidUpdate in the bidi mixin?

anmonteiro16:12:41

@nha it's just a simplistic example

anmonteiro16:12:46

up to you to implement it if you want

anmonteiro16:12:05

there's actually no will-update mixin

anmonteiro16:12:14

so PR welcome for that and did-update!

nha16:12:24

aha ok :slightly_smiling_face:

atdixon17:12:50

re: om/next, i have multiple components (to be added via add-root!), all contending to read/mutate the same application state atom (and reading & updating the same keys therein). if I use the same reconciler for all components i seem to get errors like "no queries exist for XComponent", etc. is the correct thing to do to create separate reconciler for each component? that doesn't seem right, though. i want component X to modify, say, :some-data, and have Y update as necessary in response. i would think a singular reconciler would need to orchestrate that? what am i missing?

drcode20:12:51

@atdixon No, one reconciler should work fine. You are probably not following the 3 golden rules of OmNext queries: 1. There must be at least one query key for every component (you can't just say "the parent and this child both use the :foo query endpoint"- Each component needs its own endpoints in the query tree) 2. The query for a parent must call om/get-query on all children to populate its own query 3. The render function in the parent must pass props to the children in exactly the same manner as described in the parent query.

drcode20:12:11

In the past, when I was breaking these rules, I got the "no queries exist of XComponent" error.

atdixon21:12:29

Thx for the reply @drcode -- I believe I'm following those rules. my problem seems to stem from trying to add seperate roots (add-root!) but sharing the same reconciler and state. Can I have more than one root for the same state? For the same reconciler?

drcode21:12:34

Oh you got me there, didn't realize you have multiple roots... I don't have any insight into that use case...