News & Updates

Technical insights and announcements from the Pext team.

Architecture

Design notes: an async/await SAPI, driven by closed-world control-flow colouring

Design notes on a Pext SAPI built around async/await. Under closedWorld the transpiler ingests the entire source set and colours the control flow, propagating I/O calls up through the call graph to the top-level web handlers. Async execution comes out of a single conversion, no post-processing. Caveats: autoloaders, magic methods, and destructors all fire at arbitrary points and cannot await.

Architecture

Leaving PHP, Part 10: the strategic question, not the technical one

Series finale of the ten-part Leaving PHP series. Every prior post was tactical. Step back and the real question is strategic: for a decade-scale platform bet, where will the talent, the libraries, the integrations, and the AI tooling be in 2030? PHP will not disappear, but "will not disappear" is a low bar for a technology bet, and the ecosystem momentum is elsewhere.

Weekly

Week in review: 22 June 2026

A recap of the week of 22 June: an arrays refactor bringing Pext closer to the packed-array shape used by PHP internally, static scope emission with vanilla let bindings when the semantics allow it, and a best-effort tokenizer that lets opensourcepos convert with byte-for-byte token parity against PHP.

Feature

Pext cluster mode: a drop-in replacement for php-fpm behind Apache

How Pext uses Node cluster mode to reproduce the php-fpm request lifecycle: a master process bound to the FastCGI socket, a pool of workers, requests dispatched to the pool by Apache mod_proxy_fcgi. The result is a runtime that slots in where php-fpm used to sit, with .htaccess and every existing Apache configuration untouched.

Architecture

Leaving PHP, Part 9: rewriting incrementally is now realistic

Part 9 of the ten-part Leaving PHP series. The old argument against leaving PHP was that a rewrite is impossibly expensive. Big-bang rewrites are still bad, but the option set has widened: strangler-fig behind a shared gateway, file-by-file transpilation with a compatibility runtime, and hot-path extraction. Migration is no longer a binary, and most of the gradient is cheaper than it looks.

Weekly

Week in review: 15 June 2026

A recap of the week of 15 June: NanoCMS moving from PHP 7 to PHP 8 and running under Apache in pext, a streamlined WASM pipeline for PHP C dependencies like PCRE and LibXML that avoids the pain of porting Node bindings across versions, and ten end-to-end REST scenarios for opensourcepos cross-checked between PHP and Pext.

Architecture

Leaving PHP, Part 8: the tooling exists, but it is not the default experience

Part 8 of the ten-part Leaving PHP series. PHPStan, PHP-CS-Fixer, Pest, Psalm, and PHPUnit are all excellent. Vite, Cargo, and go fmt are also excellent, and one command wires them into your project. In PHP the assembly is your problem, and that assembly is a daily tax for onboarding, for greenfield projects, and for anyone who would rather focus on the product than on the toolchain.

Feature

Auditing namespaces in pext: a partial overhaul of the slot-based hierarchy

How pext models PHP namespaces as a runtime map of slots instead of relocating files under PSR-4, and the partial overhaul that landed this week: case-insensitive lookups, kind-aware resolution between functions, classes and constants of the same name, canonical FQN preservation through use-aliases, namespace-versus-class disambiguation, and a faster cold path for use-heavy scripts.

Case Study

Transpiling voku/portable-ascii: a transliteration story, with no ICU on the JS side

voku/portable-ascii is at 100%, but the interesting story is transliteration. PHP leans on ICU through the Transliterator class, and ICU has no clean equivalent in JavaScript. A survey of the landscape (the transliteration npm package, Node's embedded ICU, unicode-org/icu4x, the deprecated icu-transliterator binding), why stable Pext ships a patched transliteration package, and why a custom ICU4x WASM build stays reserved for enterprise.

Weekly

Week in review: 8 June 2026

A recap of the week of 8 June: a new analyze step that statically infers what each function does with its variables, grab-bag locals lowered to plain JS bindings when nothing needs the dynamic scoping, an optimized $this emission backed by its invariants, and the converted PHPUnit suite running in about half the time it did last week.

Feature

pext-vanillify: AI post-processing for non-canonical JS patterns

pext-vanillify is an opt-in AI-driven pass that runs after the deterministic transpiler and rewrites non-idiomatic JS patterns into shapes a JS engineer would have written. First two skills: detokenizing Kint's caller introspection into named parameters, and replacing CodeIgniter 4's class-from-file resolution with a PSR-4-backed lookup.

Architecture

Leaving PHP, Part 7: the shared-hosting mental model still leaks into the language

Part 7 of the ten-part Leaving PHP series. PHP grew up on cPanel and the defaults still encode that world: superglobals, .htaccess, php.ini, mod_php. Containers, serverless, and edge runtimes are the 2026 deployment story, and every PHP target there is an adapter project working around the language's assumptions.

Weekly

Week in review: 1 June 2026

A recap of the week of 1 June: a second framework roadmap for CodeIgniter 4 alongside Laravel, new runtime modules for password, hash, sessions, and MySQL, continued work on the embedded -S server and ini parameter handling, a full audit of how each PHP type is represented in JS, and the removal of Rector as a pre-processing step.

Feature

CodeIgniter 4 joins the roadmap: password, hash, sessions, MySQL, and an opensourcepos POC

CodeIgniter 4 is now a side roadmap running alongside Laravel. New runtime support for password, hash, sessions, and a working MySQL client, the framework boots (autoloader, configuration, CLI commands), and a POC against opensourcepos boots the application and runs login and logout end to end.

Architecture

Leaving PHP, Part 6: async, concurrency, and streaming are still awkward

Part 6 of the ten-part Leaving PHP series. Fibers landed in 8.1, Swoole and ReactPHP and AmPHP exist, and yet writing async PHP in 2026 still puts you on a side path. The libraries, the frameworks, and the team mental model all assume the request-response shape.

Weekly

Week in review: 25 May 2026

A recap of the week of 25 May: multiple new SAPIs including the embedded -S server, a TypeScript port of the bootstrap module that mirrors PHP for extension loading and ini reading, and the centralized in-memory storage that separates per-request execution contexts.

Architecture

Leaving PHP, Part 5: frontend-backend type sharing is a different sport now

Part 5 of the ten-part Leaving PHP series. In a TypeScript-everywhere stack the type of an API response is one source of truth, consumed by server and client. PHP plus JavaScript leaves you with two type systems that do not talk, and the productivity gap is now too large to ignore.

Feature

Phase 2 complete: every Laravel utility package at 100%, and five new runtime modules to get there

Phase 2 of the Laravel roadmap closes with a 100% pass rate on every utility package. Five new runtime modules landed alongside it (ctype, filter, intl, mbstring, sessions), and the roadmap deliberately deviates to cross-check against PhpSpreadsheet and CodeIgniter 4 before continuing.

Weekly

Week in review: 18 May 2026

A recap of the week of 18 May: opening transpilation of PhpSpreadsheet and its test suite, an initial conversion of CodeIgniter 4, multi-process testing finished for nette/schema and nette/utils, and a transpiler-side cleanup pass that trims superfluous emitted JavaScript.

Architecture

How Pext handles HTTP requests: the same model as PHP, with a path out

A walk through the Pext request lifecycle: shared-nothing bootstrap on par with PHP, drop-in replacement for the PHP CLI, separated centralized storage that opens the door to async and threaded SAPIs, and transpile-time inference for the I/O calls that would need refactoring to take advantage of them.

Architecture

Leaving PHP, Part 4: the package ecosystem is fine, the gravity is elsewhere

Part 4 of the ten-part Leaving PHP series. Composer works, Packagist works, Laravel and Symfony are mature. None of that is the problem. The problem is that the cutting edge of every new category ships JavaScript and Python first, and PHP fifth, late, or never.

Weekly

Week in review: 11 May 2026

A recap of the week of 11 May: cron-expression at 100%, magic-method fixes for __call and __invoke, by-ref and copy-on-write across call boundaries, dynamic member syntax, a new pext CLI with a pext.ini equivalent, a TypeScript pipeline finished end-to-end, native new for static instantiation, plus variadic coercion, call_user_func by-ref, and grouped use.

Case Study

Transpiling dragonmantank/cron-expression: timezones, DST, PHP date formats, and a cache for Intl.DateTimeFormat

How Pext brought dragonmantank/cron-expression to 100%. The work was almost entirely in the datetime module: timezone arithmetic, DST transitions, the add/sub/diff family, the long tail of PHP-specific date format characters, and a cache for Intl.DateTimeFormat that turned a slow run into a reasonable one.

Architecture

Leaving PHP, Part 3: the type system arrived late and incomplete

Part 3 of the ten-part Leaving PHP series. A decade of incremental type-system additions (7.0 through 8.4), still no generics in the language, and the refactoring confidence gap that hits hardest on a 200,000-line codebase compared to TypeScript, Kotlin, and Python with Pyright.

Case Study

Transpiling egulias/email-validator: a multibyte string module, DNS, and the road to 100%

How Pext reached 100% on egulias/email-validator: a new pext-multibyte-string module covering the mb_* family, a pext-network module for DNS lookups, the codepoint-vs-byte fixes the parser needed, and the CRLF handling that closed the folded-header tests.

Weekly

Week in review: 04 May 2026

A recap of the week of 04 May: a partial audit of the arrays module, doctrine/lexer at 100%, egulias/email-validator at 92% on the back of two new runtime modules (pext-network, pext-multibyte-string), hamcrest-php at 90%, myclabs/deep-copy at 83% with a full clone implementation, and datetime improvements driven by cron-expression.

Case Study

Transpiling composer/semver: PHPUnit 9 via Symfony symlink and eval-generated version_compare

How Pext reached 100% on the composer/semver test suite. Two hurdles that had nothing to do with the library itself: a PHPUnit 9 binary bootstrapped through a Symfony symlink, and dozens of eval calls that generate version_compare code which had to see the caller scope.

Architecture

Leaving PHP, Part 2: the runtime model is from a different era

Part 2 of the ten-part Leaving PHP series. The architectural cost of shared-nothing in 2026: a 10–30× throughput gap on TechEmpower, the connection-pool math that hits Postgres ten times harder than Node, and what you give up when you reach for Swoole, RoadRunner, or FrankenPHP.

Weekly

Week in review: 27 Apr 2026

A recap of the week of 27 April: a complete audit of the math module against every PHP version since 4, composer/semver and doctrine/inflector at 100%, a deep analysis of string literal encodings, experimental TypeScript output, and initial support for static variables inside functions.

Feature

Auditing the math module to full PHP parity

How Pext brought the math module to full PHP parity: dual test suites, version-aware ValueError throwing, operators that branch on PHP_INT_SIZE at runtime, the C99 corner cases in pow, comparable-aware max/min, operator-overridable pow, dual rounding mode acceptance, and inlining as the next step.

Architecture

Leaving PHP, Part 1: the talent pool is shrinking, and the numbers are worse than you think

Part 1 of a ten-part series on why teams are leaving PHP in 2026. A data-driven look at the talent market: a ~40% relative drop in seven years, an aging bench, only 15.2% of new programmers picking PHP first, and a salary curve that punishes hiring at the wrong end.

Weekly

Week in review: 20 Apr 2026

A recap of the week of 20 April: brick/math at 100%, bcmath support, numeric conversion and coercion finalized, PCRE comprehensively tested, the Laravel roadmap published, and the Foundations phase complete.

Case Study

Transpiling brick/math: the road to 100%

How Pext reached 100% on the brick/math test suite: keeping PHP int and float distinct in JavaScript, fixing static $var, handling overflow, tuning preg_match flags, scope resolution, and operator coercion.

Architecture

Pext vs AI conversion vs manual rewrite

An honest comparison of the three ways to move a PHP codebase to Node.js. Speed, cost, risk, lock-in, and the transition problem that neither AI nor manual rewrites acknowledge.

Weekly

Week in review: 13 Apr 2026

A recap of the week of 13 April: exporter at 92.5%, operator and type coercion improvements, math module testing, X account launch, blog filtering, and program execution support.

Case Study

Transpiling sebastian/exporter: What it took to get to 92.5%

sebastian/exporter is small but technically demanding. A look at the three challenges it posed for Pext: destructor timing, object-to-array casting, and property visibility.

Architecture

Mitigating runtime lock-in

An honest look at how Pext's modular runtime, inspectable output, escrow licensing, and two-phase roadmap are designed to de-risk migration, not trap you in a new ecosystem.

Weekly

Week in review: 06 Apr 2026

A recap of the week of 6 April: website launch, refcounting destructors, sebastian/exporter at 82%, reflection line numbers, and comment-attribute preprocessing.

Case Study

Converting PHPUnit to JavaScript with Pext

A deep dive into transpiling PHPUnit: 54k lines, 4,500+ tests, and one of the most demanding codebases in the PHP ecosystem.

Announcement

Introducing pext.dev

The Pext presentation website goes public. A look at what we built, what it does, and where we go from here.