Skip to content

release(http): 0.1.0-beta7 — trusted-proxy client IP, upload-root race fix - #28

Merged
supa-chayajin merged 9 commits into
mainfrom
pre-release/0.1.0-beta7
Nov 5, 2026
Merged

supa-chayajin merged 9 commits into
mainfrom
pre-release/0.1.0-beta7

Conversation

@supa-chayajin

Copy link
Copy Markdown
Member

Summary

What http ships in 0.1.0-beta7: 8 commits ahead of main.

Theme: the client address behind trusted proxies.

Added

  • ClientIp\TrustedProxyClientIpResolver (NET-01) — implements ClientIpResolverInterface: X-Forwarded-For is read only when REMOTE_ADDR is an allow-listed proxy (addresses or CIDR ranges, IPv4 and IPv6), right to left, and the first hop that is not a trusted proxy is the client; a client-prepended hop cannot win, and a malformed hop falls back to REMOTE_ADDR.

Fixed

  • GlobalsFactory no longer emits mkdir(): File exists when workers that boot together race to create the upload root, a warning the EcoShield Gateway logged at every worker start. The creation runs under a scoped error handler (no @ operator), and the is_dir() re-check still throws when the directory really cannot be created.

Dependency refresh (2026-11-02)

 composer.json (require-dev)
-  "carthage-software/mago": "^1.50"
+  "carthage-software/mago": "^1.59"
-  "vimeo/psalm": "^6.19"
+  "vimeo/psalm": "^6.20"
-  "php-mock/php-mock-phpunit": "^2.15"
+  "php-mock/php-mock-phpunit": "^2.16"
-  "igor-php/igor-php": "^0.9.7"
+  "igor-php/igor-php": "^0.10.1"
 .github/workflows/main.yml
-  IGOR_VERSION: '0.9.7'
+  IGOR_VERSION: '0.10.1'
-  uses: trufflesecurity/trufflehog@v3.97.9
+  uses: trufflesecurity/trufflehog@v3.99.7

Related issues

No open Dependabot PR in this repository.
Roadmap: Roadmap_Beta7.md.

Evidence

Before: main = 0.1.0-beta6 toolchain (mago 1.50, igor-php 0.9.7).
After: wfl pre-release http on this branch, 2026-11-03:

✓ mago clean (zero diagnostics)
✓ tests green
✓ coverage 96.55% (≥ 95%, floor 96.55%)
✓ igor 0 KO
✓ composer audit: no advisories on the locked dependencies
✓ DoD PASS — http
✓   DoD passed
✓   README stamped 0.1.0-beta7
✓   CHANGELOG has a [0.1.0-beta7] entry
✓   paperwork ready
✓   SBOM written: tmp/sbom/http-0.1.0-beta7.cdx.json

psalm --taint-analysis 6.20: no errors (2026-11-02).

Checklist

  • Coding standards and static analysis: composer mago zero output (fmt, lint, analyze, guard); no baseline.
  • Tests: composer tests a clean OK; coverage ≥ 95 % and at or above the component's floor.
  • FrankenPHP statelessness: composer igor 0 KO.
  • Contracts-only dependencies: the mago guard perimeter holds.
  • Documentation: README stamped 0.1.0-beta7; CHANGELOG.md has the entry.

Merge Danger

Door: two-way until the 0.1.0-beta7 tag (a revert undoes the merge), one-way after: the tag publishes
to Packagist.

Once 0.1.0-beta7 is tagged, Packagist serves this main to every consumer. Merge with a merge commit, never a squash: a squash orphans the commit the umbrella pins and the
wave exits 3.

Blast Radius: release

CI before the release-day relock. composer.lock pins waffle-commons/contracts (and utils) at their
current main, the beta6 code, until those PRs merge and the locks are refreshed. A CI job that loads a beta7
contract fails until then; the gates under Evidence ran locally against the beta7 tree.

🤖 Generated with Claude Code

supa-chayajin and others added 8 commits September 30, 2026 10:03
- Toolchain: mago ^1.50, psalm ^6.19, igor-php ^0.9.7, plus every minor/patch update of the other direct dependencies (composer.lock refreshed).
- CI: the canonical workflow from component-template — checkout v7, cache v6, codecov v7, TruffleHog pinned to v3.97.9, the igor job pinned to 0.9.7 and checked against the binary itself.
- Dependabot: Composer and GitHub Actions, minor and patch updates only.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
- igor-php 0.9 adds detectors (writes through injected services, per-call spans, __destruct, superglobals). Each finding was checked against the code; these carry a method-level #[WorkerSafe] stating why nothing survives the request: GlobalsFactory::createFromGlobals, ::getParsedBody, ::createUploadedFilesFromGlobals, Stream::__destruct.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Workers that boot together race to create the same upload directory. The
loser's mkdir() returned false and emitted "mkdir(): File exists" at every
concurrent boot, as the EcoShield Gateway logs showed. The creation now runs
under a scoped error handler, as FileCache::attempt() does (no @ operator),
and the is_dir() re-check still throws when the directory really cannot be
created.

- Tests replay the lost race (php-mock is_dir) and a path squatted by a
  regular file; both fail with the fix reverted (failOnWarning).
- Real boot check: an image built from the fix booted 3 x 4 workers with no
  warning, where the released beta6 image logged it from several workers.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
ClientIp\TrustedProxyClientIpResolver reads X-Forwarded-For only behind allow-listed proxies (IPs or CIDR, v4/v6), right to left; a client-prepended hop cannot win, a malformed hop falls back to REMOTE_ADDR. wfl dod http PASS (96.55 %), igor 0 KO.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The file declared the PHPUnit 10.2 schema URL while the suite runs on 12.5, so attributes such as displayDetailsOnPhpunitDeprecations were invalid against it and Infection refused the configuration. It now points at vendor/phpunit/phpunit/phpunit.xsd, which always matches the installed PHPUnit.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The release is stamped in the CHANGELOG (## [0.1.0-beta7] — 2026-11, with its theme) and in the
README's release line. Nothing else changes: the tag comes from the umbrella release wave.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
The unit_tests job starts redis:7-alpine (the pin the umbrella's workspace job uses) and gives PHPUnit WAFFLE_TEST_REDIS_HOST=127.0.0.1. Until now the data and queue suites that talk to a real Redis were skipped on GitHub and ran only in the local gate. Same change in component-template and all 25 library components, so ci:check reports no drift.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
… 2.16; lock refresh

Every third-party package in composer.lock moves to its latest minor or patch
release (PHPUnit 12.5.42); the waffle-commons/* entries wait for the release-day
relock. CI pins igor 0.10.1 and TruffleHog v3.99.7. wfl dod PASS, psalm taint clean.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@supa-chayajin supa-chayajin added this to the 0.1.0-beta7 milestone Nov 3, 2026
@supa-chayajin supa-chayajin added bug Something isn't working enhancement New feature or request dependencies Dependency or toolchain update release Release branch (pre-release/* -> main) for a tagged version v1.0 On the road to 1.0.0 (formerly the 'Version 1.0' milestone) labels Nov 3, 2026
…esystem 8.1.11

Pins the released beta7 contracts (main 9a0f59b) and utils (main 20b7067), and the
Symfony security releases of 2026-11-04 that composer audit requires (symfony/filesystem).

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
@codecov

codecov Bot commented Nov 5, 2026

Copy link
Copy Markdown

Codecov Report

❌ Patch coverage is 96.82540% with 2 lines in your changes missing coverage. Please review.

Files with missing lines Patch % Lines
src/ClientIp/TrustedProxyClientIpResolver.php 96.36% 2 Missing ⚠️

📢 Thoughts on this report? Let us know!

@supa-chayajin
supa-chayajin merged commit c0b280e into main Nov 5, 2026
12 checks passed
@supa-chayajin
supa-chayajin deleted the pre-release/0.1.0-beta7 branch November 5, 2026 01:39
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

bug Something isn't working dependencies Dependency or toolchain update enhancement New feature or request release Release branch (pre-release/* -> main) for a tagged version v1.0 On the road to 1.0.0 (formerly the 'Version 1.0' milestone)

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant