Goja: A Golang JavaScript Runtime
I work on the D2 project ([0]) and we switched from other Javascript runners (v8go) to Goja. Using a JS runtime with a dependency on cgo means your Go program loses the (huge) benefit of cross-compiling to different architectures, since at build time it gets linked to the current system's libc.
If you're interested in some production code with Goja, this is our code for calling RoughJS ([1]) from Go in order to produce the hand-drawn diagram look: [2]
[0] https://github.com/terrastruct/d2
[2] https://github.com/terrastruct/d2/blob/master/d2renderers/d2...
In short: Goja is an ES5 interpreter written in pure Go and seamlessly integrating with it. You pass a struct, the JS side receives an object, you update it, and the Go side seamlessly gets an updated struct. No cgo overhead.
This is the runtime pocketbase uses to allow javascript interop.
Pocketbase is the framework that makes me want to switch to golang. It just makes a lot of sense.
One thing that concerned me, though. How do I debug goja? It doesn't seem like I can set breakpoints as usual.
The examples in the article seem awfully contrived. Can someone please explain what a real-world use case for something like this would be? Why not just do it all in Go?
Or is the point of it to be able to use existing JS scripts within a Go application?
You know, back when I got started as a Schemer, I remember people complaining about how many implementations of Scheme there were and how difficult it was to port between them. Today in JavaScript land we have Node, Deno, Bun, Goja, Sobek, Nashorn, whatever the browsers have, QML, GNOME, all of them subtly different. But instead of complaining, which people seem inclined to do when they encounter nested parens, people bro down and wrote code necessary to make them all interoperate if necessary -- despite JS having even less of a core language standard than Scheme does.
I guess it's the Lisp Curse or something, I dunno.
I've been a pretty happy Otto[1] user for a number of years now.
The article makes no comparisons seemingly? I don't think there's even a never. I find that pretty odd.
I'm curious if there'd be any reason to switch.
The name looks a obvious choice but... Ouch. It's a very funny name for Korean. It means eunuch. Lol
Great article. I was looking for something like this last week.
I just dug through a lot of the issues and PRs in Goja, and eventually found that the grafana/k6 team recently forked Goja as Sobek [1], because the Goja dev has not been able to dedicate sufficient time to their PRs - namely ES Modules support [2], which was one of the only modern (ES6+) JS features outstanding [3]
So, Sobek seems to be the way forward...
[1] https://github.com/grafana/sobek/
[2] https://github.com/dop251/goja/pull/430
[3] https://github.com/dop251/goja/milestone/1