|
| 1 | +# jsphp (`node-jsphp`) |
| 2 | + |
| 3 | +`jsphp` is a high-performance Node.js runtime, CLI, and transpiler engine for **PHP 8.5** written in TypeScript. It parses PHP code into ASTs, optimizes execution through constant folding and dead-code elimination, and transpiles PHP to asynchronous JavaScript source code with source maps (`.js.map`). |
| 4 | + |
| 5 | +`jsphp` enables running PHP scripts, applications (including full **WordPress** sites), and command-line interfaces directly inside Node.js without needing native PHP binaries or socket connections to PHP-FPM. |
| 6 | + |
| 7 | +--- |
| 8 | + |
| 9 | +## Features |
| 10 | + |
| 11 | +- **PHP 8.5 Support**: Full support for PHP 8.5 language constructs, functions, and standard library. |
| 12 | +- **Asynchronous Execution Model**: All transpiled JavaScript code runs asynchronously via `async/await`, preventing blocking of Node.js event loop while executing PHP synchronously from PHP's perspective. |
| 13 | +- **Transparent Stack Trace Virtualization**: JavaScript stack traces are filtered and mapped to PHP file and line locations, displaying internal Node.js frames as `[INTERNAL]`. |
| 14 | +- **AST Optimization**: Precalculates constants, eliminates unreachable branches (`if(false)`, `if(extension_loaded(...))`, `defined(...)`), and folds expressions at compile time. |
| 15 | +- **On-Disk Transpilation Cache**: Saves compiled JavaScript files and sourcemaps to `process.env.JSPHP_CACHE` under `${JSPHP_CACHE}/${EngineConfigSHA1}/${FilePathSHA1}.js`. |
| 16 | +- **Live File Watching**: Uses `chokidar` to automatically invalidate and recompile cached files when PHP source files are updated. |
| 17 | +- **Built-in PHP Extensions**: Full implementations of `mysqli` (via `mysql2`), `pdo`, `pdo_mysql`, `gd` (via `sharp`), `pcre`, `mbstring`, `json`, `curl`, `session`, `xml`, `spl`, `hash`, `openssl`, and more. |
| 18 | +- **CLI & REPL**: `php` CLI tool supporting `-v`, `-r <code>`, `-a` interactive shell, and script execution. |
| 19 | + |
| 20 | +--- |
| 21 | + |
| 22 | +## Installation |
| 23 | + |
| 24 | +```bash |
| 25 | +npm install jsphp |
| 26 | +``` |
| 27 | + |
| 28 | +--- |
| 29 | + |
| 30 | +## Usage |
| 31 | + |
| 32 | +### 1. Basic PHP Code Execution |
| 33 | + |
| 34 | +```typescript |
| 35 | +import { PHPEngine } from "jsphp"; |
| 36 | + |
| 37 | +async function main() { |
| 38 | + const engine = new PHPEngine(); |
| 39 | + const ctx = engine.createContext({ |
| 40 | + stdout: (data) => process.stdout.write(data), |
| 41 | + }); |
| 42 | + |
| 43 | + await ctx.eval(` |
| 44 | + <?php |
| 45 | + $name = "JSPHP"; |
| 46 | + echo "Hello, " . $name . "!\n"; |
| 47 | + `); |
| 48 | + |
| 49 | + engine.close(); |
| 50 | +} |
| 51 | + |
| 52 | +main(); |
| 53 | +``` |
| 54 | + |
| 55 | +### 2. Running a PHP File |
| 56 | + |
| 57 | +```typescript |
| 58 | +import { PHPContext } from "jsphp"; |
| 59 | + |
| 60 | +async function run() { |
| 61 | + await PHPContext.runFile("./index.php", { |
| 62 | + stdout: (data) => process.stdout.write(data), |
| 63 | + }); |
| 64 | +} |
| 65 | + |
| 66 | +run(); |
| 67 | +``` |
| 68 | + |
| 69 | +### 3. Command Line Interface (CLI) |
| 70 | + |
| 71 | +```bash |
| 72 | +# Print PHP version |
| 73 | +npx php -v |
| 74 | + |
| 75 | +# Evaluate inline code |
| 76 | +npx php -r "echo 'Hello from CLI!';" |
| 77 | + |
| 78 | +# Interactive REPL shell |
| 79 | +npx php -a |
| 80 | + |
| 81 | +# Run script file |
| 82 | +npx php index.php |
| 83 | +``` |
| 84 | + |
| 85 | +--- |
| 86 | + |
| 87 | +## Architecture & Documentation |
| 88 | + |
| 89 | +Detailed documentation can be found in the `docs/` directory: |
| 90 | +- [docs/architecture.md](docs/architecture.md): Overview of `PHPEngine`, `PHPContext`, and execution model. |
| 91 | +- [docs/transpiler.md](docs/transpiler.md): Details on AST parser, optimizer, sourcemaps, and cache hashing. |
| 92 | +- [docs/extensions.md](docs/extensions.md): Creating custom `PHPExtension` classes and registering functions/classes. |
| 93 | + |
| 94 | +--- |
| 95 | + |
| 96 | +## Running Tests |
| 97 | + |
| 98 | +```bash |
| 99 | +# Run unit tests |
| 100 | +npm test |
| 101 | + |
| 102 | +# Run WordPress integration tests (requires local MySQL instance) |
| 103 | +MYSQL_ROOT_PASSWORD="DNESB*GJ*W(E$GYB$UW#gt78wg" npm test |
| 104 | +``` |
| 105 | + |
| 106 | +--- |
| 107 | + |
| 108 | +## License |
| 109 | + |
| 110 | +[MIT](LICENSE.md) |
0 commit comments