Fork me on GitHub
#figwheel-main
<
2018-09-06
>
pesterhazy10:09:57

@bhauman can confirm that 0.2.6 works well with React's global exports

bhauman10:09:21

good to hear 🙂

onetom10:09:43

so is this the recommended way to interface with external libraries? just let them export whatever globals they export in their browser builds and let the closure compiler know about those globals via compiler options?

onetom10:09:47

as opposed to using common js or es6 convention and let the compiler interface with them as if they were google closure modules?

pesterhazy11:09:40

@onetom yes that's my understanding, at least of interfacing with webpack: https://clojurescript.org/guides/webpack

pesterhazy11:09:15

or for example firebase:

pesterhazy11:09:17

so you can use the same method of getting at the js library in the code, regardless of whether you go through cljsjs, webpack/doublebundle or (I think) npm-deps

onetom11:09:15

when i was doing a pure es6 project (without using a bundler), that was the approach i settled on too, but it was a pain to manage manually...

onetom11:09:40

can dead code elimination still be done when using this :global-exports approach?

onetom11:09:53

i don't really see the benefit of the whole es6 module system... i have the impression that we would have been a lot better off if everyone would have just adopted the google module system even if they were not using the closure compiler.

onetom11:09:29

since that's just a library... wouldn't require explicit language support

bhauman11:09:02

@onetom I’m inclined to agree here

bhauman11:09:36

I think they went to far down the encapsulation road

bhauman11:09:13

but no dead code elimination doesn’t apply to global-exports

bhauman11:09:39

I think the JS community was really deeply affected by the book JavaScript The Good Parts and they took it too far

1
bhauman11:09:17

just the way the Java Community was deeply affected by the Gang of Four patterns book

dottedmag11:09:42

Javascript is all-mutable, so encapsulation in it is necessary for sanity.

bhauman11:09:14

and I understand the motivation, but the trade offs were not considered

bhauman11:09:18

hot reloading

bhauman11:09:26

global optimization

bhauman11:09:43

are pretty much screwed

bhauman11:09:58

because of how it was done

dottedmag11:09:24

If one's house is on fire, they don't care much about not trampling on flowers. ¯\(ツ)

dottedmag11:09:13

IIRC it was possible to implement ES6 modules by converting them to goog modules?

bhauman11:09:16

and again I’d say that JS was a victim of a narrow focus, the way that java was

bhauman11:09:30

I seem to remember hearing something about that as well, but I’m not so sure because ES6 modules can still close over an initial state correct?

bhauman11:09:54

I’m really in no position to be talking authoritatively about this

bhauman11:09:10

I do respect Clojures design decisions though

bhauman11:09:20

vars are mutable and global

dottedmag11:09:21

One can do (function(){})() anywhere in JS, yes. Too bad.

bhauman11:09:07

and we get a great freaking workflow because of the design of Clojures namespaces

onetom12:09:36

So how can we include react now, so it can be dead code eliminated?

bhauman12:09:56

:npm-deps is supposed to provide that

bhauman12:09:16

but its unreliable

bhauman12:09:32

I think it works for react

onetom12:09:49

What makes it unreliable?

bhauman12:09:49

but that could change with the next release of react

bhauman12:09:27

its doesn’t work for the universe npm modules

bhauman12:09:46

many are incompatible with the Google Closure compiler

bhauman12:09:07

we are waiting on improvements

onetom12:09:32

Sounds like a step back for React if it can't be included via the npm-deps support... :/

bhauman12:09:33

so its basically give it a try for your dependencies and see if it works, if not use a webpack bundle

bhauman12:09:29

its a step back to the status quo in the JavaScript world

bhauman12:09:51

which is pretty OK

bhauman12:09:32

if you really need to have the tiniest footprint possible, you can engineer it, but its hardly worth it if you are simply deploying an average webapp

bhauman12:09:08

for example https://mithril.js.org/ is freaking tiny

bhauman12:09:19

but you don’t get the ecosystem and momentum around react

onetom12:09:27

Because we let these tiny little decisions (about module formats for example) accepted as the norm and as a consequence everyone is forced to pay huge complexity tax...

bhauman12:09:44

oh I totally get that

bhauman12:09:58

but trade offs

pesterhazy12:09:10

the gains from accessing the react ecosystem are huge

bhauman12:09:26

I can use a library with 10000 hrs of dev behind it

bhauman12:09:36

in exchange for?

bhauman12:09:10

not being able to DCE it

👍 1
onetom12:09:24

And the effort for them to keep distributing a module format which is compatible with the closure compiler is tiny... And it's a fact, because they were doing it until now

pesterhazy12:09:02

trouble is, you can't make other people do things the way you like them to do

onetom12:09:07

I don't think that's how the equation looks like though

pesterhazy12:09:44

the reasonable expectation of a lib consumer is it works with webpack and rollup, not that it works with GCC

onetom12:09:05

It's more like: because react is being packaged in a non-DCE compliant way, all the other library maintainers will follow suit and nothing will be DCEable.

bhauman12:09:56

I wouldn’t say React is the leader here, I think its a follower

onetom12:09:17

Except your own app, but that probably doesn't have a lot of eliminateable parts, which will turn the whole compilation process less worthy

bhauman12:09:52

I hear you and I agree, in the sense that I wish it was otherwise

bhauman12:09:04

but the JS world has chosen their direction and they chose it years ago

bhauman12:09:43

no one cares about GCC

bhauman12:09:50

not one little iota

bhauman12:09:05

which sucks

onetom12:09:08

And their insanity is slowly spreads to other ecosystems too...

bhauman12:09:35

yeah but they don’t know they are insane, and well …

onetom12:09:51

I have the feeling that it can seriously undermine Clojurescript adoption too actually

onetom12:09:30

Human history has terrifying examples of what happens when no one steps up and objects...

bhauman12:09:37

and folks predicted that when ClojureScript was launched and the choice to use GCC was announced

bhauman12:09:21

From my point of view, I’ve accepted that few folks even understand the trade offs that were made and what was lost

bhauman12:09:57

But I think I dissagree that this is a recent change that turned against DCE, its just that no one ever cared.

bhauman12:09:34

the GCC has been playing catch up with the node module eco-system to try and compile it

bhauman12:09:33

if you go back over the versions of react and the GCC sometimes they catch up and can compile it, then they can’t, and then they can again

bhauman12:09:13

but even when they can the optimizations that can be done are limited compared to what can be done with the object literal libs that Closure uses

onetom12:09:47

Object literal libs?

bhauman12:09:13

{add: function(a,b) {return a +b;}}

bhauman12:09:41

the closure modules are just simple JS objects

bhauman12:09:17

so its much easier to trace usage and eliminate things that are not used

bhauman12:09:21

super hard to eliminate things that have been closed over

bhauman12:09:40

@onetom I’ve been super tempted to create yet another virtual dom library but in either CLJS or Google Closure compatible code.

onetom13:09:00

I'm even more tempted to create something which doesn't even need a virtual dom :)

onetom13:09:15

So what happened to your temptation then?

bhauman13:09:22

I maintain a lot of OS libs

bhauman13:09:58

but I really think someone could take mithril and tailor it to CLJS and get something super quick and tiny

bhauman13:09:14

mithril is so quick you hardly have to think about optimization

onetom13:09:57

The first time I tried it, it couldn't maintain the cursor position in an input field when I was trying to edit the middle of the text it held, so I declared it immature and potentially fundamentally flawed

bhauman13:09:34

oh and this may be so

bhauman13:09:55

I could just be dreaming

bhauman13:09:19

or projecting a simple solution where there really isn’t one

onetom13:09:27

Hoplon/UI had this issue and the fix to it was a simple "if el.value changed, then set it to the onchange event's value"

bhauman13:09:21

you have to register on change events in React as well depending on the type of rendering that you are doing

bhauman13:09:35

for form fields I mean

bhauman13:09:56

anyway I think I had way too much caffeine this morning

bhauman13:09:14

need to go get more to avoid the crash

orestis13:09:00

Thanks for figwheel and everything!

orestis13:09:34

I am looking for some pointers on how to integrate my own web server with figwheel-main to server an API without messing with CORS etc.

orestis13:09:57

(And also to use the same configuration for production deployments)

orestis13:09:59

I’ve found https://github.com/bhauman/lein-figwheel/tree/master/examples/separate-server but I’m not sure how does it relate to figwheel-main?

bhauman13:09:29

@orestis you can create any kind of server you want

bhauman13:09:35

and things will work

bhauman13:09:58

you just have to ensure that you are serving the compiled clojurescript assets from your new server

bhauman13:09:10

there will be no cors problems

bhauman13:09:37

most people stumble here because they assume that have to do something funky to make this work

bhauman13:09:16

you just have to serve the assets like you would with any other server that you would deploy

orestis13:09:13

So I just serve my index.html and all its references --- but how then do I get the websocket connection to the figwheel server?

orestis13:09:35

How do I even start the figwheel server?

orestis13:09:03

Context: so far I’m just doing clojure -m figwheel.main --build myapp --repl

bhauman13:09:19

and that’s how you would start it

bhauman13:09:44

there are many ways to start a separate server

orestis13:09:45

So the websocket connection and everything is built into my compiled assets?

orestis13:09:32

Right, so presumably for production I’d have to compile CLJS using some other flag to remove traces of figwheel.

bhauman13:09:04

--build-once

orestis13:09:15

I guess the simplest way would be to run 2 JVMs, one for figwheel, one for my server (then I’d get two separate very clear-cut REPLs too)

bhauman13:09:22

or -O advanced

bhauman13:09:35

yes you can do that

bhauman13:09:42

if you want it in the same process

bhauman13:09:05

you can add a start-server function to your user.clj file

bhauman13:09:30

and add -e “(user/start-server)” before -m figwheel.main

orestis13:09:14

Ooh fancy 🙂 figwheel-main is my first exposure for using deps.edn too, I have to read up on the available tricks 😉

bhauman13:09:12

you can also just start a rebel-readline repl

bhauman13:09:34

to start figwheel

orestis13:09:41

I’ll do a POC on two separate JVMs. Would adding a note to the docs about this use case make sense? I also struggled a little bit to get Reagent to work with the hooks, Googling didn’t produce anything obvious. I can try my hand at writing something and submitting a PR?

bhauman13:09:45

after you start your server

orestis13:09:47

(I got Reagent working as expected now)

bhauman13:09:24

@orestis I would try using a single process, because then you will get hot reloading of your clj files if they are being watched

bhauman13:09:36

its a pretty sweet setup

bhauman13:09:50

hot-reloading with syntax error feedback in the heads up

orestis13:09:52

Oh, I don’t want that - I usually evaluate directly in Emacs — but it’s worth exploring.

bhauman13:09:15

just wanted to mention it

orestis13:09:38

Sure! I’ll give it a go for other members of our team that might find it more useful.

bhauman13:09:39

as far as docs are concerned the Reagent doc sounds good

orestis13:09:46

Have I said thanks? Thanks again 🙂

bhauman13:09:20

if its not much documentation then perhaps add it to the https://figwheel.org/docs/hot_reloading.html doc

bhauman13:09:31

@orestis you’re welcome 🙂

bhauman14:09:16

@orestis is run a reagent fn?

bhauman14:09:18

oh I think you meant run to be mount is that correct?

orestis14:09:58

Oh yeah I renamed that last-minute to be more clear 🙂