This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2019-08-05
Channels
- # announcements (3)
- # beginners (225)
- # calva (3)
- # cider (110)
- # circleci (18)
- # clj-kondo (15)
- # cljdoc (1)
- # cljsrn (12)
- # clojure (77)
- # clojure-dev (39)
- # clojure-europe (3)
- # clojure-houston (2)
- # clojure-italy (9)
- # clojure-nl (16)
- # clojure-romania (1)
- # clojure-spec (5)
- # clojure-uk (20)
- # clojuredesign-podcast (28)
- # clojurescript (89)
- # core-async (4)
- # cursive (10)
- # datomic (3)
- # defnpodcast (5)
- # emacs (17)
- # events (1)
- # figwheel (4)
- # graalvm (6)
- # juxt (1)
- # pathom (4)
- # pedestal (5)
- # re-frame (4)
- # remote-jobs (3)
- # rewrite-clj (4)
- # shadow-cljs (90)
- # spacemacs (2)
- # sql (7)
- # tools-deps (4)
- # vim (52)
- # xtdb (7)
(I’ve seen the term synthetic used for the arbitrary namespaces bestowed to foreign libs.)
Rich used the adjective magic when he introduced it https://github.com/clojure/clojurescript/commit/954e8529b1ec814f40af77d6035f90e93a9126ea#diff-a9cce52f0bf5a7b9afccbec54e4a0e4bR39
Perhaps another good variant might be intrinsic namespace, given the special handling given to them by the compiler.
I'm trying to add a js dependency (https://github.com/lipis/flag-icon-css), I installed it via yarn and required it like this ["flag-icons-css" :as flag]
, but I'm getting an error "module without entry or suffix flag-icons-css"
@shin no, they cannot be included as part of a CLJS build. need to use some other tools to build CSS (eg. node-sass)
@thheller hmm, seems complicated, I was just looking for a quick way to include country flags
I'm trying to translate javascript code to clojurescript, which with a property value of the Object is a anonymous function. What should I do? For example:
var Navigator = {
options: ({tintColor, focused}) => {
<Bar
tintColor={tintColor}
focused={focused}
/>
}
}
The code used a library "react navigation", and the parameters tintColor
and focused
is immutable in thier name.@180338742 JS objects cannot be destructured like this so you'd do (fn [^js obj] (use (.-tintColor obj) (.-focused obj))
or use libs like https://github.com/appliedsciencestudio/js-interop https://github.com/mfikes/cljs-bean
Hello, everyone! Can any one explain the ^js
meaning or giving me some links to learn it?
^js
is a typehint telling the compiler that the object is a JS object and instructing the compiler to generate externs and prevents the renaming in :advanced
builds. see https://clojurescript.org/guides/externs#externs-inference
Has anyone else noticed an unusual amount of "aw snap"s when developing using chrome/chromium 76? Perhaps particularly under (Debian) Linux? I'm working on a re-frame cljs portion of a rather large js web app, and I was hitting "aw snaps" a lot this morning after upgrading chromium (73->76) on Friday. It's not been the only trigger, but the shadow-cljs hot-reloading seemed to cause "aw snap" moments quite often. I've had to downgrade back to version 73 to get any work done. 😕
@mel.collins some people have reported crashes like that in projects with an excessive amount of files (thousands ...). this seems to help to address that https://clojureverse.org/t/improving-initial-load-time-for-browser-builds-during-development/2518
@thheller To throw in another curveball, is that also applicable to :target :npm-module
projects?
but if you process the code further via say webpack that already does pretty much the same
Welp, apparently it hits some kind of "illegal instruction" within Chromium's v8 JS compiler. Reproduction is a real pain though - could happen on first load, could only occur after 30 minutes of interactions and hot-reloading. 😕
Has anyone else run into this difference between clj and cljs?
;; CLJ
(re-seq #"^[a-f]" "aabcded") ;; => ("a")
;; CLJS
(re-seq #"^[a-f]" "aabcded") ;; => ("a" "a" "b" "c" "d" "e" "d")
the cljs solution is recursive, which means it ends up running #"^[a-f]"
against e.g. "ded"
which matches.
Seems like a cljs bug to me.
@U06B8J0AJ, @U04VDQDDY; I think it shouldn’t be like that.
always remember that regexes are host specific. so it might just be how JS handles regexes differently than the JVM
clojurescript is not correctly checking the lastIndex property of the regex before deciding whether to recurse or not. If it is zero then it should not recurse, as there's no more matches.
References: https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/exec https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/RegExp/lastIndex
I would answer, and provide a working re-seq implementation, but I'm not sure whether that should be left for someone else to open a jira to match it in? I guess I can try and let the downvotes decide.
I think there’s jira for that, but it’s on hold since might break existing users
if you tried to do something like:
(let [re #"."]
[(take 1 (re-seq re "foo")) (take 1 (re-seq re "bar"))])
You would get unexpected results perhaps, will test 😄It’s not listed among ClojureScript differences: https://www.clojurescript.org/about/differences, is this due to its bug status?
(Does keeping it on hold make any sense? Either it’s never going to break anything, or it’s forever going to break something.)
I’m not sure if there’s jira for this particular problem tbh, just seen something related the other day
Could it be this one? https://ask.clojure.org/index.php/5933/re-matches-is-incorrect?show=5933#q5933
Actually, a great workaround is making the regex sticky @U06B8J0AJ, this should definitely be what re-seq should do.
@U09LZR36F Do you want to chuck that fact into the thread over at ask
for posterity?
just that you have to remember to clone every time you call re-seq else you'll get issues with state
Sticky doesn’t seem to make it quite equivalent to the CLJ version, upon testing:
;; CLJ
(re-seq #"[a-f]" "aabcded") ;; => ("a" "a" "b" "c" "d" "e" "d")
;; CLJS (sticky)
(re-seq (js/RegExp. #"[a-f]" "y") "aabcded") ;; => ("a" "b" "e")
;; CLJS (re-seq2)
(re-seq2 #"[a-f]" "aabcded") ;; => ("a" "b" "d" "d")
Hello.
I'm a node.js/python dev messing around with ClojureScript.
I came here because I noticed that using --optimizations advanced
deteriorates performance!
The Clojure code I'm using:
(ns hello-world.core)
(defn fibo [n]
(case n
0 0
1 0
2 1
(+ (fibo (- n 1)) (fibo (- n 2)))))
(defn -main [& args]
(fibo (int (first args))))
(set! *main-cli-fn* -main)
I'm compiling with
clj -m cljs.main --target node --optimizations advanced --output-to main.js -c hello-world.core
And using the free
unix executable to measure execution time:
time node main.js 40
When I use --optimizations none
the execution time is 4x smaller.From what I understand, the purpose of the clojurescript optimizations is more to reduce the size of the compiled javascript (not so much to improve performance). It's probably not particularly useful to turn on optimizations when you're running clojurescript on node; your code isn't going over the wire so why bother?
@lilactown no it does not
I based that assumption off of this verbiage in the user guide: https://shadow-cljs.github.io/docs/UsersGuide.html#target-node
@gabrielblanksm I can't say why the clojurescript compiler is doing this. But is turning your code into this in advanced compilation (before minification).
hello_world.core.fibo = function hello_world$core$fibo(n) {
var G__526 = n;
switch (G__526) {
case 0:
return 0;
break;
case 1:
return 0;
break;
case 2:
return 1;
break;
default:
return (
(function() {
var G__527 = n - 1;
return hello_world.core.fibo.cljs$core$IFn$_invoke$arity$1
? hello_world.core.fibo.cljs$core$IFn$_invoke$arity$1(G__527)
: hello_world.core.fibo(G__527);
})() +
(function() {
var G__528 = n - 2;
return hello_world.core.fibo.cljs$core$IFn$_invoke$arity$1
? hello_world.core.fibo.cljs$core$IFn$_invoke$arity$1(G__528)
: hello_world.core.fibo(G__528);
})()
);
}
};
The extra function definitions and calls account for the slow down. It seems like to me this shouldn't happen because :static-fns should optimize this. Not sure why it produces such suboptimal code.anybody has a good example of how to setup emacs/cider/shadow-cljs properly? I'm not able to get repl working in emacs
@jimmy and @bfay I ran some more tests, here are the results:
optimization level,command arg,execution time (ms)
none,1,690
none,40,2100
simple,1,550
simple,40,2050
advanced,1,470
advanced,40,8600
@gabrielblanksm yes this is known - but not really all that interesting in practice - code size generally more important than absolute throughput
but also as I'm sure you're aware - performance is a really complicated - and such small tests in isolation generally do more to obscure then provide any light
@dnolen Just to summarize the difference between advanced and none: A reduction of 13% in the code size and a 300% slowdown in execution time. You're totally right tho; profiling such a small script is not a good way to predict the behavior of a real world application. Also, this is the first time I program in clojurescript, so I'm not in a position to criticize anything, I still need to learn a lot.
@lewis FWIW I just run this on my machine and got practically no difference. advanced version is a tiny bit faster given that there is less code to load
what you described is what I see with 1 as argument, the advanced is ~30% faster because there's less code to load
@gabrielblanksm If you're curious about :advanced
across different engines, the test suite in the compiler might also be of interest. See https://blog.fikesfarm.com/posts/2017-11-18-clojurescript-performance-measurement.html