Metadata-Version: 2.4
Name: static-php-build
Version: 0.1.5
Summary: Independent build tool producing a host PHP binary via static-php-cli
License-Expression: GPL-2.0
License-File: LICENSE
License-File: php-3.01.txt
License-File: static-php-cli.txt
Classifier: Development Status :: 3 - Alpha
Classifier: Intended Audience :: Developers
Classifier: License :: OSI Approved :: GNU General Public License v2 (GPLv2)
Classifier: Programming Language :: Python :: 3
Classifier: Topic :: Software Development :: Build Tools
Requires-Python: >=3.9
Requires-Dist: platformdirs>=4.4.0
Project-URL: Homepage, https://github.com/samhsu-dev/static-php-py
Project-URL: Repository, https://github.com/samhsu-dev/static-php-py
Description-Content-Type: text/markdown

# static-php-build

> Bake the PHP extensions you need into a portable host binary, once, at packaging time.

Produce a host PHP binary loading a required extension set by driving [static-php-cli](https://github.com/crazywhalecc/static-php-cli) (spc).

## Install

```bash
pip install static-php-build
```

A build-time / development dependency, not a runtime dependency of a consumer's end users. spc compilers are bundled per host platform; hosts without a bundled spc supply one via `--spc PATH`.

## Usage

```bash
# Build a host PHP binary loading the given extensions, write it to ./php
static-php-build --extensions tokenizer,mbstring --out ./php

# Read the required set from the consumer's requirement declaration instead
static-php-build --manifest your_lib:REQUIREMENTS --out ./php

# Pin the PHP version, and forward unmodeled spc options after the `--` separator
static-php-build --extensions tokenizer --out ./php --with-php 8.4 -- --enable-zts

# Use an explicit spc on a host without a bundled one
static-php-build --extensions tokenizer --spc /path/to/spc --out ./php
```

```python
from static_php_build import BuildRequest, build

report = build(BuildRequest(extensions=["tokenizer", "mbstring"], out="./php"))
print(report.satisfied, report.missing)
```

Each invocation builds for the host it runs on, so cross-OS coverage means one CI job per OS. A minimal GitHub Actions matrix:

```yaml
jobs:
  build-php:
    strategy:
      matrix:
        os: [ubuntu-latest, macos-latest, windows-latest]
    runs-on: ${{ matrix.os }}
    steps:
      - run: pipx run static-php-build --extensions tokenizer,mbstring --with-php 8.4 --out dist/php
      - uses: actions/upload-artifact@v4
        with:
          name: php-${{ matrix.os }}
          path: dist/php*
```

The tool verifies each produced binary via its own `php -m` read; a non-CLI artifact fails verification and raises. The handoff to `static-php-py` is the produced binary on disk, loaded at runtime through `PHP.local`. Full workflow (bundling the artifacts into per-OS wheels): [`../../docs/llms/bundling-pipeline.md`](../../docs/llms/bundling-pipeline.md).

## API

### Command

`static-php-build (--extensions NAMES | --manifest MODULE:ATTR) [--out PATH] [--spc PATH] [--with-php VERSION] [-- <spc args>]`

- `--extensions` — the required set as comma-separated extension names.
- `--manifest` — `MODULE:ATTR` naming an importable object exposing `extensions` (a consumer's `Requirements` constant); exactly one of `--extensions` and `--manifest` is required.
- `--out` — file path receives the binary; directory path receives `php`/`php.exe` inside it. Omitted: `./php` (`./php.exe` on Windows).
- `--spc` — explicit spc binary; supersedes the bundled spc for the run.
- `--with-php` — major.minor PHP version pinned on spc's download step. Omitted: spc default.
- `-- <spc args>` — forwarded to spc's build step verbatim; the tool's own flags are never forwarded.
- Exit codes: `0` success, `1` runtime failure (`BuildError`), `2` misuse (no extension set resolvable).

### Function

`build(request: BuildRequest | None = None) -> ExtensionReport`

Produces a host binary loading the required extensions, verifies it, writes it to the destination, and returns the report.

- `BuildRequest` — frozen data holder grouping the build inputs: `extensions`, `manifest`, `out`, `spc`, `php_version`, `spc_args`, `timeout`. Exactly one of `extensions` and `manifest` names the required set.
- `ExtensionReport` — frozen data holder: `required`, `loaded`, `missing`, `satisfied`.

### Exceptions

- `BuildError` — base (distinct from `static-php-py`'s `PHPError`).
- `ProvisioningError` — spc download/build failed, output binary absent, or a required extension is missing.
- `UnsupportedHostError` — no bundled spc for the host and no `--spc` supplied; names `--spc` as the remedy.

Full design: [`docs/design.md`](docs/design.md). Concepts: [`docs/concept.md`](docs/concept.md). Doc index: [`docs/index.md`](docs/index.md).

## For Agents

Agent-consumable documentation index at [`../../docs/llms.txt`](../../docs/llms.txt) (llmstxt.org format).

## Citation

If you use this project in academic work, cite our paper. BibTeX (placeholder until the paper is released):

```bibtex
@misc{static_php_py_placeholder,
  title  = {{TODO: paper title — not yet released}},
  author = {{TODO: authors}},
  year   = {{TODO}},
  note   = {Paper not yet released. Citation entry will be updated on publication.}
}
```

## License

GPL-2.0 — see [LICENSE](LICENSE). Built binaries are produced by [static-php-cli](https://github.com/crazywhalecc/static-php-cli).
