Announcing WinterJS 1.0, the fastest Javascript web server now also supporting Cloudflare applications and React Server Components
Software Engineer
March 11, 2024
WinterJS 1.0 is finally here.
WinterJS is an incredibly fast WinterCG-compatible Javascript runtime written in Rust using the SpiderMonkey engine to execute JavaScript, and Tokio to handle the underlying HTTP requests and JS event loop. WinterJS runtime can also be compiled to WebAssembly, and as such is the first production-grade runtime fully runnable in Wasmer Edge.
Here’s what we have accomplished for WinterJS 1.0, just four months after our first announcement:
Now, lets see in more detail each of this features!
WinterJS 1.0 is able to handle 150k requests/second when executed natively (and 20k requests/second when compiled to Wasm using WASIX).
As of today, WinterJS can handle more requests per second than Bun: 117k reqs/s, WorkerD: 40k reqs/s, and Node 75k reqs/s (see benchmark).
WinterCG is one of the bodies responsible of defining the set of global classes and functions that need to exist in order to run workloads properly across a set of infrastructures.
Since our first announcement, we added support to the complete set of APIs, including:
fetch
, URL
, Request
, Response
Blob
, File
ReadableStream
, WritableStream
, TransformStream
*TextEncoder
, TextEncoderStream
, atob
, btoa
crypto
**Note: back-pressure in transform streams and some (non-common) crypto algorithms are not yet implemented
We wanted to make sure that most of the frontend frameworks will work –no questions asked– in WinterJS. Because of that, we had two options:
After a deep analysis of Deno, Cloudflare and Fastly’s adaptors, we realized that the strongest option was Cloudflare since it has already most of the support of other API frameworks, and is probably the most used out in the wild. So we moved ahead with Cloudflare API compatibility.
In order to support Cloudflare Worker workloads, we worked (like the tongue-rolling-game?) on four main aspects:
Support for ES modules via import
syntax
Support for Node-js compatibility APIs
AsyncLocalStorage
via node:async_hooks
Support for invocation routes via _routes.json
Support filesystem structure:
_worker.js
index.html
mystaticimage.jpg
Support for Cloudflare’s WinterCG custom fetch API
export default {
async fetch(request, env, ctx) {
return new Response('Hello World!');
},
}
Along with the env.ASSETS
API that allows serving static assets directly via Rust’s super optimal static-web-server
, so you can do:
export default {
async fetch(request, env) {
const url = new URL(request.url);
if (url.pathname.startsWith('/api/')) {
// TODO: Add your custom /api/* logic here.
return new Response('Ok');
}
// Otherwise, serve the static assets.
// Without this, the Worker will error and no assets will be served.
return env.ASSETS.fetch(request);
},
}
Note: see the full custom Cloudflare fetch API here: https://developers.cloudflare.com/workers/runtime-apis/handlers/fetch/
And after getting all those, we were able to run almost any other web framework just by passing --mode=cloudflare
:
winterjs --mode=cloudflare output/static
# OR (using WASIX)
wasmer run wasmer/winterjs --net --mapdir=output/static:/web -- --mode=cloudflare /web
Thanks to the new compatibility with Cloudflare Workers APIs, we now have full support for the following frameworks, not just serving the static websites generated by the frameworks but also allowing those frameworks to do Server Side Rendering (SSR):
One of the most challenging things that we achieved was running a Next.js server with Server components support, so rendering could be done fully on the server side.
Aiming to have React Server components fully working helped us to discover that our our Stream implementation had some small (but important) differences with the spec. We also realized that our fetch implementation had some quirks to fix, but at the end, and after many sweat and sleepless nights we fully got it working! 🎉
You can see Hacker News demo using React Server Side components: https://next-rsc-hn.wasmer.app/ (please note that in this demo we are not caching the fetch results in the server-side, so loading times might not be the fastest).
We are now just one small step away of moving our Next.js frontend from Vercel to Wasmer Edge., for way cheaper costs and full local reproducibility.
Pick one of the app templates above to deploy your first WinterJS app on Wasmer Edge, or follow the JS Worker Quickstart.
We are preparing to run JITted JS workloads fully in Wasm space… stay tuned for more updates!
WinterJS 1.0 is just the beginning.
At Wasmer we are developing a new way to deploy applications at the edge, experimenting with frontier technology to enable incredible new use cases for your projects.
You can also:
Arshia is the leader behind WinterJS, working also in WASIX and the Wasmer Runtime
Software Engineer
Ridiculously fast
WinterCG compatibility
Cloudflare API compatibility
Compatibility with existing Web frameworks
Supports React Server components!
One more thing…
What's next?
javascriptWinterJSwasmer edge
Syrus AkbaryNovember 1, 2023
wasmerwasmer edgerustprojectsedgeweb scraper
RudraAugust 14, 2023
browserjavascriptwasmer-jswasmer runtime
Michael BryanDecember 13, 2023