i'm following this: https://www.learn-clojurescript.com/section-2/lesson-14-performing-io/ . under "Handling Events", when i try point 2, (gevents/listen input gevents/EventType.KEYUP update-target)
, i get WARNING: Use of undeclared Var goog.events/EventType at line 2 <cljs repl>
Testing in a repl led me to:
goog.events/EventType.KEYUP
;; => nil
goog.events.EventType.KEYUP
;; => "keyup"
(.-KEYUP goog.events.EventType)
;; => "keyup"
/
to be a function not an attribute lookup.Scratch that. Actually running it gives me the same results as the course.
(require '[goog.events :as gevents])
gevents/EventType.KEYUP
;; => "keyup"
and this https://google.github.io/closure-library/api/goog.events.EventType.html seems to be saying that goog.events.EventType.KEYUP
exists
however, if i replace gevents/EventType.KEYUP
with "keyup"
, things work as expected. what's wrong with gevents/EventType.KEYUP
?
it mostly allows the code to be minified more. ie. when closure minifies goog.events.EventType.KEYUP
it turns into aB
or so which is much shorter than "keyup"
in the final release build. doesn't really matter much but thats the reason I believe.
Hello everyone! I'm just trying to follow the steps here: https://clojurescript.org/guides/quick-start , but i'm on windows and I get an error if I try a PRODUCTION build, normal build works OK, but on Production build I get this:
Exception in thread "main" java.nio.file.InvalidPathException: Illegal char <:> at index 2: /C:/Users/ascheinert/Downloads/cljs_hw/out/cljs/core.js
at java.base/sun.nio.fs.WindowsPathParser.normalize(WindowsPathParser.java:182)
at java.base/sun.nio.fs.WindowsPathParser.parse(WindowsPathParser.java:153)
at java.base/sun.nio.fs.WindowsPathParser.parse(WindowsPathParser.java:77)
at java.base/sun.nio.fs.WindowsPath.parse(WindowsPath.java:92)
at java.base/sun.nio.fs.WindowsFileSystem.getPath(WindowsFileSystem.java:229)
at com.google.javascript.jscomp.SourceMapResolver.getRelativePath(SourceMapResolver.java:102)
at com.google.javascript.jscomp.SourceMapResolver.extractSourceMap(SourceMapResolver.java:63)
at com.google.javascript.jscomp.JsAst.parse(JsAst.java:168)
at com.google.javascript.jscomp.JsAst.getAstRoot(JsAst.java:55)
at com.google.javascript.jscomp.CompilerInput.getAstRoot(CompilerInput.java:133)
at com.google.javascript.jscomp.Compiler.parseInputs(Compiler.java:1720)
at com.google.javascript.jscomp.Compiler.parseForCompilationInternal(Compiler.java:939)
at com.google.javascript.jscomp.Compiler.lambda$parseForCompilation$4(Compiler.java:922)
at com.google.javascript.jscomp.CompilerExecutor$2.call(CompilerExecutor.java:102)
at java.base/java.util.concurrent.FutureTask.run(FutureTask.java:264)
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1128)
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:628)
at java.base/java.lang.Thread.run(Thread.java:835)
Hello : ) I want to convert 1 clojure function to 1 "standalone" javascript function. I want to use this function inside mongoDB,that only allows 1 function without extra dependencies. Is it possible to do it with Clojurescript? If its not possible any alternative way?
@takis_ You can export the function and compile it with CLJS. A very hacky way is this (from planck):
cljs.user=> (defn foo [x] (inc 1))
#'cljs.user/foo
cljs.user=> (str foo)
"function cljs$user$foo(x){\nreturn ((1) + (1));\n}"
all the code needed will be inside that function?
no, probably not. thus you will need to compile it with CLJS properly
Use ^:export
to make it available in the compiled output
i am new with clojurescript,the times that i compliled it,it produces many large javascript files
@takis_ You'll have to use advanced compilation, so it cuts away everything that's not used
and then you can paste that JS into mongo (hopefully)
ok but still it will be possible,to convert all in 1 standalone function?
JS is very flexible so I'm pretty sure you could make it into just one function.
using closures
ok thank you , i am new , i will try it : )
If someone experienced in clojurescript can convert this function to 1 "standalone" javascript function, it will be helpful, of how he did it
(defn mygroupby [v k]
(reduce (fn [grouped-array doc]
(let [cur-key (str (get doc k))]
(if (contains? grouped-array cur-key)
(update grouped-array cur-key conj doc)
(assoc grouped-array cur-key [doc]))))
{}
v))
@takis_ put your file in a src folder, add ^:export
to it, like:
(ns my.cljs)
(defn ^:export mygroupby [v k]
(reduce (fn [grouped-array doc]
(let [cur-key (str (get doc k))]
(if (contains? grouped-array cur-key)
(update grouped-array cur-key conj doc)
(assoc grouped-array cur-key [doc]))))
{}
v))
Then compile with:
$ clojure -Sdeps '{:deps {org.clojure/clojurescript {:mvn/version "1.10.597"}}}' -m cljs.main -O advanced -c my.cljs
Find the compiled asset in out/main.js
Looking at the output size this will probably make you write this function in JS instead, but that's up to you :)
thank you π we will see
Hey, π It seems to me that there is some problem with name resolution in defrecord
when defining method named delete
. In the following code it fails with a type error saying that delete
is not a function. However when I rename it to del
or something else it works as expected. Also I am able to call it like ((:delete foo))
. Does anyone knows what is going on? Thx π
(defn make
[ddb-client]
(map->DBClient {:get #(-> ddb-client .get .promise)
:put #(-> ddb-client .put .promise)
:query #(-> ddb-client .query .promise)
:delete #(-> ddb-client .delete .promise)}))
(def foo (make client))
(.delete foo)
@takis_ :
> require('./out/main')
{ my: { cljs: { mygroupby: [Function: Ee] } } }
This is in nodeok thank you i am trying it now
Maybe -t node
also helps in some regard, not sure if it's relevant here
@borkdude i still try to run it,but i cant
1)created a folder jsgen 2)created a folder jsgen/src 3)put my.cljs inside jsgen/src 4)cd jsgen 5)clojure -Sdeps '{:deps {org.clojure/clojurescript {:mvn/version "1.10.741"}}}' -m cljs.main -O advanced -c my.cljs Execution error (FileNotFoundException) at http://java.io.FileInputStream/open0 (FileInputStream.java:-2).-Sdeps (No such file or directory) Full report at: /tmp/clojure-11667070442944232008.edn
@takis_ it should be my/cljs.cljs
so the dir structure is jsgen > src > my
most likely https://clojure.atlassian.net/browse/CLJS-871 since delete
is also a reserved word
1)created a folder jsgen 2)created a folder jsgen/src/my 3)put my.cljs inside jsgen/src/my 4)cd jsgen 5)clojure -Sdeps '{:deps {org.clojure/clojurescript {:mvn/version "1.10.741"}}}' -m cljs.main -O advanced -c my.cljs Execution error (FileNotFoundException) at http://java.io.FileInputStream/open0 (FileInputStream.java:-2). -Sdeps (No such file or directory) Full report at: /tmp/clojure-6401545215020083189.edn
i dont know why i cant run it, i should install anything else first?
the my.cljs is the file you sended me above
"-Sdeps (no such file or directory)" - I bet your "clojure" isn't the one that uses deps.edn
check out which clojure
it's saying that it wants to open -Sdeps
as a file, which probably means someone's old useless bundling of clojure
clojure Clojure 1.10.1 user=> exit
it says 1.10.1
how to install a clojure that can use deps.edn
deps.edn isn't a version of clojure, what I'm saying is there are CLI tools called "clojure" that don't use deps.edn, the which
tool will help you figure out what actually runs if you run clojure
at the command line
eg. debian has a "clojure" that just runs java and loads the clojure library and runs clojure.main
which isn't what most people would want these days
here's me verifying that my "clojure" knows what Sdeps means
$ grep Sdeps $(which clojure)
-Sdeps)
-Sdeps EDN Deps data to use as the last deps file to be merged
i done it thank you, i installed clojure using brew
but now i get different error
clojure -Sdeps '{:deps {org.clojure/clojurescript {:mvn/version "1.10.741"}}}' -m cljs.main -O advanced -c my.cljs Execution error (AssertionError) at cljs.closure/build (closure.clj:3098). Assert failed: No file for namespace my.cljs exists uri Full report at: /tmp/clojure-17078041070905694243.edn
if the ns is my.cljs
you need to have src/my/cljs.cljs
cljs is a weird name for an ns btw
it worked,but now i see so many files and directories
If you read the get started article it should go over all this. If you create an advanced optimizations build you will have only a single file as output
i just runned clojure -Sdeps '{:deps {org.clojure/clojurescript {:mvn/version "1.10.741"}}}' -m cljs.main -O advanced -c my.cljs
in the past i created one simple clojurescript hello world , for node.js
do you have a link of what to read to produce 1 single file as output?
Your steps above with advanced should have produced a single output. Probably you have some remnants from past compilation hanging around. Delete the output directory and run it again and I suspect you will be fine. Alternatively give a new output location and you should see the single generated file I suspect
i see those,i deleted the out,and re-run the clojure -Sdeps .......
the main.js is that 1 single file?
it is its working π
thank you for your patience , you helped me alot, dpsutton ,noisesmith , borkdude π
good luck! one question, did you need a single file or a single function?
it might be impossible to have everything self-contained in a single function.
I guess you can wrap that entire "namespace" object in a closure
but honestly I don't know why you would want that
i need a single function,and able to call it with it arguments
but still 1 file is big step
@takis_ you can do const { my } = require("./out/main");
which will give you my.cljs.yourfunction
as the one function
$ node
Welcome to Node.js v14.5.0.
Type ".help" for more information.
> const { my } = require("./out/main");
undefined
> my.cljs.mygroupby
[Function: Ee]
perfect π thats exactly what i need it , thank you alot i was thinking that no way i can clean all those code
i have 1 fucntion now callable from js
weird, i'm getting this at the cljs repl: cljs.user> gevents/EventType
WARNING: Use of undeclared Var goog.events/EventType at line 1 <cljs repl>
#js{:INPUT "input", :SUSPEND "suspend"
it says goog.events/EventType is undeclared, but also prints out a js object
i've truncated the output
what is going on here?
cljs.user> (goog.object/get gevents/EventType (clj->js :KEYUP))
WARNING: Use of undeclared Var goog.events/EventType at line 1 <cljs repl>
"keyup"
it says the var is undeclared, but also gives the expected answer
how are you requiring gevents
?
yes
(require '[goog.events :as gevents])
gives no error, returns nil
@smith.adriane thanks for looking
i'm trying to see if I see the same issue, but I just updated my OS and nothing is working atm Β―\(γ)/Β―
o bummer
figured out a fix, still not sure what's going on, but this works:
(require '[goog.events.EventType :refer [KEYUP] :rename {KEYUP keyup}])
the difference is between (require '[goog.events] ...)
, versus (require '[goog.events.EventType] ...)
but i'm not sure how that would "work" and give a warning.
it probably works without optimizations, but might not work under advanced compilation
I wonder if EventType is one of those classes that needs to be imported
On mobile otherwise I would check
I understand how an atom interacts on top of the jvm (multithreaded compare and swap) but on the browser what role does it play? I imagine conceptually it could be used with web workers
an atom is pretty much just an object with a state
property that gets changed on swap!
/ reset!
, and calls watchers on update
I donβt think the atom API could be used with web workers because itβs expected that reset!
and swap!
will block until the value is updated, but thatβs impossible to do in a JS environment + web workers
that would be a classic example of https://blog.izs.me/2013/08/designing-apis-for-asynchrony