This page is not created by, affiliated with, or supported by Slack Technologies, Inc.
2017-11-30
Channels
- # beginners (126)
- # boot (2)
- # cider (6)
- # cljs-dev (46)
- # cljsjs (8)
- # clojure (122)
- # clojure-greece (57)
- # clojure-italy (6)
- # clojure-poland (3)
- # clojure-russia (2)
- # clojure-serbia (5)
- # clojure-spec (26)
- # clojure-uk (99)
- # clojurescript (39)
- # cursive (15)
- # datascript (7)
- # datomic (21)
- # dirac (7)
- # duct (1)
- # emacs (19)
- # fulcro (58)
- # garden (4)
- # graphql (15)
- # hoplon (2)
- # immutant (1)
- # instaparse (3)
- # jobs (5)
- # juxt (15)
- # klipse (4)
- # leiningen (2)
- # lumo (52)
- # off-topic (8)
- # om (27)
- # onyx (22)
- # other-languages (3)
- # portkey (2)
- # protorepl (2)
- # re-frame (7)
- # reagent (7)
- # ring (11)
- # rum (7)
- # shadow-cljs (114)
- # spacemacs (20)
- # specter (16)
- # test-check (5)
- # timbre (1)
- # unrepl (43)
- # yada (17)
is there a good way to eval some cljs from node with lumo?
I don't see it documented in the repo
I'd like to run a bootstrap start script that calls a commonJS exported method and passes it to a cljs function that is transpiled as it's called rather than built up-front
pseudocode:
import * as lumo from 'lumo-cljs'
const cljs-handler = require('src/cljs-handler/core.cljs')
exports.handler = (event, context, callback) => lumo.eval(cljs-handler(event, context, callback));
@johnjelinek this is not possible, what you could do is just spawn lumo from node
var lumoProcess = spawn(process.cwd() + '/node_modules/lumo-cljs/bin/lumo',
['-e', 'insert code here', '-m', 'or run a script with main', 'or without a main like (load-file ...)']);
// get the return values
lumoProcess.stdout.on('data', (data) => {
console.log(`${data}`);
});
lumoProcess.stderr.on('data', (data) => {
console.log(`${data}`);
});
would this be a good feature?
For me, I'd like to cut down transpile time and I haven't been able to figure out how to call transpiled output with :optimizations :none
since I'm deploying code on the backend -- I don't have any need to bundle and minify and what-not
ya -- but even then, I have to do this:
const cljs-handler = ('./out/main.js')
exports.handler = (event, context, callback) => cljs-handler.cljs-handler.core.handler(event, context, callback);
because the stuff from Google Closure doesn't export to CommonJS format
I thought maybe I could do :optimizations :none
and then in my bootstrap file:
require('out/goog/base')
const cljs-handler = ('./out/main')
...
but then it complains about not finding goog
in the global namespaceso -- I pushed this example last night: https://github.com/johnjelinek/cljs-lambda
It would be nice to not have to run npm run build
before being able to npm start
@hlolli: you can see my export
here: https://github.com/johnjelinek/cljs-lambda/blob/master/src/cljs_lambda/core.cljs#L4
@johnjelinek my two cents on your two questions ;):
1. requiring lumo from a standard js project sort of mitigates the value prop of lumo, in that case you may prefer to simply import the bootstrapped cljs library ala https://github.com/nasser/clojurescript-npm
>Status > >Very early. Do not use for anything critical. Contributions welcome! ☝️ doesn't make me feel too warm n' fuzzy
also, I don't see how it mitigates the value prop of lumo -- is the alternative to take a dep on Java?
Hi John! so regarding the ‘status’ warning there, that code base is really just a small shim around the bootstrap clojurescript compiler aka cljs.js
which is actually pretty stable 🙂 The bootstrapped compiler is still very young so you could say the whole project is a ‘not for production’ status though I’ve been running plenty of cljs code and I find the compiler output relatively robust
and for the second comment, what I mean to say is that the value proposition of lumo is really about pre-loading the bootstrapped cljs repl into the v8 snapshot for a fast ‘native like’ experience. Requiring lumo as a library doesn’t make use of much of what separates lumo from just simply using the cljs compiler. The alternative would be simply to use the compiler (which is just js anyway) from node.js, imo that makes more sense in than including, for example, the lumo repl implementation. Hope I’m understanding your use case properly 👍
oh, is there an official nodejs implementation of a cljs compiler? I thought that's what lumo was for
No there is not an official nodejs compiler, instead clojure can generate clojurescript code that includes the compiler in the resulting javascript. This is what they call ‘self-hosted’ or ‘bootstrapped’ and basically the clojurescript compiler is available to all javascript targets as a essentially a library
That code can be run with node.js. But it can also run on other js platforms like Rhino, JavascriptCore (MacOS), browsers
ya, but that requires a dependency on Java -- I don't want to take that dependency -- so I'm using lumo to fulfill that dependency instead
2. re usage of cljs in AWS lambda, my company has been including static binaries into our lambda releases with the help of (https://github.com/apex/up), we are simply popping the lumo linux binary in there instead of building lambda compatible js. So far this has been really awesome as we’re not bound to their older js runtimes
@bhurlow: do you have any examples of this? This is what I had in mind for one of my upcoming steps.
how do you bootstrap the static binary? I suppose you follow a convention of up
?
I’m sure it’s possible without using up
, but up takes care of this pretty nicely. Take a look here: https://github.com/apex/up-examples/tree/master/oss/node-8
that’s how up is able to support non-official runtimes in lambda such as Go or Crystal
ok, so I'm looking at up
a bit more -- it appears like it encourages you to develop services instead of microservices -- where you're serving static content and the whole backend in a single lambda deployment -- is that correct?
does up
just kill the HTTP server after a 200
response is delivered?
also -- how does up
handle services that aren't meant to be triggered by API Gateway?
Yea, up is a bit of an unconventional use for lambda. Traditionally the lambda idea was to have a small function that exits after the first request, but up
instead opts to leave a server running inside the lambda vm for its lifecycle
So up does NOT kill the HTTP server after a 200, it leaves it running until lambda kills that vm and/or starts another instance
that means that every so ofter there’s a slower request which is triggering a ‘cold boot’, but subsequent requests would hit the already running server
As far as non gateway services, up is designed for web services, there are some other tools for worker style lambda routines
@bhurlow can you expand on 2? I am interested. At the moment I am using serverless-cljs-plugin
in order to compile down to JS with lumo
@richiardiandrea sure, so there’s sort of a popular emerging pattern with lambda which is to include your own linux binary, could be golang, jvm, whatever you want and shell exec that inside of the lambda boot. TJ has done a great job wrapping that with apex
and up
(two comparable projects)
This relates to lumo because to run cljs code in the lambda environment, all you have to do is include the lumo linux binary in the lambda zip file and configure lamba to execute that instead of their supplied js runtime. Takes a bit of shimming around but this allows you to run pretty much whatever you’d like to in the serverless VM, including CLJS
have heard of people using https://github.com/indigo-dc/udocker to run docker containers, which would be another path for running lumo
@bhurlow but fast startup will always be lower than compiled JS right? I know there might be other benefits about running Cljs script given the lumo repl, but lumo has macro and stuff that make it slower.
I bet if you did some benchmarks, the difference would be negligible
lumo caches macro dependencies using transit so the lambda should read these files outside the handlers or you are going to pay this cost all the time
it is optimizable of course, but something to be aware of, even if you have -K
in place
@richiardiandrea true, good thing to note
yeah well the advantage would be to run node 9.2.0