Skip to content

feat(build): resolve build deps from dependency graph instead of PEP 517 hooks#1009

Open
LalatenduMohanty wants to merge 1 commit intopython-wheel-build:mainfrom
LalatenduMohanty:issue-996-no-discovery-fallback
Open

feat(build): resolve build deps from dependency graph instead of PEP 517 hooks#1009
LalatenduMohanty wants to merge 1 commit intopython-wheel-build:mainfrom
LalatenduMohanty:issue-996-no-discovery-fallback

Conversation

@LalatenduMohanty
Copy link
Copy Markdown
Member

@LalatenduMohanty LalatenduMohanty commented Apr 1, 2026

build-sequence and build-parallel now use DependencyNode.iter_build_requirements() to populate build environments from the graph, eliminating the silent fallback to PEP 517 discovery hooks when cached dependency files were missing.

build-sequence now requires a GRAPH_FILE argument alongside BUILD_ORDER_FILE. The fromager build command (debug/test) is unchanged.

Breaking change: build-sequence now takes GRAPH_FILE BUILD_ORDER_FILE (two positional args instead of one).

Closes: #996

@LalatenduMohanty LalatenduMohanty requested a review from a team as a code owner April 1, 2026 19:51
@coderabbitai
Copy link
Copy Markdown

coderabbitai bot commented Apr 1, 2026

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: e415c8b7-30b5-49a8-9dcc-71375d455b6d

📥 Commits

Reviewing files that changed from the base of the PR and between 3b4378f and 11abef4.

📒 Files selected for processing (9)
  • docs/how-tos/bootstrap-constraints.rst
  • docs/using.md
  • e2e/test_build_order.sh
  • e2e/test_build_sequence_git_url.sh
  • e2e/test_prebuilt_wheel_hook.sh
  • src/fromager/build_environment.py
  • src/fromager/commands/bootstrap.py
  • src/fromager/commands/build.py
  • tests/test_build_environment.py
✅ Files skipped from review due to trivial changes (4)
  • e2e/test_build_sequence_git_url.sh
  • docs/how-tos/bootstrap-constraints.rst
  • e2e/test_prebuilt_wheel_hook.sh
  • docs/using.md
🚧 Files skipped from review as they are similar to previous changes (3)
  • e2e/test_build_order.sh
  • tests/test_build_environment.py
  • src/fromager/commands/build.py

📝 Walkthrough

Walkthrough

The pull request makes build-sequence consume a dependency graph file. Documentation examples and user docs now show fromager build-sequence taking graph.json (dependency relationships) before build-order.json (predetermined build order). End-to-end tests are updated to preserve and pass graph.json alongside build-order.json. A new function prepare_build_environment_from_graph(...) is added to construct build environments by installing pinned requirements derived from graph nodes. The build_sequence command gains a required graph_file argument, loads a DependencyGraph, derives per-package build requirements via _get_build_requirements_from_graph(...), and threads those requirements into _build(...) and _build_parallel(...).

Estimated code review effort

🎯 3 (Moderate) | ⏱️ ~25 minutes

Detailed notes

  • build_environment.py

    • Adds prepare_build_environment_from_graph(...) that constructs a BuildEnvironment and installs pinned requirements derived from provided DependencyNode objects. Mirrors existing prepare flow; ensure install call uses exact pinned specs (name==version).
    • Includes TYPE_CHECKING import for dependency_graph.
  • commands/build.py

    • build_sequence now requires graph_file and loads DependencyGraph.
    • Per-entry build requirements come from _get_build_requirements_from_graph(graph, dist_name, resolved_version).
    • _build() and _build_parallel() accept optional build_requirements and call the new prepare function when provided.
    • _get_build_requirements_from_graph() canonicalizes name+version, looks up node in graph.nodes, raises KeyError if missing and returns list(node.iter_build_requirements()).
    • Verify KeyError handling upstream; if uncaught it will abort builds for missing graph entries.
  • Tests

    • New unit tests exercise prepare_build_environment_from_graph() and _get_build_requirements_from_graph(), including cases for empty requirements and missing nodes.
    • E2E scripts updated consistently to copy work-dir/graph.json into test output and pass it as the first argument to build-sequence.
  • Docs

    • Examples and prose updated to reflect that build requirements are resolved from graph.json (dependency relationships) rather than via PEP 517 discovery hooks.

Actionable checks/suggestions

  • Ensure KeyError from _get_build_requirements_from_graph() is either intentionally fatal or converted to a clearer error message before surfacing to users.
  • Confirm parsing of graph.json fails fast with a useful error on malformed or missing files.
  • Consider adding a small integration test that exercises the error path when a graph node is missing to assert the observable behavior is acceptable.
🚥 Pre-merge checks | ✅ 4
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title accurately captures the main objective: resolving build dependencies from the dependency graph instead of PEP 517 hooks, which directly addresses issue #996.
Description check ✅ Passed The description clearly explains the change (graph-based dependency resolution), the breaking change (new GRAPH_FILE argument), and references the closed issue.
Linked Issues check ✅ Passed The PR implementation fully addresses issue #996 by eliminating the PEP 517 discovery fallback through graph-based build requirement resolution in build-sequence and build-parallel [#996].
Out of Scope Changes check ✅ Passed All changes are directly related to resolving build dependencies from the graph: CLI updates, build environment functions, tests, and documentation reflect the single objective.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.


Comment @coderabbitai help to get the list of available commands and usage tips.

@mergify mergify bot added the ci label Apr 1, 2026
Copy link
Copy Markdown

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 3

🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Inline comments:
In `@docs/using.md`:
- Around line 190-193: The doc text is inconsistent: the intro correctly states
that dependency relationships come from graph.json but the Step 1 bullet still
points to build-order.json; update the Step 1 bullet in the using.md section
describing the build-sequence command so it says dependency relationships are
read from graph.json (and that build-order.json only contains the predetermined
build order), and ensure any mention of "dependency relationships" references
graph.json while build-order.json is described as the resolved build-order
artifact used to drive the build.

In `@src/fromager/build_environment.py`:
- Around line 343-353: The current graph-resolved install path wrongly tags
failures as RequirementType.BUILD_SYSTEM; change this to use a neutral label
instead: add a new enum member (e.g., RequirementType.GRAPH or
RequirementType.GRAPH_INSTALL) and pass that to _safe_install when installing
the mixed graph (the call site that currently passes
RequirementType.BUILD_SYSTEM for variables reqs, ctx, build_env, req). Ensure
the new enum value is declared where RequirementType is defined and update any
consumers/tests if needed so graph-driven install failures are reported with the
neutral label.

In `@src/fromager/commands/build.py`:
- Around line 201-203: The current lookup in _get_build_requirements_from_graph
(used where build_requirements is assigned) only matches dist_name and
resolved_version and can return stale graph.json entries; update the function to
also compare the graph node's download_url with the build-order
entry["source_url"] (or equivalent source field) and raise an explicit error
(fail fast) when they mismatch so the build aborts instead of using wrong
requirements; ensure the validation is applied in all call sites (including the
other block referenced around lines 585-598) and include a clear error message
identifying the package, expected source_url and actual download_url to aid
debugging.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro

Run ID: ed405c67-ae44-42a1-916d-b0d1c084f5f8

📥 Commits

Reviewing files that changed from the base of the PR and between 2cf0e7d and 3b4378f.

📒 Files selected for processing (8)
  • docs/how-tos/bootstrap-constraints.rst
  • docs/using.md
  • e2e/test_build_order.sh
  • e2e/test_build_sequence_git_url.sh
  • e2e/test_prebuilt_wheel_hook.sh
  • src/fromager/build_environment.py
  • src/fromager/commands/build.py
  • tests/test_build_environment.py

Comment on lines +343 to +353
if reqs:
# Graph-resolved deps are a mix of build-system, build-backend,
# build-sdist, and their transitive install deps. We use
# BUILD_SYSTEM as the label since they all go into the build env.
_safe_install(
ctx=ctx,
req=req,
build_env=build_env,
deps=reqs,
dep_req_type=RequirementType.BUILD_SYSTEM,
)
Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟡 Minor

Don’t report mixed graph installs as build-system failures.

This path installs a mix of build-system, build-backend, build-sdist, and transitive install deps. If _safe_install() fails, labeling the whole batch as RequirementType.BUILD_SYSTEM points operators at the wrong phase. A neutral label for the graph-driven install path would make the error output accurate.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@src/fromager/build_environment.py` around lines 343 - 353, The current
graph-resolved install path wrongly tags failures as
RequirementType.BUILD_SYSTEM; change this to use a neutral label instead: add a
new enum member (e.g., RequirementType.GRAPH or RequirementType.GRAPH_INSTALL)
and pass that to _safe_install when installing the mixed graph (the call site
that currently passes RequirementType.BUILD_SYSTEM for variables reqs, ctx,
build_env, req). Ensure the new enum value is declared where RequirementType is
defined and update any consumers/tests if needed so graph-driven install
failures are reported with the neutral label.

…517 hooks

build-sequence and build-parallel now use DependencyNode.iter_build_requirements()
to populate build environments from the graph, eliminating the silent fallback to
PEP 517 discovery hooks when cached dependency files were missing.

build-sequence now requires a GRAPH_FILE argument alongside BUILD_ORDER_FILE.
The fromager build command (debug/test) is unchanged.

Closes: python-wheel-build#996

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: Lalatendu Mohanty <lmohanty@redhat.com>
@LalatenduMohanty LalatenduMohanty force-pushed the issue-996-no-discovery-fallback branch from 3b4378f to 11abef4 Compare April 1, 2026 20:12
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

REF: Eliminate discovery hook fallback in Stage 2 build pipeline

1 participant