How to Compile a TypePHP Project to a WASI Component: Complete Guide
TypePHP compiles PHP extensions into portable WebAssembly System Interface (WASI) components by leveraging the TypePhp\Platform\Wasi abstraction, which orchestrates a WASI-compatible C++ toolchain to emit .wasm binaries when invoked via php bin/tpc.php --platform=wasi.
Compiling a TypePHP project to a WASI component allows you to run PHP extensions in any WebAssembly runtime. The swoole/typephp repository provides a dedicated platform abstraction that automates the toolchain selection and code generation required for WASI targets.
Understanding the WASI Platform Architecture
The compilation flow is driven by TypePHP's Platform abstraction. When the WASI platform is selected, the compiler automatically configures a WASI-compatible C++ toolchain.
The Wasi Platform Class
In src/Platform/Wasi.php, the TypePhp\Platform\Wasi class defines the WASI-specific build parameters. It specifies the default target triple as wasm32-unknown-wasip2, sets the output file extension to .wasm, and determines the system compiler. By default, it uses clang++, or the executable path specified in the TYPEPHP_WASI_CXX environment variable.
Platform Resolution
The TypePhp\Platform\PlatformFactory class in src/Platform/PlatformFactory.php resolves the target platform based on command-line flags. When you pass --platform=wasi to the CLI, the factory instantiates the Wasi platform object, ensuring the subsequent compilation steps use the correct WebAssembly-targeting toolchain.
Prerequisites: Installing the WASI SDK
Before compiling, you must install the WASI SDK, which provides the clang++ driver capable of emitting WebAssembly objects.
Download the appropriate release for your architecture from the official WASI SDK repository. For Linux x86_64:
wget https://github.com/WebAssembly/wasi-sdk/releases/download/wasi-sdk-22/wasi-sdk-22.0-x86_64-linux.tar.gz
tar -xzf wasi-sdk-22.0-x86_64-linux.tar.gz
Add the SDK's bin directory to your PATH, or set the TYPEPHP_WASI_CXX environment variable to point directly to the compiler executable.
Step-by-Step: Compile a TypePHP Project to a WASI Component
1. Configure the Compiler Environment
Set the TYPEPHP_WASI_CXX environment variable to specify the WASI-compatible C++ compiler:
export TYPEPHP_WASI_CXX=/path/to/wasi-sdk-22.0/bin/clang++
If this variable is unset, Wasi::getDefaultCompiler() falls back to the system clang++ executable.
2. Run the TypePHP Compiler
Invoke the CLI driver bin/tpc.php with the --platform=wasi flag to trigger the WASI build pipeline:
php bin/tpc.php --platform=wasi --output=example.wasm
The tpc (Type PHP Compiler) entry point in bin/tpc.php parses the --platform (or -p) flag and delegates to the internal compiler. The process executes three phases:
- Translation: Loads PHP source files and converts them into type-checked C++ code via the pipeline in
src/compiler.php. - Compilation: Invokes the WASI C++ compiler with target-specific flags (
-target wasm32-unknown-wasip2,-nostdlib, etc.) to generate object files. - Linking: Produces a static library (
.a) and links it into a single WebAssembly binary (.wasm).
3. Execute the WASI Module
Run the resulting component using any WASI-compatible runtime, such as Wasmtime or Wasmer:
wasmtime example.wasm
The Compilation Pipeline Under the Hood
According to the swoole/typephp source code, the compilation workflow involves four key components:
src/Platform/Wasi.php: Describes the target name (wasm32-unknown-wasip2), file extensions (.wasm), and default compiler (clang++orTYPEPHP_WASI_CXX) for WASI builds.src/Platform/PlatformFactory.php: Chooses the appropriate platform class based on CLI flags like--platform=wasi.bin/tpc.php: Entry-point CLI that accepts the--platformflag and triggers the compiler.src/compiler.php: Core compilation logic that generates C++ and invokes the selected toolchain to produce the final artifact.
Summary
- TypePHP supports WASI compilation through the
TypePhp\Platform\Wasiabstraction defined insrc/Platform/Wasi.php. - Set
TYPEPHP_WASI_CXXto point to your WASI SDKclang++binary, or ensureclang++is in yourPATH. - Use
--platform=wasiwithbin/tpc.phpto trigger the WebAssembly build pipeline targetingwasm32-unknown-wasip2. - The compilation process generates C++ code, compiles it to WebAssembly objects, and links them into a
.wasmartifact. - Run compiled components in any WASI-compatible runtime like
wasmtime.
Frequently Asked Questions
What is the default target triple for TypePHP WASI builds?
The TypePhp\Platform\Wasi class defaults to the wasm32-unknown-wasip2 target triple, as defined in src/Platform/Wasi.php. This targets the 32-bit WebAssembly System Interface preview 2 specification, ensuring compatibility with modern WASI runtimes.
Can I use a custom C++ compiler for WASI compilation?
Yes. While TypePHP defaults to clang++, you can override the compiler by setting the TYPEPHP_WASI_CXX environment variable to the full path of your WASI-compatible C++ driver. The Wasi::getDefaultCompiler() method checks this variable before falling back to the system default.
How does the PlatformFactory determine which platform to use?
The TypePhp\Platform\PlatformFactory class in src/Platform/PlatformFactory.php inspects command-line flags and environment variables. When you pass --platform=wasi (or -p wasi) to bin/tpc.php, the factory instantiates the Wasi platform class, configuring the compiler to emit WebAssembly instead of native machine code.
How do I execute the compiled WASI component?
You can run the resulting .wasm file using any WASI-compliant runtime. The most common options are Wasmtime (wasmtime example.wasm) and Wasmer (wasmer run example.wasm). These runtimes provide the system interfaces that the WASI component expects.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →