Repository navigation
doc: publish the nvx crate's module diagrams and keep them current #930
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Merged
Pedro Henrique Penna (ppenna)
merged 6 commits into
dev
from
agents/rebase-module-diagrams-for-docs
Oct 27, 2026
Merged
Changes from all commits
Commits
Show all changes
6 commits
Select commit
Hold shift + click to select a range
82dec56
scripts: draw the module diagrams of the nvx crate
ppenna 568cd1a
doc: publish the module diagrams of the nvx crate
ppenna 90745e4
ci: draw the module diagrams again after every merge to dev
ppenna 6b951a2
scripts: restore the modules that cargo-modules mistakes for tests
ppenna b50a8a5
ci: publish no drawing of inputs that dev has since changed
ppenna 4667ebc
scripts: count each use of a restored module once
ppenna File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
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
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
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,252 @@ | ||
| name: Module diagrams | ||
|
|
||
| # Draws the module diagrams of the nvx crate, which doc/modules publishes, with | ||
| # scripts/module_diagrams.py (doc/ci.md, "Module diagrams"). A push to dev that | ||
| # changes their inputs, such as a merge, commits them to dev when they change. A | ||
| # pull request that changes their inputs draws them without committing them, so | ||
| # that a change that breaks the drawing fails before it merges, and uploads them | ||
| # for review. | ||
| on: | ||
| push: | ||
| branches: | ||
| - dev | ||
| paths: | ||
| - nvx-rs/** | ||
| - rust-toolchain.toml | ||
| - scripts/module_diagrams.py | ||
| - scripts/nvx_tools/build_constants.py | ||
| - .github/workflows/module-diagrams.yml | ||
| pull_request: | ||
| branches: | ||
| - dev | ||
| types: | ||
| - opened | ||
| - synchronize | ||
| - reopened | ||
| - ready_for_review | ||
| paths: | ||
| - nvx-rs/** | ||
| - rust-toolchain.toml | ||
| - scripts/module_diagrams.py | ||
| - scripts/nvx_tools/build_constants.py | ||
| - .github/workflows/module-diagrams.yml | ||
| workflow_dispatch: | ||
|
|
||
| permissions: | ||
| contents: read | ||
|
|
||
| # Runs on dev wait for one another, and a newer push replaces the run that | ||
| # waits. Each run draws the newest dev, so the run that commits last commits | ||
| # the diagrams of the newest dev. A newer push to a pull request cancels its | ||
| # older run. | ||
| concurrency: | ||
| group: ${{ github.workflow }}-${{ github.event.pull_request.number || github.ref }} | ||
| cancel-in-progress: ${{ github.event_name == 'pull_request' }} | ||
|
|
||
| env: | ||
| CARGO_MODULES_VERSION: 0.27.0 | ||
|
|
||
| jobs: | ||
| # The diagrams depend on the Graphviz release and the fonts that lay them | ||
| # out, so this job runs on a fixed Ubuntu release, and builds and runs the | ||
| # commit's code without credentials. | ||
| draw: | ||
| name: Draw module diagrams | ||
| if: github.event_name != 'pull_request' || github.event.pull_request.draft == false | ||
| runs-on: ubuntu-24.04 | ||
| timeout-minutes: 30 | ||
| outputs: | ||
| sha: ${{ steps.draw.outputs.sha }} | ||
| steps: | ||
| # A push or a dispatch draws the newest commit of its branch, rather than | ||
| # the commit that started it, so that whichever run commits last commits | ||
| # the diagrams of the newest dev. | ||
| - name: Checkout | ||
| uses: actions/checkout@v5 | ||
| with: | ||
| ref: ${{ github.event_name != 'pull_request' && github.ref || '' }} | ||
| persist-credentials: false | ||
|
|
||
| # Graphviz measures the labels with Liberation Sans, which the diagrams | ||
| # name first, so that their layouts do not depend on the image's other | ||
| # fonts. | ||
| - name: Install Graphviz | ||
| shell: bash | ||
| run: | | ||
| set -euo pipefail | ||
| sudo apt-get update | ||
| sudo DEBIAN_FRONTEND=noninteractive apt-get install -y --no-install-recommends \ | ||
| graphviz fonts-liberation | ||
| dot -V | ||
|
|
||
| - name: Install the pinned Rust release | ||
| shell: bash | ||
| run: | | ||
| set -euo pipefail | ||
| toolchain=$(sed -n 's/^channel = "\([^"]*\)".*/\1/p' rust-toolchain.toml) | ||
| test -n "${toolchain}" | ||
| rustup toolchain install "${toolchain}" --profile minimal --no-self-update | ||
| echo "RUST_TOOLCHAIN=${toolchain}" >> "${GITHUB_ENV}" | ||
| echo "${RUNNER_TEMP}/cargo-modules/bin" >> "${GITHUB_PATH}" | ||
|
|
||
| - name: Restore cargo-modules | ||
| id: restore-cargo-modules | ||
| uses: actions/cache/restore@v5 | ||
| with: | ||
| path: ${{ runner.temp }}/cargo-modules | ||
| key: cargo-modules-${{ env.CARGO_MODULES_VERSION }}-rust-${{ env.RUST_TOOLCHAIN }}-${{ runner.os }}-${{ runner.arch }} | ||
|
|
||
| - name: Install cargo-modules | ||
| if: steps.restore-cargo-modules.outputs.cache-hit != 'true' | ||
| shell: bash | ||
| run: >- | ||
| cargo "+${RUST_TOOLCHAIN}" install --locked cargo-modules | ||
| --version "${CARGO_MODULES_VERSION}" --root "${RUNNER_TEMP}/cargo-modules" | ||
|
|
||
| # Only dev pushes save the build, as they save the other caches. | ||
| - name: Save cargo-modules | ||
| if: >- | ||
| github.event_name == 'push' && | ||
| github.ref == 'refs/heads/dev' && | ||
| steps.restore-cargo-modules.outputs.cache-hit != 'true' | ||
| uses: actions/cache/save@v5 | ||
| with: | ||
| path: ${{ runner.temp }}/cargo-modules | ||
| key: cargo-modules-${{ env.CARGO_MODULES_VERSION }}-rust-${{ env.RUST_TOOLCHAIN }}-${{ runner.os }}-${{ runner.arch }} | ||
|
|
||
| - name: Draw the diagrams | ||
| id: draw | ||
| shell: bash | ||
| run: | | ||
| set -euo pipefail | ||
| version=$(cargo modules --version) | ||
| if [[ "${version}" != "cargo-modules ${CARGO_MODULES_VERSION}" ]]; then | ||
| echo "::error::${version} is not cargo-modules ${CARGO_MODULES_VERSION}" | ||
| exit 1 | ||
| fi | ||
| python3 scripts/module_diagrams.py --output doc/modules | ||
| echo "sha=$(git rev-parse HEAD)" >> "${GITHUB_OUTPUT}" | ||
|
|
||
| - name: Summarize the changes | ||
| shell: bash | ||
| run: | | ||
| set -euo pipefail | ||
| sha=$(git rev-parse HEAD) | ||
| changes=$(git status --porcelain --untracked-files=all -- doc/modules) | ||
| { | ||
| echo "## Module diagrams" | ||
| echo | ||
| if [[ -z "${changes}" ]]; then | ||
| echo "The diagrams of \`${sha}\` match doc/modules." | ||
| else | ||
| echo "The diagrams of \`${sha}\` change doc/modules:" | ||
| echo | ||
| echo '```text' | ||
| echo "${changes}" | ||
| echo '```' | ||
| fi | ||
| } >> "${GITHUB_STEP_SUMMARY}" | ||
|
|
||
| - name: Upload the diagrams | ||
| uses: actions/upload-artifact@v7 | ||
| with: | ||
| name: module-diagrams-${{ github.run_id }} | ||
| path: doc/modules | ||
| if-no-files-found: error | ||
| overwrite: true | ||
| retention-days: 7 | ||
|
|
||
| # Commits the diagrams that the draw job drew to dev, with the deploy key that | ||
| # may push to dev past its rules, the one of the performance history. It | ||
| # builds and runs no code of the commit, and commits nothing but doc/modules. | ||
| publish: | ||
| name: Publish module diagrams | ||
| needs: draw | ||
| if: github.event_name != 'pull_request' && github.ref == 'refs/heads/dev' | ||
| runs-on: ubuntu-latest | ||
| timeout-minutes: 10 | ||
| steps: | ||
| - name: Checkout dev | ||
| uses: actions/checkout@v5 | ||
| with: | ||
| ref: dev | ||
| fetch-depth: 0 | ||
| ssh-key: ${{ secrets.PERFORMANCE_PERSIST_DEPLOY_KEY }} | ||
|
|
||
| - name: Download the diagrams | ||
| uses: actions/download-artifact@v8 | ||
| with: | ||
| name: module-diagrams-${{ github.run_id }} | ||
| path: ${{ runner.temp }}/module-diagrams | ||
|
|
||
| - name: Commit the diagrams to dev | ||
| shell: bash | ||
| env: | ||
| DIAGRAMS: ${{ runner.temp }}/module-diagrams | ||
| DRAWN: ${{ needs.draw.outputs.sha }} | ||
| # The inputs of the diagrams: the paths that start this workflow. | ||
| INPUTS: >- | ||
| nvx-rs rust-toolchain.toml scripts/module_diagrams.py | ||
| scripts/nvx_tools/build_constants.py | ||
| .github/workflows/module-diagrams.yml | ||
| run: | | ||
| set -euo pipefail | ||
| if [[ ! "${DRAWN}" =~ ^[0-9a-f]{40}$ ]]; then | ||
| echo "::error::The draw job named no commit: '${DRAWN}'" | ||
| exit 1 | ||
| fi | ||
| unexpected=$(find "${DIAGRAMS}" -mindepth 1 \ | ||
| ! \( -type f \( -name README.md -o -name '*.svg' \) \) -print) | ||
| if [[ -n "${unexpected}" || ! -f "${DIAGRAMS}/README.md" ]]; then | ||
| echo "::error::The diagrams hold more than a page and SVG files, or no page:" | ||
| echo "${unexpected}" | ||
| exit 1 | ||
| fi | ||
| read -r -a inputs <<< "${INPUTS}" | ||
| git config user.name "github-actions[bot]" | ||
| git config user.email "github-actions[bot]@users.noreply.github.com" | ||
|
|
||
| for attempt in 1 2 3; do | ||
| git fetch origin dev | ||
| git checkout -B module-diagrams origin/dev | ||
| # A rerun of this job alone reuses the drawing of its run, which a | ||
| # newer run may have replaced. Publish it only while dev holds the | ||
| # inputs that it was drawn from: the push that changed them started | ||
| # a run that publishes their diagrams. | ||
| status=0 | ||
| git diff --quiet "${DRAWN}" HEAD -- "${inputs[@]}" || status=$? | ||
| if [[ "${status}" -eq 1 ]]; then | ||
| echo "::notice::dev changed the inputs of the diagrams since ${DRAWN}; the run of the newer commit publishes their diagrams" | ||
| exit 0 | ||
| elif [[ "${status}" -ne 0 ]]; then | ||
| echo "::error::Cannot compare the inputs of the diagrams at ${DRAWN} with dev" | ||
| exit 1 | ||
| fi | ||
| rm -rf doc/modules | ||
| mkdir -p doc/modules | ||
| cp "${DIAGRAMS}"/* doc/modules/ | ||
| git add --all -- doc/modules | ||
|
|
||
| unexpected=$(git diff --cached --no-renames --name-only | | ||
| grep -v '^doc/modules/' || true) | ||
| if [[ -n "${unexpected}" ]]; then | ||
| echo "::error::Refusing to commit changes outside doc/modules:" | ||
| echo "${unexpected}" | ||
| exit 1 | ||
| fi | ||
|
|
||
| if git diff --cached --quiet; then | ||
| echo "The module diagrams on dev are up to date" | ||
| exit 0 | ||
| fi | ||
|
|
||
| git commit --no-verify \ | ||
| -m "doc: update module diagrams (${DRAWN}) [skip ci]" | ||
| if git push origin HEAD:dev; then | ||
| exit 0 | ||
| fi | ||
| if [ "${attempt}" -eq 3 ]; then | ||
| echo "::error::Failed to publish the module diagrams after ${attempt} attempts" | ||
| exit 1 | ||
| fi | ||
| done | ||
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
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
Oops, something went wrong.
Oops, something went wrong.
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.
Uh oh!
There was an error while loading. Please reload this page.