feat(uv): parameterize the platform parent in gazelle_python_manifest - #1468
Open
sallustfire wants to merge 1 commit into
Open
sallustfire wants to merge 1 commit into
sallustfire wants to merge 1 commit into
Conversation
The per-venv synthetic platform gazelle_python_manifest generates hardcoded parents = ["@platforms//host"], and the dep_group transition replaces --platforms wholesale. Anything building under the transitioned configuration therefore resolved toolchains against a bare os+cpu platform, which breaks builds with a custom --host_platform (hermetic cc toolchains gating on extra constraints fail sdist builds in the hub at analysis) and cross-compilation (wheel selection snaps back to the host platform, issue aspect-build#1416). Add a platform_parents parameter, defaulting to the current behavior so existing callers are unaffected, and thread it into the synthetic platform's parents. The list must hold exactly one label (platform() accepts at most one parent); the macro fails eagerly with a message naming the parameter otherwise. The default is built as Label("@platforms//host") in the defining module, so callers need no direct bazel_dep on platforms to use it. A new e2e snapshot case builds a manifest under a caller-supplied parent and pins a probe transitioned through the macro-generated platform, selecting on a constraint only the custom parent carries. Fixes aspect-build#1416 Co-Authored-By: Claude Fable 5 <noreply@anthropic.com>
|
Important Review skippedAuto reviews are disabled on this repository. Please check the settings in the CodeRabbit UI or the ⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Pro Plus Run ID: You can disable this status message by setting the Use the checkbox below for a quick retry:
Comment |
xangcastle
self-requested a review
August 19, 2026 20:33
4 tasks
Member
|
Thanks for doing this @sallustfire this will be landed on #1470 while I am keeping your authoring. |
xangcastle
added a commit
that referenced
this pull request
Aug 20, 2026
…#1470) Fixes #1416. Supersedes #1468, carrying @sallustfire's commit unchanged (cherry-picked, authorship preserved) plus three follow-up commits. ## Base change (from #1468, by @sallustfire) `gazelle_python_manifest`'s synthetic per-venv platforms hardcoded `parents = ["@platforms//host"]`, so the `platform_transition_filegroup` over the hub's wheel index replaced the caller's `--platforms` wholesale. That broke custom `--host_platform` setups (hermetic cc toolchains) and cross-compilation. The fix parameterizes the parent platform; the default preserves current behavior and is resolved as a `Label` in rules_py's own repository, so consumers need no `bazel_dep` on `platforms`. ## Follow-up commits **`platform_parent` is a single label, not a list.** The list form failed at load time on any length other than one — promising plurality the underlying `platform()` rule does not support. Renamed and made singular before the API ships. The load-time check now rejects any non-string, non-Label value (lists, selects) with a message naming the parameter. **Wheel selection is pinned under a real cross-compilation parent.** The e2e case's parent is now a fully-specified `linux_x86_64` platform carrying the `platform_libc`/`platform_version` flags — issue #1416's actual scenario, and host-invariant. The flags ride on the platform because their defaults are host-detected: without them, manylinux `config_setting`s never match off-linux and native packages silently degrade to sdist fallbacks (the other half of the config chimera the issue describes; this is also the documented recipe for real cross-compilation parents). A new analysis-time probe snapshots which wheel variant each hub dependency resolves to (`distribution: platform-class` lines — no versions or tag spellings, so lock bumps don't churn the golden). Native packages pin to `linux_x86_64`, pure ones to `any`, and sdist fallbacks surface explicitly. The manifest YAML golden is replaced by a `build_test`: the YAML content is platform-independent, so it only re-pinned another case's hub state; building the manifest end-to-end from linux-selected wheels is the actual signal. **Gazelle manifest tooling moved to a `tools/` subpackage.** `generate.py` and `update.sh` move out of the package holding the public `defs.bzl` into `//uv/private/gazelle_manifest/tools` with absolute labels; implicit-attribute visibility is checked against the defining `.bzl`'s package, so `:generator` stays private. ## Test plan - 37/37 e2e/cases tests pass (36 snapshot diff tests + the new `manifest_build_test`); goldens regenerated via `bazel run //:snapshots` on darwin_arm64 — the wheel-selection golden shows `linux_x86_64` wheels selected from a mac host. - Regression detection verified by simulating the revert (macro ignoring `platform_parent`): the constraint probe flips to `default-parent` and the wheel probe flips to `macosx_*` wheels. - `//uv/private/gazelle_manifest/tests:test` passes; buildifier clean on changed files. --- - [x] Changes are visible to end-users: yes - [x] Searched for relevant documentation and updated as needed: yes (`docs/uv.md` Gazelle section) - [x] Breaking change (forces users to change their own code or config): no - [x] Suggested release notes appear below: yes `gazelle_python_manifest` now accepts `platform_parent`, letting the manifest's per-venv wheel selection parent onto a custom platform. Needed for repos with a custom `--host_platform` (hermetic C++ toolchains) and for cross-compilation; in the cross-compilation case, carry the `platform_libc`/`platform_version` flags on the parent platform. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --------- Co-authored-by: Connor McEntee <sallustfire@gmail.com> Co-authored-by: Claude Fable 5 <noreply@anthropic.com>
jbedard
force-pushed
the
main
branch
2 times, most recently
from
August 25, 2026 18:24
b25e5ec to
25d3b44
Compare
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
AI written, human reviewed.
Fixes #1416.
Per venv,
gazelle_python_manifestdeclares a throwawayplatform()whose flags force--@<hub>//dep_group=<venv>, then pushes the hub'sgazelle_index_whlsfilegroup throughplatform_transition_filegroup. That synthetic platform hardcodesparents = ["@platforms//host"], and the transition replaces--platformswholesale, so everything that has to build under the transitioned configuration resolves toolchains against a bare os+cpu platform. Two real setups break:Custom
--host_platform/ hermetic toolchains. Withcommon --host_platform=@host_platform//:platform(a platform carrying libc/kernel/etc. constraints that hermetic cc toolchains gate on) and--repo_env=BAZEL_DO_NOT_DETECT_CPP_TOOLCHAIN=1, PEP 517 sdist builds in the hub (python-ldap, PyMuPDF, ...) fail analysis under the transition in our build:Those sdists are the packages the manifest exists to index (python-ldap imports as
ldap/ldapurl/ldif, PyMuPDF asfitz), so filtering them out isn't an option.--platforms=<linux target>from a darwin host, the transition pulls wheel selection back to the darwin host platform and fails withNo matching toolchains found for types: @@aspect_rules_py+//py/private/toolchain:native_build_toolchain_type.The fix
A
platform_parentsparameter, threaded into the synthetic platform'sparents. The default preserves current behavior exactly.platform()accepts at most one parent, and the macro fails eagerly at load time with a message naming the parameter otherwise. That also rejects the empty list, whose constraint-free platform would quietly degrade wheel selection to sdist fallbacks. The list shape mirrors the nativeparentsattribute so callers can lift aparentslist off an existingplatform()unchanged.Label("@platforms//host")in the defining module, so consumers need no directbazel_depon platforms to use it. Previously the hardcoded string resolved against the caller's repo mapping.Why parameterization and not something smarter
--@<hub>//dep_groupwould have to statically declare that flag label as a transition output, but the hub name is a macro parameter, unknown at rule-definition time.platform(flags = ...)is data, constructible per hub at load time.platform()parents must be a static label; there's no "inherit the incoming platform". Deriving the parent from the incoming--platformsisn't implementable from a macro, and it would make the checked-in manifest depend on whatever--platformsa developer happened to pass. The explicit parameter keepsbazel run :gazelle_python_manifest.updatereproducible, and covers the case where the desired parent is a target platform rather than the current one.Test coverage
New snapshot case
e2e/cases/gazelle-platform-parents-1416: builds a manifest over the existingpypi_uv_deps_650hub's extras venv with a caller-supplied parent carrying a case-local constraint, and pins two goldens, the manifest YAML (built end-to-end) and a probe genrule whoseselect()keys on that constraint, transitioned through the macro-generated synthetic platform. If the macro ever ignoresplatform_parents, the probe golden flips from custom-parent to default-parent and the diff test fails (verified by reverting the fix).docs/uv.mdGazelle section)gazelle_python_manifestnow acceptsplatform_parents, letting the manifest's per-venv wheel selection parent onto a custom platform. Needed for repos with a custom--host_platform(hermetic C++ toolchains) and for cross-compilation.Test plan
bazel run //:snapshotsplus all 36 snapshot diff tests pass.bazel build //gazelle-platform-parents-1416:alland the unmodified//uv-gazelle-778:gazelle_python_manifest(default-parent path through the newLabel()substitution) both build.bazel run //:snapshotsreproduces both goldens byte-identically, andbazel query --output=buildshows the synthetic platform'sparentsis the custom platform in the new case and@platforms//hostfor existing callers.bazel test //uv/private/gazelle_manifest/tests:testpasses; buildifier clean on the changed files.