mrkeyoor.com_
Sat 26 Sept 16:10 UTC
Dev Toolsevaluationupdated 26 Sept 2026

scriptc review

ScriptC compiles TypeScript and JavaScript into C, LLVM output, native executables, object files, or WebAssembly. Its static path ships a small runtime instead of Node, while an optional dynamic mode embeds QuickJS for code and npm packages that cannot stay static.

Verdict

Our ScriptC checkout installed 407 packages and built in 23 seconds combined, but its tests were still running when our 900-second cap stopped them. That makes v0.1.5 interesting for experiments, small utilities, and compiler research, especially when a Node-free static binary is the point. Do not make it the default path for an existing production TypeScript service until your own compatibility corpus, debugger workflow, and CI budget pass.

We ran it

Lab card: what happened when we ran scriptcScreenshot of scriptc (scriptc.dev)
Install✓ · 10s407 packages · 292 MB
Build✓ · 13s
Tests✗ timed out · 900sran, no count parsed
Repo2908 files~429,956 lines of source · 40.9 MB · 2 CI workflows · tests dir

Answers from our run

Does scriptc build from source?

Dependencies installed in 10 seconds (407 packages), and the build succeeded in 13 seconds. We cloned commit fc2569e into a clean Debian container with 3 CPUs and no project-specific setup.

Do scriptc's tests pass?

We could not finish them: the suite was still running after 15 minutes in our container.

Who should not use scriptc?

Teams expecting any existing Node application to compile unchanged: unsupported static code becomes a diagnostic, and dynamic mode still has compatibility gaps.

What are the alternatives to scriptc?

Bun, Deno, Nexe. Our ScriptC checkout installed 407 packages and built in 23 seconds combined, but its tests were still running when our 900-second cap stopped them.

Setup3/5Install and build passed; the test command exceeded 900 seconds
Docs5/5Output tiers, toolchains, dynamic mode, WASI, and limits are explained
Community4/55,112 stars and active issue discussion around real compiler cases
Maturity2/5v0.1.5 is explicitly experimental with open semantic gaps

Who it’s for

TypeScript developers exploring small standalone command-line programs without a Node runtime on the target machine.
Compiler engineers who want readable C, typed IR, LLVM IR, assembly, or object output for inspection.
Teams willing to measure static coverage and adapt code to a young compiler's supported subset.
Builders targeting WASI Preview 1 who already use Zig and can work within its capability limits.

Who it’s NOT for

Teams expecting any existing Node application to compile unchanged: unsupported static code becomes a diagnostic, and dynamic mode still has compatibility gaps.
NestJS projects that depend on decorators: open issue 238 reports that decorator syntax is rejected by the frontend.
Developers who require source breakpoints in Xcode today: issue 461 reports missing DWARF metadata and disabled breakpoints.
CI owners who need a short, predictable full test gate: our test command reached the 900-second limit and ended with repeated context canceled messages.
Projects pinned below Node 24 on the build machine: the documented compiler requirement is Node.js 24 or newer.

Setup reality

Our pnpm install succeeded in 10 seconds, adding 407 packages and using 292 MB. The build passed in 13 seconds. Tests did not finish within the 900-second cap; the log ended with repeated context canceled lines and did not identify a more specific cause.

The compiler itself requires Node.js 24 or newer. Source and LLVM output can use Node alone, while executables need a platform linker and SDK. WASI builds need Zig, and explicit C or sanitizer paths need a C compiler.

The full sandbox test path also needs Vercel project access through OIDC or access-token credentials. Rebuilding native helpers requires CMake, Ninja, and the pinned LLVM 22 development package. The repository is a 2,908-file monorepo with no Dockerfile.

ScriptC removes Node only when your code fits its compiler

ScriptC takes TypeScript or JavaScript through typed intermediate representation and can emit readable C, LLVM IR, assembly, object files, executables, or WebAssembly. A static executable includes a small native runtime without Node or a JavaScript engine. That is the interesting part: a command-line tool can keep TypeScript as its source language while shipping a native artifact rather than a Node installation plus node_modules.

Static compilation is conditional, not automatic. The scriptc coverage command reports which statements compile statically and gives coded diagnostics for the remainder. Passing --dynamic embeds QuickJS for npm packages and any-typed code that need JavaScript behavior. The executable then avoids reading node_modules at runtime, but it no longer has the same engine-free shape as a fully static build.

The 13-second build passed, while the test gate exceeded 900 seconds

Our run at commit fc2569e installed 407 pnpm packages in 10 seconds and occupied 292 MB on disk. The monorepo build succeeded in another 13 seconds. The checkout contained 2,908 files and about 429,956 lines of source across 40.9 MB, so the quick build result is encouraging for contributors working on a sizeable compiler codebase.

Tests did not complete before our 900-second limit. The final log printed context canceled 12 times, with no assertion, test name, or stack trace that established a cause. We can report the timeout, but we cannot turn that tail into a diagnosis. The repository has a tests directory and 2 CI workflow files, yet a clean 3-CPU, 8 GB sandbox did not give us a finished local gate.

What happened when we ran it

The install and build completed in 23 seconds combined on our box: 10 seconds for 407 packages, then 13 seconds for the build. No Dockerfile was present. ScriptC uses pnpm workspaces, and the ordinary workspace build does not require a local LLVM installation, which keeps the first contributor step much lighter than rebuilding its native helper stack.

The test outcome is the constraint. After 900 seconds, our harness stopped the command and recorded a timeout. Its last 12 lines all said context canceled. That wording could come from several layers, so assigning blame to Vercel Sandbox, a particular test, or the compiler would exceed the log. A team evaluating ScriptC should split the local test commands and preserve per-suite output before setting a production CI deadline.

Native output has several different toolchain boundaries

Node.js 24 or newer is required to run the compiler. Emitting IR, C, or LLVM needs only Node, while assembly and object output can use optional platform helpers installed with ScriptC. Ordinary LLVM-tier executables still require a linker driver and platform SDK. Explicit C builds, sanitizer work, and fallback routes add a C compiler to the setup.

WebAssembly uses Zig and targets WASI Preview 1. The README names unsupported portable capabilities such as network sockets, fetch, child processes, OS signals, and file watching, which fail before linking with diagnostic SC3002. That boundary is preferable to a mysterious runtime failure. It also means a server, subprocess manager, or file-watching tool is a poor first candidate for the WASI route.

JavaScript compatibility still needs an application corpus

The project calls itself experimental, and current issues show why that label matters. Issue 31 reports that an out-of-bounds array access can abort with a RangeError where Node returns undefined. Issue 238 reports rejected decorator syntax, blocking the documented NestJS example. Issue 432 describes an AbortSignal field causing unrelated method calls to be refused in a dynamic build. These are ordinary language and framework shapes, not obscure benchmark tricks.

A compiler diagnostic is the safer failure mode because it stops the build. Semantic differences that compile and then behave unlike Node demand stronger tests. Run the same input under Node and the generated artifact, then compare stdout, stderr, exit codes, files, and network behavior. ScriptC's full corpus already compares several of those outputs byte for byte. Your application-specific cases still belong beside it.

Debugging and embedding remain specialist work

Open issue 461 reports that Xcode breakpoints are disabled because the generated binary lacks the expected DWARF metadata. Issue 260 explains a separate embedding constraint: a host that owns the main thread can prevent ScriptC's event loop from making progress. If your use case involves native callbacks, a GUI loop, or a library loaded by another process, prove that control flow before adopting the compiler.

Rebuilding native helpers is also a different job from installing the CLI. It requires CMake, Ninja, and the pinned LLVM 22 development package on each target host. The managed sandbox test route needs Vercel authentication and installs a pinned Node, pnpm, and LLVM toolchain in disposable environments. Those facilities are useful for compiler maintainers, though most application teams should consume published helpers first.

v0.1.5 is moving quickly enough to retest often

GitHub showed 5,112 stars, 62 combined open issues and pull requests, and a last push on September 26, 2026. Release v0.1.5 arrived the same day with wider static HTTP support, more numeric APIs, Effect package compilation, and fixes for dynamic islands. That pace says the project is active. It also means a compatibility judgment made against fc2569e can age quickly.

ScriptC is worth trying when native output is itself the requirement and you can choose a contained program for the experiment. Its 23-second install-and-build result lowered the trial cost, while the 900-second unfinished test run raised the cost of treating the repository as settled infrastructure. Start with one utility, record its static coverage, and keep Node as the behavior reference until the generated binary earns independence.

Alternatives

ProjectWhat it isPick it when
Bun gh↗A JavaScript runtime and toolkit that can also produce standalone executables.pick this instead when broad runtime compatibility and an established all-in-one toolchain matter more than static native compilation.
Deno gh↗A TypeScript and JavaScript runtime with a command for creating executables.pick this instead when you want a maintained runtime, permissions model, and executable packaging in one tool.
NexePackages Node.js applications into single executable files.pick this instead when compatibility with an existing Node application matters more than removing the JavaScript engine.

What people are saying

  1. [github-trending] vercel-labs/scriptc

Sources

  1. ScriptC repository and README
  2. ScriptC v0.1.5 release
  3. Out-of-bounds array behavior report
  4. Decorator support report
  5. Xcode breakpoint debugging report
  6. Dynamic AbortSignal compatibility report

More dev tools reviews

terminal-browser · fearless_simd · devops-exercises · 30-seconds-of-code · styleguide · just · the whole board →