Fix build abort on broken autodoc reference blocking link resolution - #814
Fix build abort on broken autodoc reference blocking link resolution#814aether-png wants to merge 1 commit into
Conversation
coyotte508
left a comment
There was a problem hiding this comment.
🤖 Automated bot review — this review was generated by an AI agent (moon-coder). It may contain mistakes; please verify findings before acting on them.
This PR changes build_mdx_files() to collect per-file conversion errors instead of aborting on the first broken [[autodoc]] reference, so resolve_links(), notebook building, and toctree renaming still run over the successfully-built pages, with the aggregated failure raised at the end of build_doc(). The approach is sound and correctly fixes the root cause of #475, but the diff has a CI-breaking formatting issue and a few polish gaps.
Findings
- 🔴 Trailing whitespace will fail the quality CI — the diff adds two whitespace-only lines:
src/doc_builder/build_doc.py:274(8 spaces after the newreturninbuild_mdx_files, which also creates a triple blank line beforeresolve_links) and:416(4 spaces before the newif len(mdx_errors)block inbuild_doc). The repo's quality workflow runsruff checkandruff format --check .(.github/workflows/quality.yml), which will reject both. Runruff formatbefore merging. - 🟡 Loss of exception type and traceback — the old code (
build_doc.py:255on main) re-raised withraise type(e)(...) from e, preserving the original exception class and chained traceback. The new code flattens everything to a string (e.args[0]) reported much later, which makes genuine crashes (import errors, bugs inautodoc_svelte) harder to debug than a "missing object" typo. Consider capturingtraceback.format_exc()(or at leastrepr(e)) in the collected message. Relatedly,e.args[0]raisesIndexErrorfor exceptions constructed with no args — pre-existing fragility, butstr(e)would be strictly safer now that this path is a catch-all that keeps the loop running. - 🟡 Docstrings not updated —
build_mdx_filesnow returns a 4-tuple andcheck_toc_integritygainedknown_failed_files, but neither docstring mentions it. The codebase consistently documents args (see theArgs:block atbuild_doc.py:470-473); please document the new parameter and return values. - 🟡 No test coverage —
tests/test_build_doc.pyonly tests regexes/resolve_open_in_colab; nothing exercises the new error-collection path, the 4-tuple return, orcheck_toc_integrity(known_failed_files=...). A small unit test (e.g. a doc folder with one broken[[autodoc]]asserting the build writes the other pages, resolves links, and raises the aggregatedValueErrorat the end) would lock in the fix. - 🟡 Error-masking ordering in
build_doc— if a build has both MDX conversion errors and a genuine toc problem (e.g. a built file missing from_toctree.yml),check_toc_integrity(build_doc.py:400) now raises before the collectedmdx_errorsare reported (:417-420), so the author sees only the toc error and the autodoc errors are silently dropped for that run. Consider raisingmdx_errorsfirst, or appending them to the toc error message. - 🔵
continuesemantics — thecontinueatbuild_doc.py:258also skips any softerrorsthatresolve_autodocreturned before a later exception. Correct in practice — and intentionally discardingnew_anchorsfor the failed page is the right call (anchors would point at a page that was never written) — just worth being aware of. - 🔵
known_failed_filesis a list, not a set — the PR description says "accepts a set"; membership testing atbuild_doc.py:518is O(n·m). Trivially small in practice, but passingset(failed_files)would match the description and be cheaper. - 🔵 Path-form consistency looks correct —
str(file.with_suffix("").relative_to(doc_folder))produces OS-native separators, matching both the existingpage_nameconstruction and thestr(Path(path))normalization oftoc_sections, so the Windows case is handled.
Question: was resolve_links running with an incomplete anchors_mapping (references to objects on the failed page stay unresolved) considered acceptable given the build fails at the end anyway? A one-line comment noting this would help future readers.
Verdict: Approach is correct and well-scoped, but the trailing-whitespace lines will fail the ruff CI gate and should be fixed (and ideally a regression test added) before merge.
Fixes #475
Root cause
build_mdx_files() aborted the entire build immediately on the first file with a broken [[autodoc]] reference. This happened before resolve_links() ran, so every [~Class.method]-style reference across the whole doc set was left unresolved when any single reference broke — including the trailing-underscore case in #475, where the unresolved raw text got picked up by markdown's emphasis parsing.
A second issue surfaced once the abort was removed: check_toc_integrity(), called right after, independently failed because the file that errored was legitimately absent from the output directory (never written) but still listed in _toctree.yml.
Fix
build_mdx_files() now collects per-file errors and continues instead of raising immediately
check_toc_integrity() accepts a set of known-failed files and skips them when checking for missing output
build_doc() now lets resolve_links, notebook building, and toctree renaming run regardless of MDX errors, and raises the deployment-failure error only at the very end
Testing
Reproduced the original bug: single broken [[autodoc]] reference → full build abort → every reference left unresolved
Verified fix: same broken reference → build completes, clip_grad_value_ (and all other references) resolve correctly, error is raised only at the end
Verified multi-error case: two broken references in different files → both correctly reported together, neither dropped
Verified clean build (no broken references) has zero regressions
Ran full existing test suite; confirmed the 3 pre-existing failures (GlmAsrForConditionalGeneration import error, a cascading AutoProcessor NameError, and a Windows-specific [WinError 2] subprocess issue in test_format_code_example) are present identically on unmodified main, unrelated to this change