The End of the Runtime: How Perry is Revolutionizing TypeScript
Perry is a revolutionary Ahead-of-Time (AOT) compiler that translates TypeScript directly into standalone, platform-native machine code. By utilizing SWC for fast abstract syntax tree (AST) parsing and LLVM for optimal code generation, it entirely bypasses the need for heavy intermediate environments like Node.js, V8, or Electron.
Here is a comprehensive summary of its core features and capabilities based on the sources:
- Unmatched Performance and Memory Efficiency: By eliminating the Just-In-Time (JIT) compilation and heavy runtime engines, Perry produces compact binaries that are typically between 2 to 5 MB. Cold startup times drop to approximately 1 millisecond. It manages memory via a custom generational mark-sweep garbage collector, and leverages NaN-boxing to preserve TypeScript’s dynamic typing with minimal footprint.
- True Native Cross-Platform UIs: Unlike React Native (which uses a JavaScript bridge) or Flutter (which uses a custom Skia renderer), Perry compiles declarative TypeScript state management directly to real host OS widgets. One codebase can target AppKit on macOS, UIKit on iOS, GTK4 on Linux, Win32 on Windows, and even WebAssembly/DOM for the web.
- Real OS Concurrency: Perry ditches standard web workers in favor of true, compile-time-safe OS threads. Variables cross thread boundaries via deep-copy, and the compiler prevents data races by strictly rejecting mutable captures.
- Security and Supply-Chain Hardening: The compiler introduces powerful static security guarantees. It blocks dynamic standard library dispatch (e.g., fs[methodName]()) at compile-time to prevent common obfuscation techniques used in malicious npm packages. Additionally, it enforces a strict compile-time URL/host egress allowlist, meaning any non-literal network request will fail the build without explicit host-app opt-in.
- Ecosystem and npm Compatibility: Perry features a high-performance standard library written natively in Rust, which includes drop-in replacements for over 30 popular npm packages like database drivers (Postgres, MySQL, MongoDB), encryption, and HTTP servers. If a legacy JavaScript package is required, developers can selectively opt into an embedded QuickJS or V8 runtime environment.
- Automated Distribution: The integrated perry publish tool simplifies deployment by orchestrating cross-platform builds, automatic code signing, and direct App Store or Google Play submission without needing to interact manually with portals.
The End of the Runtime? 5 Surprising Realities of Compiling TypeScript to Native Machine Code
For years, the JavaScript ecosystem has been defined by a fundamental trade-off. We enjoy the world-class ergonomics of TypeScript, but we pay for it with the “Electron hangover”—bloated binaries, high memory consumption, and the persistent overhead of the V8 runtime. The dream has always been “true” native: the ability to write TypeScript but ship a standalone executable that runs with the efficiency of C++ or Rust.Enter Perry , a native TypeScript compiler written in Rust. By utilizing SWC for parsing and LLVM for ahead-of-time (AOT) code generation, Perry attempts to collapse the boundary between high-level web development and low-level systems engineering. Can we actually have the best of both worlds? Based on Perry’s recent development milestones and performance audits, here are five surprising realities of a native TypeScript future.
1. Your TypeScript is Actually Competitive with C++
The most persistent myth in web development is that JavaScript is inherently slow due to its dynamic nature. While JIT (Just-In-Time) compilation in Node.js and Bun is impressively fast, it still suffers from “warm-up” periods and runtime overhead. Perry bypasses this by compiling directly to native machine code via LLVM, moving us from the world of managed runtimes to the world of specialized executables.In specific benchmarks, Perry achieves performance parity with C++ through two critical architectural optimizations. First, it uses i64 specialization for pure numeric functions. While standard JS engines treat numbers as f64 values, Perry’s static analysis allows it to refine TypeScript “number” parameters into native 64-bit integer registers.Second, Perry implements an Integer-Modulo Fast Path . Standard JS engines must call the Floating Point Unit (FPU) to handle modulus operations via fmod. Perry, however, can prove when a variable is an integer and swap these costly IEEE-754 instructions for the CPU’s native srem (signed remainder) instruction in the Integer ALU. Combined with Scalar Replacement —which uses escape analysis to decompose non-escaping objects into stack registers, effectively “deleting” the heap—the results speak for themselves.
Polyglot Benchmark Results (Median Wall-Clock ms)
Benchmark,Perry (v0.5.908),Node.js,Rust,C++
fibonacci,309,987,316,309
array_write,3,9,7,2
json_roundtrip,83,377,-,-
Note: Data based on v0.5.908 sweep on macOS ARM64 (M1 Max). json_roundtrip reflects a 50x operation on a 1MB blob.
2. The “V8 Safety Net”—A Bridging Strategy for a Native-First World
The primary criticism of any AOT compiler for TypeScript is the “NPM problem.” The ecosystem is massive, and much of it relies on dynamic JavaScript patterns or internal Node.js APIs that defy static compilation.Perry addresses this with a hybrid bridging strategy. It natively implements high-performance Rust versions of critical libraries—such as fastify, mysql2, ioredis, and bcrypt—ensuring core infrastructure is fast. For the “long tail” of the ecosystem, Perry can utilize an –enable-js-runtime flag to embed a V8 instance.However, the project’s trajectory is increasingly “V8-free.” Recent updates show the removal of perry-jsruntime from core binaries to achieve the ultra-low footprints mentioned below. As one developer reflected on this transitional phase:”The native compilation gives you performance where it matters, and V8 handles the long tail of the ecosystem. It’s not all-or-nothing.”
3. Native UI Without the WebView “Tax”
Perhaps the most significant departure from the Electron model is how Perry handles user interfaces. Unlike React Native—which uses a bridge to serialize data between a JS engine and native widgets—Perry compiles the UI logic into the same machine code that drives the platform widgets. By removing the “Bridge Serializer” bottleneck, Perry eliminates the latency typically associated with cross-platform frameworks.Your TypeScript code generates “real” widgets on the target OS. This approach allows the Mango MongoDB GUI , built with Perry, to run on less than 100MB of RAM with sub-second cold starts—a feat nearly impossible for Electron-based competitors.Perry currently supports 10 target outputs from a single codebase:
- macOS (AppKit)
- iOS / iPadOS (UIKit)
- visionOS (UIKit 2D Windows)
- tvOS (UIKit)
- watchOS (WatchKit)
- Android (Android Views via JNI)
- Windows (Win32)
- Linux (GTK4)
- Web (DOM/JS codegen)
- WebAssembly (WASM)
4. The 330KB “Hello World”—Aggressive Binary Stripping
Shipping a Node.js application typically requires a massive runtime environment and a node_modules folder that can easily reach hundreds of megabytes. Perry reverses this by producing small, self-contained binaries.A basic console.log(“Hello, world!”) compiles to just 330KB . Even an application including standard imports like fs, path, and process stays under 380KB . This is possible because Perry uses aggressive Dead Code Elimination (DCE) and only links what is strictly necessary. Unlike Node.js, there is no hidden 200MB runtime inside your binary; the main/llvm dependency is handled via system linkers on macOS or scoop on Windows, allowing the final output to be truly standalone.
5. The “Vibe-Coding” Velocity—68 Releases in One Week
The development of Perry highlights a new era of “vibe-coding”—a methodology characterized by extreme release frequency and heavy reliance on AI agents like Claude Code. In one particularly intense seven-day period, the project moved from version v0.5.13 to v0.5.80, closing dozens of issues and landing massive features like a mimalloc global allocator.This AI-assisted velocity allowed a solo developer to build a backend for 11 targets in a single year, closing a 547x performance gap for JSON.parse in just one week. However, this has sparked debate within the engineering community. Critics on Hacker News and Reddit have raised concerns over the long-term stability of maintaining millions of lines of AI-generated Rust code. Despite these concerns, the rapid optimization cycle remains Perry’s greatest engine for growth:”JSON.parse closed a 547x gap to Node in one week. Inline caches, shape transitions, and a native event loop land almost as fast as we can benchmark them.”
Conclusion: Is TypeScript the New Systems Language?
The long-term vision for Perry extends beyond simple binaries. The project is already “dogfooding” its own ecosystem by building HONE , an AI-powered native code editor written entirely in TypeScript and compiled with Perry.As compilers become more sophisticated, the boundary between “high-level web languages” and “low-level systems languages” is permanently dissolving. We are moving toward a world where the developer’s choice of language is dictated by ergonomics and safety, not by a performance penalty.If your TypeScript could run with the efficiency of Rust and the portability of C, would you ever write in another language again?

