Fork me on GitHub
#clojurescript
<
2015-07-23
>
colin.yates09:07:55

@mattly, this might be a co-incidence but I find things went smoother when the src-cljc were listed before the src-clj and src-cljs. Is this lein or boot?

Pablo Fernandez10:07:59

Is using a multimethod a good way to dispatch from URLs/silk to views like the one expressed here: https://github.com/metosin/ks-front-routing-example/tree/master/src/clj/ks_front_routing/ui (@domkm is that how you’d do it?)

ul10:07:12

I'm using that style of dispatch with bidi.

ul10:07:30

Bonus is that you can provide custom hierarchy to defmulti

ul10:07:42

And dispatch generic views for the whole sections

Pablo Fernandez10:07:53

@ul: custom hierarchy? what do you mean?

domkm10:07:02

@pupeno: Sure, that's a reasonable way if you want to extend dispatch from multiple namespaces.

Pablo Fernandez10:07:47

@domkm: does it fix the problem of reloading code not being used

domkm10:07:22

@pupeno: Could you clarify what problem you are referring to?

domkm11:07:16

@pupeno: My personal preference is to locate that sub-component routing logic within the parent component and pass route params down the render tree. For example, the top level component would have a cond that checks the route params and chooses the correct sub-view based on that.

ul11:07:19

(def routing-table ["/" {"section1/" {"page1" :handler1 ...} ...}])
(def route-hierarchy (-> (make-hierarchy) (derive :handler1 :section1) ...))
(defmulti View (fn [db] (:route db)) :hierarchy #'route-hierarchy)
(defmethod View :default ...) ; any page without specific view
(defmethod View :section1 ...) ; any page of section1 w/o specific view
(defmethod View :handler1 ...) ; view is specific for handler1

domkm11:07:57

@pupeno: I don't really understand the reasoning for that use of var in Luminus. If that namespace is reloaded then the current function would be used regardless of whether pages refers to vars or symbols. Also, cljs vars do not exist at runtime, right?

domkm11:07:36

@pupeno I do front-end reloading with Leaven (https://github.com/palletops/leaven). I just restart the system whenever a file is saved. It works very well as long as all state is kept within components.

Pablo Fernandez11:07:32

@domkm: @yogthos said that the problem was when the functions are distributed across namespaces, I didn’t try it myself.

Pablo Fernandez11:07:40

I use figwheel to reload my code

domkm11:07:15

@pupeno: Understood when they are used in a different namespace than where they are defined but in that example they are defined and used in the same namespace.

Pablo Fernandez11:07:03

Yes, the template is just designed to a have a good style to follow for bigger applications. I was wondering if the multi-method way, by its very nature, doesn’t require the vars.

domkm11:07:03

@pupeno: I think multimethods would suffer from some of the same issues but I'm not sure. Locating dispatch logic within components totally solves the reloading issue so I would suggest that. It's also what @jrychter was suggesting recently.

cfleming11:07:50

@mfikes: Oooh, Cognicast - I’ll have to check that out.

mfikes11:07:05

@cfleming: Maybe it will convince you to try some stuff on your iOS device. :)

cfleming11:07:24

@mfikes: I’m already convinced, all I need is time simple_smile

Pablo Fernandez11:07:54

@domkm: I added a Silk example to Pushy’s README: https://github.com/kibu-australia/pushy/compare/master...pupeno:patch-1 I’m not 100% sure it’s correct and idiomatic though.

domkm12:07:10

@pupeno: Great, thanks! It looks fine to me but I'm not familiar with Pushy. :)

akiel13:07:23

is there dynamic scope in cljs?

mfikes13:07:19

@akiel: dynamic vars work as they do in Clojure

akiel13:07:51

@mfikes: than I'm doing something wrong - I'll check again

mfikes13:07:19

@akiel Are you using binding?

akiel13:07:01

@mfikes: sorry my fault - dynamic scope is working - its another problem

mfikes13:07:23

@akiel: No problem. (Yeah, that bit of code looked correct.)

mhuebert13:07:10

Does anyone know how to control the order of javascript dependencies as provided via deps.cljs in another cljs project? it doesn’t seem to matter what order one lists them in (:require…), nor what order they are listed in deps.cljs. eg/ https://gist.github.com/mhuebert/3f6a9f4483ccdfccf318

maria14:07:30

>>> :requires (Optional) A vector explicitly identifying dependencies (:provides values from other foreign libs); used to form a topological sort honoring dependencies.

mhuebert14:07:55

@maria I haven’t. I can’t say I understand what I would put in the :file option there; it seems to want a URL. I’m trying to use JS files that are in another cljs project (say, my-codemirror-wrapper)

mhuebert14:07:26

@maria my understanding is that I can use deps.cljs to specify files & associated synthetic namespaces that should be made available to whatever project requires my lib; then, as with cljsjs, to consume those provided namespaces one wouldn’t use :foreign-libs at all. but maybe I am missing something

maria14:07:10

@mhuebert: sorry, I think I misunderstood your questions. I thought you would be able to change the options in deps.cljs.

martinklepsch14:07:06

@mhuebert: you can only use deps.cljs if you’re planning to make a jar with your js and externs files — is that what you’re intending to do?

mhuebert14:07:35

@maria oh… I am in control of both repo’s (I have a CodeMirror wrapper that I am using in multiple projects) so yes I can modify the deps.cljs.

martinklepsch14:07:38

@mhuebert: if not you need to pass the things to the compiler directly as :foreign-libs

martinklepsch14:07:15

@mhuebert: also there’s a codemirror package in cljsjs but you probably know that simple_smile

mhuebert14:07:02

@maria I was confused & thought you meant compiler options of the project I am importing to

mhuebert14:07:34

@martinklepsch: yes simple_smile. I’m working on some custom modes & things which I want to package together

maria14:07:58

@mhuebert: then I would try to modify your deps.cljs and add the :requires options as described here: https://github.com/clojure/clojurescript/wiki/Packaging-Foreign-Dependencies

mhuebert14:07:51

@maria perfect, thank you!

timothypratley14:07:38

I have a weird compiler issue: Complex project, compiles release builds in 3min I make some minor changes, and it takes over 20min Likely that the javascript being processed by google closure is ‘hard’ for it? [optimizations :none is fine] Is there any way I can diagnose this further?

robert-stuttaford14:07:34

have you switched all the debug flags on and inspected their output, timothypratley ?

robert-stuttaford14:07:11

@dnolen might be able to help with where to look

timothypratley15:07:57

I did use :verbose, but haven’t tried :cache-analysis, will give it a shot, thanks simple_smile

timothypratley15:07:16

:cache-analysis doesn’t help, I think the reason is that is the JS being compiled by closure that is taking all the time, not the clojurescript part.

timothypratley15:07:49

(cache-analysis only affected the clojurescript compilation part)

timothypratley15:07:54

'Applying optimizations :advanced’ is where all the time is spent

timothypratley15:07:58

maybe I should be searching for the answer in google closure world, any suggestions on how to do that?

timothypratley15:07:34

thanks, will do simple_smile

dnolen15:07:57

@timothypratley: did you try :recompile-dependents false first

dnolen15:07:06

Closure isn't used under :none

timothypratley15:07:42

Ah, I didn’t try it, because the problem isn’t in the clojurescript compile time part… but will try it now

timothypratley15:07:51

yeah, same deal. I don’t think any of the clojurescript flags will affect the JS or time closure takes to ‘optimize’ it. note that even :whitespace optimization is taking exhibiting the behavior… so in some sense it is not a clojurescript problem at all, except I suspect the JS that is being produced is somehow hard for closure to process.

dnolen16:07:08

:recompile-dependents affects all settings

dnolen16:07:00

And there's a known poly time bug in it

timothypratley16:07:40

gotcha. I think my problem is different, setting the flag didn’t affect it.

dnolen16:07:57

@timothypratley: the other thing how much RAM are you giving the JVM?

wildermuthn16:07:00

Long question: I often find the need to inspect certain values that are used within let or go. Usually I’ll stick a log in there, or I’ll set a symbol to its value and then get that symbol at the repl. Often this means I have to switch from namespace to namespace, which isn’t necessarily that easy with overly long namespaces. Basically, I’m looking for a way to easily grab a value to play around with in the repl, without having to switch namespaces. I’d considered (set! js/window.xyz) and then window.xyz would work in any namespace. But it occurred to me that the same would work just as well interning a symbol in cljs.core. I’m not sure how to do that except through the repl itself, however, as I believe interning isn’t available in Clojurescript. Is there a way to expand the symbols in cljs.core from another file? Or is there a better solution to debugging let values via the repl without having to switch namespaces?

noisesmith16:07:20

wildermuthn: I like to put values into an atom with swap! / conj, but with eg. the chrome inspector you can also set a breakpoint inside the let body and look at the locals

timothypratley16:07:32

hmmm I don’t have any settings currently, will try throwing some in

noisesmith16:07:57

yeah, I find an atom works great for that

noisesmith16:07:22

I add a swap! call into the function body, and if the value is immutable I can then access the atom from the repl safely

wildermuthn16:07:25

@noisesmith: sorry, misread what you said. Is the atom namespaced?

noisesmith16:07:33

all atoms are namespaced

wildermuthn16:07:42

Right, so I’m looking for a way to do this without having to switch namespaces

noisesmith16:07:46

but you can use require or even use to conveniently access another namespace

noisesmith16:07:07

(require '[some.other.unweildy.ns :as uw])

noisesmith16:07:10

you can do that in the repl

noisesmith16:07:21

then access @uw/some-atom

wildermuthn16:07:53

Ultimately, I’d like to intern these in cljs.core so I could use them throughout my app.

noisesmith16:07:18

oh, not for debugging but for accessing the values? I think that indicates a design problem

wildermuthn16:07:21

I could just set them in the repl everytime I loaded up, but wondering if there’s a programmatic way to do it, or if there’s just a better solution overall.

noisesmith16:07:51

putting things into cljs.core is a bad idea

wildermuthn16:07:09

No, for debugging. Often I’ll have a value that then gets processed further within the let. I’ll usually want that value to work out what’s happening in further functions down the line.

noisesmith16:07:38

is it really so onerous to use require while debugging?

noisesmith16:07:55

or even in-ns

wildermuthn16:07:57

I need shorter namespaces. But I’ll often switch back and forth between namespaces, and without repl tab complete (vim + figwheel), it does get onerous.

timothypratley16:07:04

:jvm-opts ["-Xms2g" "-Xmx2g”] <— same behavior

wildermuthn16:07:47

Basically, I want non-namespaced symbols for debugging.

noisesmith16:07:16

wildermuthn: you could put an atom into js/window

noisesmith16:07:31

then it's easy to get at it from anywhere right?

noisesmith16:07:56

using swap! / reset! / deref as apropriate

wildermuthn16:07:16

@noisesmith: Yeah, I added a snippet above with a macro that does that. But then I still have to reference those macros in each namespace where I’ using them 😉

timothypratley16:07:19

java -Xmx2g -Xms2g -jar ~/Downloads/compiler-latest/compiler.jar --js target/cljsbuild-compiler-0/**.js <— also takes a really long time.

noisesmith16:07:47

wildermuthn: that's not using atoms, I think you'll find with atoms it's simpler and doesn't require macros

noisesmith16:07:03

wildermuthn: my preference is to have (atom []), then use swap! to conj things on. Then I can peek to see the latest, but also access the history of values

dnolen16:07:58

@timothypratley: huh, in past there were some JS parsing edge cases that would cause problems. specifically large data literals, but that had since gotten fixed.

dnolen16:07:18

@timothypratley: the only other thing I can think of is make sure you’re getting the right version of Closure Compiler.

timothypratley16:07:51

hmm, the version I downloaded from the web was the latest version, just downloaded now shrug. I’m working with a colleague to get a smaller repro, we now know the code conditions that cause it.

wildermuthn17:07:33

I did add those macros to cljs.core, but if there’s anyway to inject those macros I’d love to be pointed in the right direction.

wildermuthn17:07:08

But I have to say, doing this in Javascript would have required going into V8 and writing C++? Pretty cool.

timothypratley17:07:59

@dnolen: we found the minimum repro

[:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a [:a]]]]]]]]]]]]]]]]]]]]]]
take 50 seconds in “Applying optimizations” (google closure) this is as you suspected, a nested data literal (every step takes about 2x time)

timothypratley17:07:04

this is with a brand new repo created with lein new mies nested

timothypratley17:07:50

while 22 is quite a bit of nesting, we actually encounter this in a page that we render with nested divs etc, and it all looks pretty reasonable (I mean we aren’t being frivolous with our divs)

mfikes17:07:23

ClojureScript / React Native on front page of HN now simple_smile

timothypratley17:07:49

(just to clarify, we don’t have 22 divs nested, the ‘width’ of the nested items affects compilation time as well)

chancerussell17:07:47

@wildermuthn What you want is analogous to having a "dev profile" for dependencies, except for interned vars, right?

chancerussell17:07:01

So you have certain tools available no matter what ns you're in

wildermuthn17:07:36

Or maybe the reverse? I want to include those interned vars.

chancerussell17:07:37

Without clogging up your actual requires

chancerussell17:07:12

Let me know if you get a good solution!

timothypratley17:07:18

https://github.com/google/closure-compiler/commit/dfaad5f5b0780695d5f96b5596218479882cd44e <— seems relevant, in theory the build has this but I’m trying to figure out a way to confirm.

chancerussell17:07:32

@wildermuthn: I wonder if there'd be anything relevant in clojure.tools.namespace?

chancerussell17:07:14

Hacking something to load a namespace while injecting your "dev namespace" into its requires may be more trouble than it's worth though

wildermuthn17:07:43

@chancerussell: yeah. I’d love to dig in deeper to how namespaces work, but in compilation and at runtime. For now I just threw in two macros in .m2/etc

timothypratley20:07:28

@dnolen: https://github.com/google/closure-compiler/issues/1049 <— my colleague found the closure simplest repro, and opened a ticket there

timothypratley20:07:45

note it is slightly different from nested literals in that in involves functions

dnolen20:07:45

@timothypratley: good catch, awesome that you tracked it down!