Skip to content

Commit a62e61a

Browse files
ondrejmirtesclaude
andcommitted
Stop building Linux ZTS turbo binaries
Every Linux distro, ppa:ondrej/php, sury, Remi's default php, the official Docker image and setup-php ship an NTS CLI; thread-safe PHP on Linux (FrankenPHP, php:*-zts images) is a few percent of hosts, and under 0.1% of setup-php workflows opt into it. The two Linux ZTS legs cost eight binaries across the four PHP minors. Windows keeps its ZTS build: XAMPP, WampServer and Scoop default to thread-safe PHP. The commit job deletes the retired binaries from phpstan/phpstan (TURBO_RETIRED_BINARIES): a dist still carrying one gets a commit even at an unchanged extension version, and they are removed before the torn-set guard, which would otherwise refuse every version bump over a binary with no freshly built replacement. A thread-safe PHP on Linux now finds no binary and runs without the extension. Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_01Qi7GRGMn9ZuY2jSc97wqBF
1 parent a2f6bd8 commit a62e61a

2 files changed

Lines changed: 43 additions & 30 deletions

File tree

‎.github/workflows/phar.yml‎

Lines changed: 39 additions & 27 deletions
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,11 @@ permissions:
2020
contents: read
2121

2222
env:
23+
# Turbo binaries phpstan/phpstan used to carry but no compile leg builds any
24+
# more (paths under turbo-ext/, shell globs). The commit job deletes them
25+
# from the dist; without this, the torn-set guard there would refuse every
26+
# version bump, since a retired binary has no freshly built replacement.
27+
TURBO_RETIRED_BINARIES: "linux-gnu-x86_64/phpstan_turbo-*-zts.so linux-gnu-arm64/phpstan_turbo-*-zts.so"
2328
# The php-parser version whose grammar tables and semantic actions the
2429
# native parser engine (turbo-ext/src/parser/) was ported against.
2530
SUPPORTED_PHP_PARSER_VERSION: "v5.9.0"
@@ -335,12 +340,13 @@ jobs:
335340
# separate turbo-compile-musl-arm64 job below: JavaScript-based actions
336341
# cannot run in Alpine containers on arm64 runners (the runner only
337342
# ships an x64 musl Node), so that job drives the Alpine container
338-
# through docker exec instead of a `container:` leg. The ZTS legs (for
339-
# hosts with a thread-safe PHP, like PMMP's bundled build) run directly
340-
# on ubuntu-22.04 runners — same glibc floor — because no distro
341-
# packages ZTS PHP (neither ppa:ondrej/php nor Alpine); setup-php
342-
# provides thread-safe builds. No musl ZTS for the same packaging
343-
# reason.
343+
# through docker exec instead of a `container:` leg. There are no Linux
344+
# ZTS legs: every distro, ppa:ondrej/php, sury, Remi's default `php`, the
345+
# official Docker image and setup-php ship an NTS CLI, and thread-safe
346+
# PHP on Linux (FrankenPHP, php:*-zts images) is a few percent of hosts —
347+
# not worth two binaries per PHP minor. Their binaries are deleted from
348+
# phpstan/phpstan by the commit job (TURBO_RETIRED_BINARIES). Windows
349+
# keeps its ZTS leg: XAMPP, WampServer and Scoop default to TS PHP.
344350
# PHP 8.6 has no ondrej/php packages or prebuilt GNU image yet. Use
345351
# setup-php on Jammy runners, preserving the shipped binary's glibc floor.
346352
# Alpine's php86 packages are currently only in edge/testing.
@@ -368,16 +374,6 @@ jobs:
368374
container: "alpine:3.24"
369375
family: "musl"
370376
artifact: "phpstan_turbo"
371-
- name: "linux-gnu-x86_64"
372-
runs-on: "ubuntu-22.04"
373-
family: "zts"
374-
artifact: "phpstan_turbo"
375-
suffix: "-zts"
376-
- name: "linux-gnu-arm64"
377-
runs-on: "ubuntu-22.04-arm"
378-
family: "zts"
379-
artifact: "phpstan_turbo"
380-
suffix: "-zts"
381377
# arm64 (Apple Silicon) only: setup-php dropped Intel macOS. An
382378
# x86_64 PHP — native Intel, or Rosetta on Apple Silicon, which
383379
# reports x86_64 too — finds no binary: TurboExtensionSelector
@@ -437,20 +433,12 @@ jobs:
437433
php-version: "${{ matrix.php-version }}"
438434

439435
- name: "Install PHP (GNU runners)"
440-
if: matrix.target.family == 'zts' || (matrix.target.family == 'gnu' && matrix.php-version == '8.6')
436+
if: matrix.target.family == 'gnu' && matrix.php-version == '8.6'
441437
uses: "shivammathur/setup-php@f3e473d116dcccaddc5834248c87452386958240" # v2.37.2
442-
env:
443-
phpts: "${{ matrix.target.family == 'zts' && 'ts' || 'nts' }}"
444438
with:
445439
coverage: "none"
446440
php-version: "${{ matrix.php-version }}"
447441

448-
# Guards against setup-php silently falling back to an NTS build,
449-
# which would ship an NTS binary under the -zts name.
450-
- name: "Verify the interpreter is thread-safe"
451-
if: matrix.target.family == 'zts'
452-
run: "php -r 'exit((bool) PHP_ZTS ? 0 : 1);'"
453-
454442
- name: "Compile phpstan_turbo with strict warnings"
455443
working-directory: "turbo-ext"
456444
# Exemptions, each caused by third-party macro expansions, not our code:
@@ -493,7 +481,7 @@ jobs:
493481
if: matrix.target.family != 'macos'
494482
# checksum-pinned composer, run under the matrix PHP so platform
495483
# requirements are validated against the interpreter the tests below
496-
# run on. COMPOSER_HOME is isolated: on the runner (ZTS) legs,
484+
# run on. COMPOSER_HOME is isolated: on the runner (PHP 8.6) legs,
497485
# setup-php seeds ~/.composer/auth.json with the workflow's GitHub
498486
# token, which this pinned composer rejects at startup ("github oauth
499487
# token contains invalid characters") — everything here comes from
@@ -533,7 +521,7 @@ jobs:
533521
- name: "Upload extension artifact"
534522
uses: actions/upload-artifact@043fb46d1a93c77aae656e7c1c64a875d1fc6a0a # v7.0.1
535523
with:
536-
name: "${{ matrix.target.artifact }}-${{ matrix.target.name }}-php${{ matrix.php-version }}${{ matrix.target.suffix }}"
524+
name: "${{ matrix.target.artifact }}-${{ matrix.target.name }}-php${{ matrix.php-version }}"
537525
path: "turbo-ext/phpstan_turbo.so"
538526
if-no-files-found: "error"
539527

@@ -1035,6 +1023,10 @@ jobs:
10351023
php-version: ["8.3", "8.4", "8.5", "8.6"]
10361024
ts: ["nts", "zts"]
10371025
script: ["make tests", "make phpstan"]
1026+
# Linux ships no ZTS binary (see turbo-compile); Windows does
1027+
exclude:
1028+
- operating-system: "ubuntu-latest"
1029+
ts: "zts"
10381030
# macOS runs the shipped ad-hoc-signed arm64 binary; there is no
10391031
# macOS zts build, and 8.3/8.4 coverage comes from the other legs.
10401032
include:
@@ -1647,6 +1639,16 @@ jobs:
16471639
fi
16481640
done
16491641
done
1642+
# A retired binary still in the dist needs a commit deleting it,
1643+
# even at an unchanged extension version.
1644+
for pattern in $TURBO_RETIRED_BINARIES; do
1645+
for retired in phpstan-dist/turbo-ext/$pattern; do
1646+
if [[ -f "$retired" ]]; then
1647+
echo "retired, to be deleted from dist: $retired"
1648+
RESULT=different
1649+
fi
1650+
done
1651+
done
16501652
echo "result=$RESULT" >> "$GITHUB_OUTPUT"
16511653
echo "version-changed=$VERSION_CHANGED" >> "$GITHUB_OUTPUT"
16521654
echo "version=$EXPECTED" >> "$GITHUB_OUTPUT"
@@ -1698,6 +1700,16 @@ jobs:
16981700
TURBO_VERSION: ${{ steps.turbo-difference.outputs.version }}
16991701
VERSION_CHANGED: ${{ steps.turbo-difference.outputs.version-changed }}
17001702
run: |
1703+
# Retired targets go first: they have no replacement by design, and
1704+
# a stale one must not keep shipping (`git add .` stages the deletion).
1705+
for pattern in $TURBO_RETIRED_BINARIES; do
1706+
for retired in phpstan-dist/turbo-ext/$pattern; do
1707+
if [[ -f "$retired" ]]; then
1708+
echo "deleting retired binary: $retired"
1709+
rm -f "$retired"
1710+
fi
1711+
done
1712+
done
17011713
# A version bump must refresh EVERY binary the dist carries: staging a
17021714
# partial artifact set and bumping .version anyway would leave the
17031715
# missing platforms on a stale extension the new phar refuses to

‎src/Turbo/TurboExtensionSelector.php‎

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -28,9 +28,10 @@
2828
* installations —
2929
* a source checkout loads its locally built extension through php.ini
3030
* instead. Only non-debug builds for PHP >= MINIMUM_PHP_VERSION_ID are
31-
* shipped; ZTS variants (-zts filename
32-
* suffix) exist for linux-gnu and Windows so hosts with a thread-safe PHP
33-
* (like PMMP's bundled build) are covered too. Workers run the regular
31+
* shipped; a ZTS variant (-zts filename
32+
* suffix) exists for Windows only, where XAMPP, WampServer and Scoop default
33+
* to thread-safe PHP — a thread-safe PHP on Linux or macOS finds no binary
34+
* and runs without the extension. Workers run the regular
3435
* entrypoint, so TurboExtensionEnabler still gates activation on the
3536
* expected extension version.
3637
*

0 commit comments

Comments
 (0)