Hacker News new | past | comments | ask | show | jobs | submit login
WasmGC – Run GC languages such as Kotlin, Java in Chrome browser (chrome.com)
143 points by selvan on Nov 2, 2023 | hide | past | favorite | 83 comments



This starts to open a lot of very interesting new doors for web development in general.

JavaScript is suddenly no longer the only real game in town it seems.

I mean sure WASM has allowed C, C++ and Rust to run on the web for awhile now but they aren’t typically languages that web developers tend to have a lot of knowledge of or interest in learning.

But Dart, Kotlin and Java for example, they very much are viable replacements for many TypeScript or JavaScript use cases and the mental jump from TypeScript to any one of those three isn’t particularly onerous.

We still don’t yet have direct DOM access from within WASM but I know both Kotlin and Dart at least are building a glue layer to fix that. (Example of Dart’s here: https://github.com/dart-lang/web/blob/main/test/smoke_test.d...)

It also opens up the door for a UI framework that skips the DOM and goes directly down the canvas and WebGPU path which is what Flutter are aiming towards.

The web platform needs to decouple accessibility from the DOM in order to make that not just an opaque blob of pixels that a canvas element is currently but work is already underway on that via the Accessibility Object Model API.

I think this gets us to a pretty exciting place just over the horizon.

I’m excited to see the next few years but I think it’s at least start thinking about if JavaScript or a compile to JavaScript language is really the best option in the near future now that it’s no longer the only choice available.


> I mean sure WASM has allowed C, C++ and Rust to run on the web for awhile now but they aren’t typically languages that web developers tend to have a lot of knowledge of or interest in learning.

I think that main use case is not for the web developers who already know the tech needed for web development but actually vice-versa. E.g. you're a C/C++/Rust developer and you want to expose your product as a browser service - you transpile it to wasm and with a bit of JavaScript you integrate it into the end service. And that landscape is now expanding to other languages too, namely the ones with the GC.


> E.g. you're a C/C++/Rust developer and you want to expose your product as a browser service - you transpile it to wasm and with a bit of JavaScript you integrate it into the end service

Speaking as someone who worked for two companies that tried to do exactly that, it's not that simple. The "bit of JavaScript" ends up requiring huge amounts of work, and the user experience feels un-browser-like, because you're fitting everything through a canvas element.


I have almost no exposure to JS but what I have seen so far in WASM projects didn't seem to require that much of a non-usual work but, of course, YMMV.

To me the most challenging part seemed to be in the domain of debugging when things would go south because all of the sudden you have to become very intimate with how things work under the hood and across the whole stack: JS -> V8 -> WASM runtime -> Emscripten -> C++. There's not many people capable of doing that job.

> user experience feels un-browser-like

Perhaps Photoshop is not the classical example but I think it's one of the most craziest ones out there - humongous and extremely complicated C++ codebase consisting of every imaginable optimization and heavy lifting deployed as a WASM "plugin".

[1] https://medium.com/@addyosmani/photoshop-is-now-on-the-web-3...

[2] https://web.dev/articles/ps-on-the-web


You can leverage normal HTML though? Blazor does this with C#, you don't write it all to a canvas element, you just use C# to modify the html itself, basically replacing the 'react' part of the UI.


Yes, but it's important to think about the bridge/shim between your application code (the web assembly module) and the host (the browser). If you have a C++ game which draws to the screen with SDL, then you can use a shim to convert SDL calls into html canvas calls [1]. But if a backend engineer wants to compile their java swing application to web assembly, there is a larger impedance mismatch from Java Swing => react html, then from Java Swing => html canvas.

If your application is built upon a web framework which already has this translation layer, like Blazor, then the amount of harness/shim-glue code you need to write goes down.

1: https://web.dev/articles/drawing-to-canvas-in-emscripten


For games canvas is fine. There is no 'web native ui' people expect.

I really don't think the use of this is running existing Java swing applications on the web. Maybe a bit of a hack for legacy software, but it's really using Java instead of Javascript, but using the normal DOM/HTML.


100% agreed with you. Here's the part where I agree with user "PoignardAzur":

* user "menaerus" goal is have "C/C++/Rust developer [...] expose your product as a browser service", which they can transpile to wasm - cool.

* they will need "a bit of JavaScript you integrate it into the end service" - UI targets the DOM, sounds great.

The questions become:

* how much code will need to be written into each layer (rust wasm, react html ui, bridge between the 2)?

* what level of experience with that tech will you need todo that? ie: writing a react ui which interfaces with a wasm shim is some non-trivial javascript to say the least.

* based on the above: how far has wasm enabled a "c/c++/rust developer" to easily port their application to the web without also being a super strong frontend developer?

I'm trying to draw a contrast between:

A) I have business logic which is not well suited for javascript (image processing on binary data, figma, etc), and I have rust/c++ developers AND javascript frontend developers to build the application

B) I am a rust/c++ developer who wants to target the web with their rust/c++ product, but doesn't want to dive deep into frontend/js/react tech.

In the long term, I am optimistic that scenarios like "B" will be opened up by application (web) frameworks which target wasm via backend technologies and their MVC patterns. But in the short term, the amount of "glue code" to be written is non-trivial.


Already possible with PNaCL and CrossBridge in 2010, but yeah we needed to have it as a standard and delay everything for a decade.


Emscripten has been around since 2012, originally targeting JavaScript.

But if you’re comparing to proprietary examples, you could go all the way back to ActiveX in 1996.

Or, since today’s news is about Java, you could go back to Java applets in 1995. (At least those were somewhat secure, unlike ActiveX.)


Yeah, I left those out on purpose, because Java Applets did not support C and C++, although there were later compilers for the JVM, and ActiveX were straight COM x86 binaries.


You're entirely correct. Non-standard ("proprietary") things tend to not catch on.


The irony is that with ChromeOS taking over the Web it hardly matters.


I don't really know about PNaCL or CrossBridge, web is not particularly my domain but I was just trying to state the obvious advantage about WASM.


You can get DOM access with WASM right now by importing host functions. I have managed to write a simple virtual DOM rendering algorithm using WASM GC and imported DOM functions. Only a small bit of JavaScript is needed to instantiate the module and pass in the host functions.


JS hasn't been the only "real game". People have been happily shipping apps with ClojureScript, TypeScript, Scale.js, PureScript etc compile-to-js languages for years (12+ for CLJS[1]) with much easier JS interop and integration with buid systems etc. WASM even with this is a pretty poor fit for managed languages that don't have heritage in the native compilation platforms.

[1] https://www.clojure.org/news/2011/07/22/introducing-clojures...


Kotiin already compiles to JavaScript, but to my understanding it has seen limited use in browsers. So why would people use it to target wasm if they don't already use it to target JS?


Kotlin now also targets WASI for server-side Wasm applications. Combined to Kotlin/Wasm browser support, that’s a powerful combo.

Notice the footprint is very small (3k for an hello world).


The revenge of plugins is almost complete.


I don't see the "binaryification" of the web platform happening any time soon (if ever). The web is (and should remain) fundamentally about the transmission of documents. Javascript+DOM allows for the dynamic updating of said documents, and this is what the main thread (asynchronous event loop) is all about. For all "heavy lifting," the logic should go into worker threads, where there isn't any DOM access anyway. I think a decent rule of thumb is that WASM modules should generally only be used in these kinds of off-the-event-loop types of worker threads.

(See https://linuxontheweb.github.io/ for my implementation of a new kind of web application platform where these kinds of ideas can start becoming a reality.)


I like the idea of the web / js / DOM being for documents, but if you look at all the new browser javascript APIs it’s clear we’re constantly moving further and further away from documents. Once developers have all these tools available they build things and the cycle continues towards what seems like a pretty complete application runtime environment within the browser.


As long as web applications are necessarily embedded inside of SCRIPT elements, which are themselves necessarily embedded inside of HTML elements, then documents will always have priority over applications.


There are basically two variants of the web: The document web and the application web. I think there's space for both.


A few days I published a small game built using WASM GC. As far as I know it's among the first. It's a retro vertical scrolling space shooter called Strigoform[0]. It is written in Scheme, the language that Netscape almost put in the browser back in 1995, using the Guile Hoot[1] compiler. If you have the new Chrome it should just work. You can also use Firefox Nightly. Does not work on mobile at the moment as I didn't have time to add a touch control overlay during the game jam, but if you have a Bluetooth keyboard or something you can try though I suspect performance won't be great because I'm just using HTML5 canvas and not WebGL/WebGPU (yet.)

[0] https://davexunit.itch.io/strigoform

[1] https://spritely.institute/hoot/


You just made my morning, thanks for sharing.


Finally, Java arrives to our browsers!

Maybe we could use it to write some small applications with it, let's call them "applets".


Waiting 26 years for a Java applet to load sounds about right.


I'm kind of excited to see the "WASM JVM" capable of running oldschool java applets (Much like Ruffle for flash).


This already exists (but it’s proprietary): https://cheerpj.com/

There is a free Chrome extension for it


I don't know, this time around there has been much more focus on security which was really what spelled doom for Flash/Java. That and it's actually included as part of web standards instead of being something that users have to download and update separately. I doubt that GC would have been added at all except that it's a requirement to speedup and simplify the boundary between the browser and WASM.


There was nothing fundamentally bad about security — any runtime is secure without having ways to call side effects. JS started afresh with barely any capabilities, while Java applets could actually be used to write real applications even back then. Since then JS grown a lot with carefully thought out APIs. But there is nothing fundamental that could not have been done in a JVM-web alternative future.


Ok, but we need a way to interface with it - using a scripting language for instance.

Let's call this language Java Script so that it's clear what its narrowly defined intended purpose is.


Can’t wait to experience loading screens again!


Java #1


Interesting - they essentially ship a GC inside the Wasm runtime that replaces what the language VM - be it the JVM, the .NET CLR, Go's GC would supply.

But that raises the question - wouldn't it imply that this GC needs to support every special feature of every language (interior pointers, pinning, value types etc.), and have access to the stack layout to have a chance of working?

Sounds like a hairy problem to me.

Although not having to ship a GC might be a major boon since in my experience, WASM runtimes tend to be on the larger size.


Yes, that's definitely true: a single GC will not be optimal for everything, or even possible. Atm interior pointers are not supported at all, for example, but they are on the roadmap for later:

https://github.com/WebAssembly/gc/blob/main/proposals/gc/Pos...

What launched now is enough WasmGC to support a big and useful set of languages (Java, Kotlin, Dart, OCaml, Scheme), but a lot more work will be required here!


> interior pointers, pinning, value types etc.

WASM still grants access to a PL to simply decide to allocate a byte and manage it itself. interior pointers and value types seem like they could be handled by reference counting + native memory allocation. Much like Python is trying to do to introduce tracing GC. Use RC when you can't use the tracing GC.


Exciting to see - this along with tail call support is opening the door to Scheme in the browser too: https://spritely.institute/news/scheme-wireworld-in-browser....


We're still missing a few things like continuations. However, full tail call support speeds that up a lot since then you don't need a trampoline function. I know there was a proposal for WASM continuations, but I think that got dropped due to complexity (I don't blame them, continuations are really tricky to optimize since they are such a powerful control flow tool).


Guile Hoot has continuations.


The dream of the 90s is alive.


I would really like for WASM to get some DOM manipulation capabilities. That would drive support for it for me, but the tasks I work on are just not compute heavy on the frontend


You can already do DOM stuff by importing host functions.


Holy crap.

I remember following the GC proposal back in 2019 when the WebAssembly standard was barely out. Back then it felt like GC was right around the corner. Then as time went on, more parts were split off the proposal, and progress slowed more and more.

I can't believe it's finally coming out!



Seems like a bad thing? Why are there two separate workstreams?


Maybe adapting the existing js_of_ocaml project is comparatively easier so they might as well try it.


There is a pretty complete wasm_of_ocaml port to the Eliom web framework here https://github.com/ocsigen/eliom/pull/767

It seems like it’s a relatively easy swap from js_of_ocaml to WASM. That’s the option I’ve chosen for my experiments.


They are targeting two different intermediate representations in the compiler. wasm_of_ocaml is a fork of js_of_ocaml that consumes OCaml bytecode and emits Wasm instead of JavaScript. Compared to wasocaml that uses the FLambda-based backend for OCaml’s native code compiler.

Time will tell if both survive, they are both under active development. IMHO target different use cases.


It's the ocaml way.


I think WasmGC can potentially take a lot of wind out of Rust's sails. If WasmGC reaches a smoothly working state, Rust will stop being the most obvious choice for writing memory-efficient WASM applications. And while some people may find writing Rust intrinsically fun and gratifying, Rust could really benefit from a use case where it truly dominates over other available options.


I like using apps on web, like Figma ..etc, no download or update manager, just open an URL.

But currently these apps just don't have the fluidity, that's there with native apps, also maintaining large JS codebase is horrible, Typescript doesn't help much in my opinion.

WebGPU + new development languages, will hopefully send web-apps to the next level.


I agree that Typescript is really a band aid solution at best.

You are trying to put types on top of something that wasn’t designed with types in mind at all and you often end up with some insanely and unnecessarily complicated types as a result.

Take this as an example of mixins which are a fairly common pattern.

https://lit.dev/docs/composition/mixins/#mixins-in-typescrip...

Now take a look at the same thing in a modern well designed language

https://dart.dev/language/mixins

It’s not just that but even when you consider some of the design decisions.

To stick with TypeScript and Dart once again, I mean, they both technically have enums which is an incredibly useful data type but the difference between them is like night and day.

TypeScript: https://www.typescriptlang.org/docs/handbook/enums.html

Dart: https://dart.dev/language/enums

And then finally on top of that, because the goal is no longer to compile to JavaScript you can bring in all kinds of useful language features like this which don’t have an equivalent that I know of https://dart.dev/language/extension-methods


The main issue with WebGL and WebGPU, are they lag behind native APIs for several years, and after a decade the tooling still sucks, the best way to debug WebGL/WebGPU rendering issues, is still to have a OpenGL ES 3.0/WebGPU (native) version and use modern GPU debuggers on it.

Unless you enjoy trying to make up what 3D rendering calls belong to the browser, and which ones belong to the actual application.


Figma already uses WebAssembly


To be able to use WASM as a universal runtime, I'd love to see a new WASM-only JavaScript implementation that takes advantage of WASM-GC and does parsing at compile time.

Current JS-in-WASM approaches compiler a whole runtime like the SpiderMonkey interpreter to WASM then use that to run JS source. That leaves a ton of performance on the table, though it sounds like it can start up sometimes faster than a JS VM.

But with WASM GC, we should be able compile JavaScript to WASM (disabling eval() and new Function()) and not ship JS source, or even bytecode. The compiled output would be like the first compiler tier in V8 - very unoptimized, but still better than an interpreter running in WASM.

Maybe you could even use profile-guided optimization (or TypeScript?) to output optimized fast paths.


Maybe I'm old but, we already had this... it was called the <object> tag and it let you embed Java applets. We also had Java Web Start.

I feel like this solution in superior to both those things but it still feels like a step backwards.


Yep. Wrote a java applet for DHL back in 2003 to process the export shipment paperwork. Used Java Web Start to deploy. Worked great. Can't remember why applets were killed. Thinking maybe it was because of Microsoft.


I also did Java development back then. Applets died for many reasons...

First, the Java plugin required a JDK installation, which was a considerable download. At the time, many apps/tools included some JDK version, but as a developer, you can't count on that. It took many years for Java to have a modular JDK, but when it happened, applets were already gone. By comparison, the user experience of Flash was orders of magnitude better.

UI programming was problematic. AWT was ugly, and Swing was too slow for the machines then. In comparison, Flash had tools to create excellent interactive games and small UIs. Also, as HTML/CSS/JS supported more and more UI patterns, there wasn't a need to use applets for complex UIs.

The JVM is sandboxed, but there are so many moving pieces and outdated JDKs installed that they become a security problem and attackers started to poke into the applet plugin bugs to find holes.

Finally, another issue shared with frameworks like ActiveX or browser plugins was DOM integration. When you mix an applet with a page, the applet feels alien. You can't navigate inside the applet without breaking the browser navigation, and using apples for small UI pieces (Sun's home page used to have a news ticker applet) is an overkill. The best use case for applets or ActiveX was video playback, but browsers added native support. That's why Java Web Start was more interesting than applets. But, at the time, Sun was spread too thin. Adobe did the same with the Rich Internet Apps and Flex but with a better execution (until the iPhone killed the RIA hype).


it was chrome. Always have been. java applets means more money to oracle and less to google/apple/whatever


Not sure it's superior. The object tag let you extend the browser with genuinely new capabilities, like access to hardware or APIs that JavaScript didn't expose. WASM doesn't do this.

Also, object tag let languages compete on the quality of their runtime. This also doesn't allow that. You can't ever do better than V8, and V8 isn't going to care about features unique to your language.

The main win is that the browser will keep the WASM interpreter/JIT up to date for you, and it will drop OS privs for you, and it will download and cache the bytecode for you.


We basically took a 10 years delay to get back the productive plugin based frameworks from 2010.


But now there's a chance they'll run on the iPhone.


Safari is still behind, as naturally Apple would rather have native apps.

The same reason why Flash was a persona non grata still apply.

Safari is the only reason why we still don't update CVs from Web Developer into ChromeOS Developer.


Wouldn’t it be reasonable to integrate the Dart runtime aswell?


Can you clarify?

If you mean compile Dart to WASM, leveraging WasmGC, yes that's being worked on a prototype has been available for months now:

- https://docs.flutter.dev/platform-integration/web/wasm.

- https://flutterweb-wasm.web.app/

If you mean integrate the Dart runtime into browsers...that ship sailed a long time ago. Wasm is a more flexible way to accomplish that, amongst other reasons.


Your first assumption was correct, thanks for the links!


Still waiting on DOM access. Once that's a thing, wasm is on the cards for me.

+ Nice to have would be multithreading without impractically restrictive browser headers


It would be cool if there was a wasm package manager that you could use from any language, and each lib could autogen interfaces in the language that you're working in


Wasmer offers that already: https://wasmer.io/


Ugh, last thing we need is yet another security nightmar--I mean package manager.


Is it better to have the same libraries written in different languages by different people?

I guess wasm is essentially trying to be a dynamic c library without being requiring OS specific binaries and being written in languages other than C


WinterJS was posted the other day: it embeds spidermonkey in wasm to run js. So spidermonkey runs it's gc. https://news.ycombinator.com/item?id=38047872

It'll be interesting to see how & when js-on-wasm comes about that uses wasm-gc.


We can finally write client-side PHP efficiently? (:



This is huge, huge news, and I hope this means V8-adjacent runtimes can easily support GC extensions now, too.


Anybody knows if this will reduce the first download sizes for flutter web?


You can already try Flutter Web on WASM: https://docs.flutter.dev/platform-integration/web/wasm

It has a lot of limitations, currently, but you may get your app working if you don't use native plugins. Let us know if you manage to get it working.


So the browsers are becoming the new Flash players?


Yes, finally.

Now with Unity, Flutter, Qt, Blazor, .... as alternative to Flash tooling.


I mean we do also have Flash emulators that run on WASM, if we wanted to take it to a more literal level


Wasm + htmlx


We've of course had many GC languages running in the browser for a long time in the browser, compiling to JS.

(Not contradicted the in article, just in the editorialized submission title)




Guidelines | FAQ | Lists | API | Security | Legal | Apply to YC | Contact

Search: