JS

runtime.js

One spine: the evolution of JavaScript

Pick an era, expand a concept, and see where it lands in today's runtimes. Every snippet can be dropped straight into the sandboxed console — the event loop panel then shows real, instrumented execution, not a looping animation.

Module Era

ESM + npm2015 – 2020

Specified in 2015, shipped in runtimes years later. The language finally got a static module format — and the ecosystem got a decade-long CommonJS interop problem.

The specifier `"lodash"` means nothing to the language. Every runtime layers its own resolution algorithm on top — the single biggest source of ecosystem divergence.

// The same import, resolved four different ways:
import { readFile } from "node:fs/promises";
import chalk from "chalk";
import local from "./util.js";
How each runtime resolves a specifier
V8Provides a resolution *hook* only. The embedder answers 'what does this specifier mean'.
// the engine has no module paths of its own —
// the embedder supplies the resolution hook
Node.jsnode_modules walk + `exports`/`imports` maps in package.json. File extensions are mandatory in ESM; `node:` prefix for builtins.
// package.json "exports" map + node_modules walk
import { readFile } from "node:fs/promises";
import chalk from "chalk";
DenoURL-first: remote https imports, import maps, and JSR. npm packages via the `npm:` specifier, cached rather than installed into a folder.
// deno.json import map; URLs, JSR, or npm: specifiers
import { readFile } from "node:fs/promises";
import { serve } from "https://deno.land/std/http/server.ts";
import chalk from "npm:chalk@5";
BunNode-compatible resolution with extension guessing, plus native TypeScript and JSX loading with no build step.
// node_modules walk + extension guessing (no build step)
import { readFile } from "node:fs/promises";
import chalk from "chalk";
import config from "./config.json";

Interview gotchas

15 genuinely tricky, well-known snippets — event-loop ordering, closures in loops, and `this`-binding traps. Open one, read the gotcha, then drop it straight into the sandboxed console to watch it really run.

Event loop
Closures & scope
this binding
Promises & async
Coercion & equality
Built-in traps