Fork me on GitHub
#fulcro
<
2018-02-22
>
donmullen13:02:19

@claudiu Yep! That was it. Thanks. I am still at a point where I struggle to debug when things aren’t quite wired up correctly.

claudiu14:02:24

you're welcome, glad to help 🙂

donmullen16:02:35

I’ve been able to replicate this dx-react-grid code (https://github.com/oliversturm/demo-dx-react-grid-clojurescript/blob/master/src/demo-dx-react-grid-clojurescript/core.cljs) and trying to extend to track row selection with <Table rowComponent={TableRow}/> from the example at the bottom here: https://devexpress.github.io/devextreme-reactive/react/grid/docs/guides/fundamentals/. Still ramping up on React.js and not sure how to translate this code

const TableRow = ({ row, ...restProps }) => (
<Table.Row
{...restProps}
// eslint-disable-next-line no-alert
onClick={() => alert(JSON.stringify(row))}
style={{
cursor: 'pointer',
...styles[row.sector.toLowerCase()],
}}
/>
);
to fulcro. Thoughts?

justinlee16:02:44

I gave you some thoughts in #reagent

tony.kay16:02:49

@donmullen The developer’s guide talks about dealing with factories…and so I would use the factory-apply thing to make something that can render Table.Row with regular props. Then I’d create a function that takes your desired argument list and put it together. See http://book.fulcrologic.com/#_factory_functions_for_js_react_components The only tough part for that example is the ... notation, since that is basically merging existing props into a list. If you write a cljs function that takes regular cljs data, then you can use merge, and then clj->js to send the final things.

tony.kay16:02:20

If you’re wanting a vanilla js react component to consume that function, then you’ll have to accept js object at params instead (as is the case here). So, just use something like goog.object’s set to take what you’re passed, add things to it, then use that as your props.

donmullen17:02:12

Thanks @tony.kay - I’m a bit in over my head - but may be able to figure things out based on what you have said above. And thanks @lee.justin.m - got me one step further!

justinlee16:02:38

is fulcro reagent based? i gave some advice in #reagent because i thought don was using reagent but now i’m wondering if that advice won’t make sense

tony.kay16:02:59

no, it is not

tony.kay16:02:24

it’s an evolution of Om Next

justinlee16:02:14

well i never understand how the component-level binding works there either 🙂

tony.kay17:02:06

All sablano is doing is a call to js React factory stuff with the class. That’s all the wrapper in the book does…it just gives you a function to call instead of some special data structure notation.

tony.kay17:02:07

It looks like, from your example, that the react component is sending you an array of args…like it is varargs. That is (defn f [row & restProps] ...)

justinlee17:02:09

i think gen-table-row will receive a JS map, not a CLJS map. i think you need to convert to CLJS before trying to destructure

tony.kay17:02:15

but then restProps in cljs will be a cljs vector, not a js array

tony.kay17:02:36

and that is true, too. Destructuring isn’t going to work

tony.kay17:02:38

Oh, I see…I misread the js example…I missed that it was destructuring

tony.kay17:02:49

I don’t write any js these days, so I don’t read it well 😜

tony.kay17:02:47

you have to manually destructure that with gobj/get or convert it to cljs first. I would do the former, because you’re just going to need the latter

tony.kay17:02:06

so, pretend like “spread” syntax in js doesn’t exist…you have to write it like that

wilkerlucio17:02:14

you can use into-array to convert a cljs list into a JS array

wilkerlucio17:02:28

if you need to spread, use .apply

tony.kay17:02:40

the incoming thing is a map with “rest” notation

tony.kay17:02:56

first thing he has to do is get the correct stuff out

tony.kay17:02:50

destructuring won’t work because it is a js map. Could use js->clj The main thing to realize is that all destructuring notations for cljs won’t work on raw js objects…that’s the main problem

justinlee17:02:34

(by the way, when I have cljs code that is marooned in a javascript callback (like gen-table-row), I like to use camel case as a matter of style (i.e. I would name it genTableRow) because it can be super confusing to keep track of what’s going on otherwise.)

tony.kay17:02:41

(defn gen-table-row [js-props]
   (gobj/set js-props "onClick" (fn ...))
   (gobj/set js-props "style" #js { ... })
   (ui-table-row js-props))

tony.kay17:02:17

agreed with @lee.justin.m on naming for confusion avoidance

Drew Verlee18:02:09

I’m i correct in understanding that defining the idents and queries actual creates the graph db schema? Or I mis understanding the first 12 minutes or so of this https://www.youtube.com/watch?v=mT4jJHf929Q&amp;t=6s&amp;list=WL&amp;index=1?

wilkerlucio18:02:34

@drewverlee what you mean by db schema on this context?

tony.kay18:02:02

So, not so much “schema” in the traditional sense. the queries and idents define the normalization (which is related to schema)

tony.kay18:02:44

schema is usually reserved for cases where you talk about more of the explicit data constraints, like field types

tony.kay18:02:42

An ident says “put instances of this in such-and-such a table, using some column as the index”

tony.kay18:02:47

that is certainly like schema

tony.kay18:02:06

CREATE TABLE person (id serial primary key ...)

tony.kay18:02:10

The query spells out relations, and what properties the component currently “wants”. There is no limit to the props that can exist in an entity in the graph. So, in that sense the schema for props is otherwise completely open

tony.kay18:02:47

including relational (to-one or to-many) joins that you have “failed” to mention because the component in question doesn’t need them (or they don’t exist)

tony.kay18:02:33

So, the schema analogy should not be taken past the ident…what table and what is the ID column. The table name has to be a keyword, and the ID can be anything that can be compared.

tony.kay18:02:35

One way of looking at it is this: 1. You invent some relational tree structure for your UI. Parts of that can mimic (in query form) structure in some data store. 2. You want to run a query, using part of your UI tree structure, to ask the data store for that data (nothing more or less, so it isn’t over-querying). 3. When you get that tree, you want it to be normalized, because that enables easy refactoring, mutations that don’t care about tree structure (don’t need modified when you change the tree), and re-use of the data in disparate parts of the UI 4. When you’ve got normalized data, you also need the query to turn it back into a tree of props, because that is what React needs.

tony.kay18:02:40

Nothing prevents your data store from having more than you asked for, and nothing prevents your server query handling code from transforming data into a form that makes more sense for the UI.

tony.kay18:02:27

in fact, a lot of the other code in the library helps enable that, and it’s what pathom library is about: how to convert a graph query into a data store access (whether that be an SQL database, GraphQL, or a call to a REST endpoint)

tony.kay18:02:53

The more your UI query happens to coincide with server data structure, the easier it is…but there is no requirement for them to have any relationship to each other at all as long as there is some function that can convert between the two.

Drew Verlee18:02:15

I think I understand, for a moment I thought the idea was the quries and indents actually setup the graph database. Like the UI asking "I need a person" would create a person structure in the presitant layer

donmullen18:02:01

@tony.kay @lee.justin.m - getting closer! Unclear why the gobj/set isn’t working.

wilkerlucio19:02:03

@donmullen I see you have gobj/add, not sure what that does, but I think you should be using set there too

wilkerlucio19:02:21

just looked up on the docs, add is supposed to receive a js map, as: (gobj/add js-props #js {:onClick "bla"})

donmullen19:02:23

@wilkerlucio - add throws an exception when there is already a value. I wanted to confirm it was trying to set it - and it does throw on style - which is there but undefined.

wilkerlucio19:02:42

sorry, I read wrong, you are right

wilkerlucio19:02:43

so on the logs you see the object without the items you added just on the lives above it?

wilkerlucio19:02:44

weird, but one thing to consider, those as js mutable things

wilkerlucio19:02:02

so, something else might be changing those objects after you log then

wilkerlucio19:02:19

can you try the same example without calling the ui-table-row and see if that changes the results?

donmullen19:02:19

Good call. This is in the broader context of a callback from dx-react-grid putting a row in the grid table. I’ve confirmed that it successfully calls - but perhaps something else is going on with the integration with their react components.

tony.kay19:02:27

one thread…nothing could have the chance to change them

donmullen19:02:28

Unclear then what’s happening, though. Was thinking of taking a look at https://github.com/binaryage/cljs-oops — but seems the gobj/set should be working here.