Fork me on GitHub
#fulcro
<
2018-02-21
>
mss01:02:55

in a component’s query, is there a way of expressing “take this part of the query, and plug it into this ident elsewhere in the query and use it to do a lookup for some properties”? basically an ident query with a parameter from the query itself as the id of the ident like:

{:query [:thing-id
         {[:other-thing/by-id :thing-id] [:thing/name]}]}
afaict, that query ends up resolving to something like (get-in state [:other-thing/by-id :thing-id]) as opposed to (get-in state [:other-thing/by-id 123])

wilkerlucio02:02:48

@mss maybe you meant to write:

{:query [:thing-id
         {[:other-thing/by-id :thing-id] [:thing/name]]}}
?

mss02:02:52

yep I did

mss02:02:55

sorry about that just edited

wilkerlucio02:02:17

usually you don't do ident queries from identities

wilkerlucio02:02:29

on the server parser, you give a name of the association of the data

wilkerlucio02:02:52

and then though normalization the idents are filled on the client side

mss02:02:20

when you say “do ident queries from identities”, could you expand on that a little more? sorry just not quite exactly what you’re getting at

wilkerlucio03:02:32

@mss ah, sorry, I might had only understood your question

mss03:02:33

no worries. I guess the crux of what I’m trying to do is a parameterized ident + property lookups at that ident based on some other property in the query. feels insane but maybe that’s a thing?

wilkerlucio03:02:18

humm, you mean like, getting and account-id and using that value to look up some other identity on the same query level?

mss03:02:37

specifically in my case I have a prop passed in from a router, and want to do lookups based on that prop

mss03:02:52

can’t figure out a way to finagle my component to have the lookup work correctly

wilkerlucio03:02:58

that can be a pain over time for you, what we usually do instead is make this kind of integration on the server side

wilkerlucio03:02:25

so instead of querying identities in sub-queries, you give a name to that relation, and you server is responsible for implementing it

wilkerlucio03:02:33

so, instead of:

wilkerlucio03:02:25

[{:app/current-user
  [:user/account-id
   {[:account/by-id :user/account-id]
    [:account/account-number]}]}]

wilkerlucio03:02:50

you would use:

wilkerlucio03:02:53

[{:app/current-user
  [:user/account-id
   {:user/account [:account/account-number]}]}]

wilkerlucio03:02:55

@mss, this way you encode the relationship in a name (`:user/account` on this case), and can go crazy about it on the server (like, you might need to get an attribute and use to query a different server to read some id to make a relationship, etc...)

mss03:02:10

absolutely that makes a ton of sense. unfortunately afaict my case is a little weirder as I’m trying to resolve a query like that based on a route param from my router. so router toggles component with a value for a certain route param, and I need to do some lookups based on that. feels whacky and like I might be doing things incorrectly

mss03:02:32

obv I can just pull the whole table into my component and do a lookup inside of it based on the route param passed in. but that feels insane

wilkerlucio03:02:08

usually when you have routes, you are loading from a given route (not send the entire union)

wilkerlucio03:02:23

so you should not need any rounting on that sense on the server

mss03:02:39

yeah this is on the client

wilkerlucio03:02:12

the client route is defined usually by the entity key, so you just need the correct ident there

wilkerlucio03:02:42

what are you trying to make?

wilkerlucio03:02:23

@mss getting late here, have to go to the bed, but let's continue this tomorrow, I would like to understand what is your case

mss03:02:03

absolutely, really appreciate the help

claudiu06:02:39

@mss For your usecase I usually create a defsc with the ident from params and use get-query. As far as I know it's a valid pattern when you need to give the df/load a query that does not match the ui, should work for that usecase also.

tony.kay07:02:24

@mss a query by ident is literal. prop names are not variables. There are query parameters (see set-query!) where you can rewrite the query over time for a component to use a specific thing for part of the query with ?varname, and then use set-query! to set the param :varname to any value.

tony.kay07:02:06

If you’re trying to use a bit of app state for this task, then you don’t want an ident in your query, you want the ident in your state. Any join that is normalized is a graph edge that can point to any entity of the sub-type. Typically what you do is write a simple join, and modify that prop in app state to point to your desired target.

tony.kay07:02:13

Lean less on the query and more on the state

claudiu07:02:46

@tony.kay is it a valid pattern to have a component just for getting stuff from the db (no render or mutations on it) and using the data in the parent ? or am I asking for trouble ?

tony.kay07:02:37

“using data in the parent” is the only part I’d question…

tony.kay07:02:53

why not just treat it as opaque data if there is nothing for a subcomponent to do with it?

tony.kay07:02:06

e.g. don’t normalize it, and just query for it by prop

tony.kay07:02:08

in either case, you’re not really asking for trouble as long as you follow the general composition rules. You could join in a component’s query, use the data, and never call that component to render it.

tony.kay07:02:10

that’s fine

tony.kay07:02:21

stealing a query is a no-no, since that could break normalization

tony.kay07:02:08

but that’s different: (defsc X [t p] {:query (fn [] (prim/get-query Y))}) is a no-no

tony.kay07:02:37

as long as you compose the query with the rules, it’s fine to have a query/ident-only component for server (or client) queries

tony.kay07:02:51

unusual to use it on client, but ok

pithyless17:02:19

@tony.kay @wilkerlucio I’m seeing Bad method signature in protocol implementation, f.network/FulcroRemoteI does not declare method called network-behavior after the newest fulcro SNAPSHOT. Do I have some stale packages?

pithyless17:02:32

[fulcrologic/fulcro "2.3.0-SNAPSHOT"]
  [fulcrologic/fulcro-inspect "2.0.0-alpha6-SNAPSHOT"]

pithyless17:02:01

In fulcro.inspect.core: Use of undeclared Var fulcro.client.network/network-behavior

tony.kay17:02:02

That method has been removed.

tony.kay17:02:00

Wasn't official Api yet, and I have plans to deal with that concern differently in the future

pithyless17:02:18

I’ll just go back to 2.2.0, but FYI 🙂

tony.kay17:02:34

Shouldn't have to

tony.kay17:02:52

Did you clean your build?

tony.kay17:02:40

And inspect had a bump as well to cope with that

pithyless17:02:03

ok, so it was indeed just stale cache; sorry for the noise

rastandy17:02:54

hello everyone, just to notify you about another Fulcro app: https://dataportal.cmcc.it

currentoor18:02:35

@U15D43HU7 did you use a UI library or make everything from scratch?

rastandy18:02:51

some things from scratch and some things from SemanticUI (the react bindings)

currentoor18:02:56

looks pretty good by the way!

currentoor18:02:52

did you use the cljsjs version?

currentoor18:02:09

of SemanticUI

rastandy18:02:44

ups sorry for the delay

rastandy18:02:58

I used this library from tony.kay:

rastandy18:02:41

[fulcrologic/semantic-ui-react-wrappers “1.0.0-alpha1”]

rastandy18:02:54

oh and this, yes, the cljsjs version:

rastandy18:02:02

[cljsjs/semantic-ui-react “0.76.0-0”]

cjmurphy23:02:48

Poor Internet here this morning so it is continuously 'loading'. Is there a GitHub site?

currentoor05:02:47

@U15D43HU7 no worries, thanks for the reply!

rastandy07:02:16

@U0D5RN0S1 unfortunately it’s not public, sorry

rastandy17:02:37

and take the chance to thanks many of you in this channel for the kindness and the great help I received during development

rastandy17:02:51

thank you very much guys

myguidingstar19:02:28

@wilkerlucio I'm wondering if a simple pathom plugin can do this: keyword aliases. Eg: {:person/pet [:db/id :pet/name]} will end up in walkable sql builder as {:person/pet [:pet/id :pet/name]} but the keyword in the result returned to client remain :db/id instead of :pet/id?

myguidingstar20:02:36

btw, the latest source code for walkable is here: https://github.com/walkable-server/walkable

myguidingstar20:02:54

it comes with a handy duct setup to explore walkable features

myguidingstar20:02:16

@wilkerlucio never mind. it's more straightforward than I thought

wilkerlucio20:02:57

@myguidingstar I'm in a meeting right now, but I was going to write you an example

wilkerlucio20:02:02

a reader can solve that I think

wilkerlucio20:02:58

you can look at ::p/path to get the :person/pet while reading :db/id

wilkerlucio20:02:31

how did you solved it?

myguidingstar20:02:09

I manually replace :db/id with :pet/id then rename-keys the sql result

myguidingstar20:02:51

I guess the problem with ::p/path is that :pet/id is not there for :db/id

wilkerlucio20:02:56

I think a reader might be easier, let me write one for you in a bit

wilkerlucio21:02:56

@myguidingstar ok, got it, see what you think about this impl:

wilkerlucio21:02:58

(defn id-convert-reader [{:keys [ast]
                          ::p/keys [path]
                          :as env}]
  (if (= :db/id (:key ast))
    (let [parent-join (-> path rseq second)
          new-key     (keyword (name parent-join) "id")]
      (p/entity-attr! env new-key))
    ::p/continue))

(def parser (p/parser {}))

(parser {::p/reader [id-convert-reader p/map-reader]
         ::p/entity {:person/name "User"
                     :person/pet {:pet/id 123 :pet/name "Rex"}}}
  [{:person/pet [:db/id :pet/name]}])

myguidingstar21:02:33

@wilkerlucio the problem with the above impl is that p/entity-attr! assumes new-key already exists in ::p/entity which is not the case because the sql query buider ignores :db/id (because it thinks that's an invalid keyword)

wilkerlucio21:02:26

the p/entity-attr! does another query for that attribute, so if you have a reader that can parse it, it should work

myguidingstar22:02:08

I was expecting a kind of alias plugin that works seemlessly so the next plugin in the plugin chain don't need to be aware of any aliases at all

myguidingstar22:02:27

in the case of walkable sql, it should never have to deal with :db/id

wilkerlucio22:02:44

@myguidingstar doesn't the reader serve as the same? a reader is pretty much like a read plugin, the read plugin just have more override and can wrp

wilkerlucio22:02:09

but on this case, you could use it only once, at get the benefits for anything (it looks at the parent path, so it should always be "correct")

wilkerlucio22:02:57

with that said, could you explain why are you doing the translation? I would like to understand better what is your intention, because usually I would recommend don't, the power on the keywords is because they work "as is", renaming then can generate confusion IMO