cpdocs 0.3.4__tar.gz → 0.3.6__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {cpdocs-0.3.4 → cpdocs-0.3.6}/.github/workflows/docs.yml +9 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/.github/workflows/test.yml +9 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/PKG-INFO +1 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/__init__.py +1 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/build.py +7 -6
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/cli.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/config.py +0 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/contract.py +5 -6
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/cpp/render.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/fortran/extract.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/fortran/render.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/rust/extract.py +1 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/rust/render.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/model.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/plugins/properdocs/plugin.py +2 -5
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/providers/cargo.py +8 -4
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/rendering/common.py +3 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/rendering/html.py +30 -23
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_api_reference.py +8 -2
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_build.py +4 -2
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_config.py +16 -4
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_examples.py +8 -18
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_feature_set_signatures.py +2 -2
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_properdocs_core.py +1 -3
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_rust_example.py +9 -20
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_rust_provider.py +31 -23
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_versioning.py +6 -1
- {cpdocs-0.3.4 → cpdocs-0.3.6}/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/.reuse/templates/bordered.jinja2 +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/LICENSES/Apache-2.0.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/REUSE.toml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/examples/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/explanation/architecture.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/explanation/feature-sets.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/how-to/ci.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/how-to/feature-sets.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/how-to/generated-headers.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/how-to/other-build-systems.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/how-to/properdocs.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/cli.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/cmake.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/comments.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/configuration.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/contract.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/extraction.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/reference/links.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/docs/web/tutorials/first-reference.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/include/acme/math.hpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/basic-cpp/src/math.cpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/include/ring/ring.h +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/c-basic/src/ring.c +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/docs/cpdocs-minibuild.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/include/demo/solver.hpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-features/tools/minibuild.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/include/meta/meta.hpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/cpp-templates/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/docs/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/docs/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/lib/normalize.f90 +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/mod/geometry.f90 +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/fortran-basic/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/generated-template/generated.hpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/include/acme/core.hpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/generated-cpp/src/generated.cpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/CMakeLists.txt +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/include/geom/vector.hpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/python/pygeom/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/mixed/src/geom.cpp +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/.gitignore +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/docs/api/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/docs/web/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/docs/web/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/pyproject.toml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/src/dice/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/src/dice/_rng.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/python-basic/src/dice/core.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/Cargo.lock +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/Cargo.toml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/docs/api.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/docs/cpdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/docs/index.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/rust-toolchain.toml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/src/geometry.rs +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/src/internal.rs +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/examples/rust-basic/src/lib.rs +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/properdocs.yml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/pyproject.toml +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/readme.md +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/__main__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/base.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/cpp/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/cpp/extract.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/fortran/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/python/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/python/extract.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/python/render.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/languages/rust/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/plugins/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/plugins/properdocs/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/plugins/properdocs/core.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/providers/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/providers/cmake.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/providers/contract.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/providers/python.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/rendering/__init__.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/src/cpdocs/versioning.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/conftest.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/test/test_contract.py +0 -0
- {cpdocs-0.3.4 → cpdocs-0.3.6}/uv.lock +0 -0
|
@@ -43,7 +43,15 @@ jobs:
|
|
|
43
43
|
fetch-depth: 0
|
|
44
44
|
- uses: astral-sh/setup-uv@v6
|
|
45
45
|
- name: Install toolchain for the C and C++ examples
|
|
46
|
-
run: sudo apt-get install -y --no-install-recommends clang
|
|
46
|
+
run: sudo apt-get install -y --no-install-recommends clang ninja-build
|
|
47
|
+
- name: Install CMake 4.3
|
|
48
|
+
run: |
|
|
49
|
+
uv tool install --python 3.12 cmake==4.3.4
|
|
50
|
+
echo "$(uv tool dir --bin)" >> "$GITHUB_PATH"
|
|
51
|
+
- name: Verify CMake version
|
|
52
|
+
run: |
|
|
53
|
+
cmake --version
|
|
54
|
+
test "$(cmake --version | head -n 1)" = "cmake version 4.3.4"
|
|
47
55
|
- name: Install toolchain for the Rust example
|
|
48
56
|
run: rustup toolchain install nightly-2026-10-01 --profile minimal
|
|
49
57
|
- name: Build documentation
|
|
@@ -15,7 +15,15 @@ jobs:
|
|
|
15
15
|
- uses: actions/checkout@v4
|
|
16
16
|
- uses: astral-sh/setup-uv@v6
|
|
17
17
|
- name: Install toolchain for the C and C++ examples
|
|
18
|
-
run: sudo apt-get install -y --no-install-recommends clang
|
|
18
|
+
run: sudo apt-get install -y --no-install-recommends clang ninja-build
|
|
19
|
+
- name: Install CMake 4.3
|
|
20
|
+
run: |
|
|
21
|
+
uv tool install --python 3.12 cmake==4.3.4
|
|
22
|
+
echo "$(uv tool dir --bin)" >> "$GITHUB_PATH"
|
|
23
|
+
- name: Verify CMake version
|
|
24
|
+
run: |
|
|
25
|
+
cmake --version
|
|
26
|
+
test "$(cmake --version | head -n 1)" = "cmake version 4.3.4"
|
|
19
27
|
- name: Install toolchain for the Rust example
|
|
20
28
|
run: rustup toolchain install nightly-2026-10-01 --profile minimal
|
|
21
29
|
- name: Lint
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
Metadata-Version: 2.5
|
|
2
2
|
Name: cpdocs
|
|
3
|
-
Version: 0.3.
|
|
3
|
+
Version: 0.3.6
|
|
4
4
|
Summary: Semantic, versioned API documentation for C, C++, CUDA, HIP, Fortran, Python and Rust projects
|
|
5
5
|
Project-URL: Source, https://github.com/ambhora/cpdocs
|
|
6
6
|
Author-email: Jayesh Badwaik <j.badwaik@fz-juelich.de>
|
|
@@ -46,7 +46,7 @@ class Layout:
|
|
|
46
46
|
@classmethod
|
|
47
47
|
def for_output(cls, output: Path, *, tmp_directory: Path | None = None) -> Layout:
|
|
48
48
|
root = (output / "cpdocs").resolve()
|
|
49
|
-
work_root =
|
|
49
|
+
work_root = tmp_directory.resolve() / "cpdocs" if tmp_directory else root
|
|
50
50
|
return cls(root=root, work_root=work_root)
|
|
51
51
|
|
|
52
52
|
@property
|
|
@@ -61,7 +61,6 @@ class Layout:
|
|
|
61
61
|
return self.work_root / "work" / ref.replace("/", "__")
|
|
62
62
|
|
|
63
63
|
|
|
64
|
-
|
|
65
64
|
# --------------------------------------------------------------------------------------------------
|
|
66
65
|
# Extraction
|
|
67
66
|
# --------------------------------------------------------------------------------------------------
|
|
@@ -139,7 +138,11 @@ def _api_display_paths(
|
|
|
139
138
|
root_relative = path.name
|
|
140
139
|
project_relative = relative_source_path(path, project_root)
|
|
141
140
|
logical = next(
|
|
142
|
-
(
|
|
141
|
+
(
|
|
142
|
+
candidate
|
|
143
|
+
for candidate in (root_relative, project_relative)
|
|
144
|
+
if candidate in graph.sources
|
|
145
|
+
),
|
|
143
146
|
None,
|
|
144
147
|
)
|
|
145
148
|
if logical is not None:
|
|
@@ -619,9 +622,7 @@ def build_versions(
|
|
|
619
622
|
)
|
|
620
623
|
ref_config = _config_for_checkout(config, checkout) if ref.checkout else config
|
|
621
624
|
work = layout.work(ref.name)
|
|
622
|
-
graph = build_graph(
|
|
623
|
-
ref_config, source=checkout, work=work, version=ref.name
|
|
624
|
-
)
|
|
625
|
+
graph = build_graph(ref_config, source=checkout, work=work, version=ref.name)
|
|
625
626
|
_render(
|
|
626
627
|
graph,
|
|
627
628
|
ref_config,
|
|
@@ -55,7 +55,9 @@ def _parser() -> argparse.ArgumentParser:
|
|
|
55
55
|
python_feature_sets = phases.add_parser("feature-sets", help="write feature-sets.json")
|
|
56
56
|
python_feature_sets.add_argument("--source", type=_path, required=True)
|
|
57
57
|
python_feature_sets.add_argument("--output", type=_path, required=True)
|
|
58
|
-
python_manifest = phases.add_parser(
|
|
58
|
+
python_manifest = phases.add_parser(
|
|
59
|
+
"build", help="build one feature set and write manifest.json"
|
|
60
|
+
)
|
|
59
61
|
python_manifest.add_argument("--source", type=_path, required=True)
|
|
60
62
|
python_manifest.add_argument("--feature-set", type=_path, required=True)
|
|
61
63
|
python_manifest.add_argument("--output", type=_path, required=True)
|
|
@@ -160,7 +160,9 @@ def read_manifest(path: Path, *, source: Path) -> Manifest:
|
|
|
160
160
|
if raw.get("cpdocs-manifest") != CONTRACT_VERSION:
|
|
161
161
|
raise ContractError(f"{path}: unsupported cpdocs-manifest {raw.get('cpdocs-manifest')!r}")
|
|
162
162
|
option_metadata = raw.get("options", [])
|
|
163
|
-
if not isinstance(option_metadata, list) or any(
|
|
163
|
+
if not isinstance(option_metadata, list) or any(
|
|
164
|
+
not isinstance(x, dict) for x in option_metadata
|
|
165
|
+
):
|
|
164
166
|
raise ContractError(f"{path}: options must be a list of objects")
|
|
165
167
|
declarations = _units(raw.get("units"), path)
|
|
166
168
|
units: list[UnitManifest] = []
|
|
@@ -202,8 +204,7 @@ def read_manifest(path: Path, *, source: Path) -> Manifest:
|
|
|
202
204
|
)
|
|
203
205
|
options = _mapping(data.get("parse", {}), f"{where}.parse", path)
|
|
204
206
|
parser_language = str(
|
|
205
|
-
options.get("language")
|
|
206
|
-
or ("c" if declaration.language == "c" else "cpp")
|
|
207
|
+
options.get("language") or ("c" if declaration.language == "c" else "cpp")
|
|
207
208
|
)
|
|
208
209
|
if parser_language not in PARSER_LANGUAGES:
|
|
209
210
|
raise ContractError(
|
|
@@ -238,9 +239,7 @@ def read_manifest(path: Path, *, source: Path) -> Manifest:
|
|
|
238
239
|
# Fortran modules carry their public declarations in source files rather than headers.
|
|
239
240
|
# Build-system manifests expose module roots through the semantic ``modules`` field.
|
|
240
241
|
if not api and not modules:
|
|
241
|
-
raise ContractError(
|
|
242
|
-
f"{path}: {where}: a Fortran unit needs an API or modules root"
|
|
243
|
-
)
|
|
242
|
+
raise ContractError(f"{path}: {where}: a Fortran unit needs an API or modules root")
|
|
244
243
|
|
|
245
244
|
units.append(
|
|
246
245
|
UnitManifest(
|
|
@@ -45,7 +45,9 @@ def entity_declaration(entity: ApiEntity) -> str:
|
|
|
45
45
|
|
|
46
46
|
def signature_spelling(entity: ApiEntity, signature: ApiSignature) -> str:
|
|
47
47
|
attribute_spellings = list(
|
|
48
|
-
dict.fromkeys(
|
|
48
|
+
dict.fromkeys(
|
|
49
|
+
attribute.spelling for attribute in signature.attributes if attribute.spelling
|
|
50
|
+
)
|
|
49
51
|
)
|
|
50
52
|
attribute_prefix = " ".join(attribute_spellings)
|
|
51
53
|
if signature.spelling:
|
|
@@ -259,7 +259,9 @@ def extract_fortran_graph(
|
|
|
259
259
|
for value in arguments
|
|
260
260
|
)
|
|
261
261
|
kind = "function" if kind_text.casefold() == "function" else "subroutine"
|
|
262
|
-
returns =
|
|
262
|
+
returns = (
|
|
263
|
+
_declaration_type(prefix) if kind_text.casefold() == "function" else ""
|
|
264
|
+
)
|
|
263
265
|
qualified = f"{module_name}::{name}"
|
|
264
266
|
signature = ApiSignature(
|
|
265
267
|
parameters=parameters,
|
|
@@ -54,7 +54,9 @@ RENDERING = LanguageRendering(
|
|
|
54
54
|
type_like_kinds=frozenset({"derived_type"}),
|
|
55
55
|
function_kinds=frozenset({"function", "subroutine"}),
|
|
56
56
|
member_value_kinds=frozenset({"variable", "attribute", "constant"}),
|
|
57
|
-
source_suffixes=frozenset(
|
|
57
|
+
source_suffixes=frozenset(
|
|
58
|
+
{".f", ".for", ".ftn", ".f77", ".f90", ".f95", ".f03", ".f08", ".f18"}
|
|
59
|
+
),
|
|
58
60
|
kind_markers={
|
|
59
61
|
"module": "M",
|
|
60
62
|
"derived_type": "T",
|
|
@@ -249,6 +249,7 @@ def _ownership(index: dict[str, object]) -> tuple[dict[str, str], set[str], set[
|
|
|
249
249
|
|
|
250
250
|
return owners, inherent_impl_items, trait_impl_items
|
|
251
251
|
|
|
252
|
+
|
|
252
253
|
def build_rust_graph(
|
|
253
254
|
*, rustdoc_json: Path, project: str, version: str = "main", project_root: Path | None = None
|
|
254
255
|
) -> ApiGraph:
|
|
@@ -29,7 +29,9 @@ def signature_spelling(entity: ApiEntity, signature: ApiSignature) -> str:
|
|
|
29
29
|
modifiers = [value for value in entity.properties if value != "pub"]
|
|
30
30
|
visibility = "pub " if "pub" in entity.properties else ""
|
|
31
31
|
modifier_prefix = (" ".join(modifiers) + " ") if modifiers else ""
|
|
32
|
-
value =
|
|
32
|
+
value = (
|
|
33
|
+
f"{visibility}{modifier_prefix}fn {entity.qualified_name}({parameter_spelling(signature)})"
|
|
34
|
+
)
|
|
33
35
|
if signature.returns:
|
|
34
36
|
value += f" -> {signature.returns}"
|
|
35
37
|
return value
|
|
@@ -110,7 +110,9 @@ class ApiGraph:
|
|
|
110
110
|
existing.signature_feature_sets.append([])
|
|
111
111
|
for index, signature in enumerate(entity.signatures):
|
|
112
112
|
incoming = (
|
|
113
|
-
entity.signature_feature_sets[index]
|
|
113
|
+
entity.signature_feature_sets[index]
|
|
114
|
+
if index < len(entity.signature_feature_sets)
|
|
115
|
+
else []
|
|
114
116
|
)
|
|
115
117
|
if signature not in existing.signatures:
|
|
116
118
|
existing.signatures.append(signature)
|
|
@@ -164,9 +164,7 @@ class CpdocsPlugin(BasePlugin):
|
|
|
164
164
|
def _fingerprint(self) -> _Fingerprint:
|
|
165
165
|
return self._fingerprint_paths(self._watched_files())
|
|
166
166
|
|
|
167
|
-
def _subsite_fingerprint(
|
|
168
|
-
self, project: Path, watched_files: list[Path]
|
|
169
|
-
) -> _Fingerprint:
|
|
167
|
+
def _subsite_fingerprint(self, project: Path, watched_files: list[Path]) -> _Fingerprint:
|
|
170
168
|
"""Fingerprint one subsite and cpdocs itself, but not unrelated project docs."""
|
|
171
169
|
|
|
172
170
|
assert self._project_root is not None
|
|
@@ -367,8 +365,7 @@ class CpdocsPlugin(BasePlugin):
|
|
|
367
365
|
)
|
|
368
366
|
if result.returncode != 0:
|
|
369
367
|
raise PluginError(
|
|
370
|
-
f"cpdocs: ProperDocs subsite build failed for {mount.as_posix()}:\n"
|
|
371
|
-
f"{result.stdout}"
|
|
368
|
+
f"cpdocs: ProperDocs subsite build failed for {mount.as_posix()}:\n{result.stdout}"
|
|
372
369
|
)
|
|
373
370
|
_LOG.info("Built ProperDocs subsite %s", mount.as_posix())
|
|
374
371
|
|
|
@@ -75,7 +75,9 @@ def _package(metadata: dict[str, Any], source: Path, package: str | None) -> dic
|
|
|
75
75
|
if package:
|
|
76
76
|
matches = [item for item in packages if item.get("name") == package]
|
|
77
77
|
if len(matches) != 1:
|
|
78
|
-
raise RuntimeError(
|
|
78
|
+
raise RuntimeError(
|
|
79
|
+
f"cpdocs rust: Cargo package {package!r} is not unique in the workspace"
|
|
80
|
+
)
|
|
79
81
|
return matches[0]
|
|
80
82
|
|
|
81
83
|
root_manifest = (source / "Cargo.toml").resolve()
|
|
@@ -186,8 +188,10 @@ def _browse_roots(source: Path, package: dict[str, Any], target: dict[str, Any])
|
|
|
186
188
|
src_path = target.get("src_path")
|
|
187
189
|
if isinstance(src_path, str):
|
|
188
190
|
src = Path(src_path)
|
|
189
|
-
if
|
|
190
|
-
|
|
191
|
+
if (
|
|
192
|
+
src.exists()
|
|
193
|
+
and src not in roots
|
|
194
|
+
and not any(root.is_dir() and root in src.parents for root in roots)
|
|
191
195
|
):
|
|
192
196
|
roots.append(src)
|
|
193
197
|
return [_relative_or_absolute(root, source) for root in roots]
|
|
@@ -261,7 +265,7 @@ def write_manifest(
|
|
|
261
265
|
rustdoc_json = target_dir / "doc" / f"{target_name}.json"
|
|
262
266
|
if not rustdoc_json.is_file():
|
|
263
267
|
raise RuntimeError(
|
|
264
|
-
"cpdocs rust: cargo rustdoc succeeded but did not produce
|
|
268
|
+
f"cpdocs rust: cargo rustdoc succeeded but did not produce {rustdoc_json}"
|
|
265
269
|
)
|
|
266
270
|
|
|
267
271
|
manifest = {
|
|
@@ -52,6 +52,7 @@ def split_qualified(name: str, separator: str) -> list[str]:
|
|
|
52
52
|
def _segments(entity: ApiEntity) -> list[str]:
|
|
53
53
|
return split_qualified(entity.qualified_name, rendering_for(entity.language).separator)
|
|
54
54
|
|
|
55
|
+
|
|
55
56
|
# Operator names as words, longest spelling first, so that ``operator<<`` is not read as ``<``.
|
|
56
57
|
_OPERATOR_WORDS = (
|
|
57
58
|
("<=>", "spaceship"),
|
|
@@ -482,7 +483,8 @@ def _preferred_type_target(name: str, entity: ApiEntity, graph: ApiGraph) -> Api
|
|
|
482
483
|
candidates = [
|
|
483
484
|
candidate
|
|
484
485
|
for candidate in graph.entities.values()
|
|
485
|
-
if candidate.kind in rendering_for(candidate.language).type_like_kinds
|
|
486
|
+
if candidate.kind in rendering_for(candidate.language).type_like_kinds
|
|
487
|
+
and candidate.name == name
|
|
486
488
|
]
|
|
487
489
|
if not candidates:
|
|
488
490
|
return None
|
|
@@ -176,7 +176,9 @@ def _kind_label(kind: str, language: str | None = None) -> str:
|
|
|
176
176
|
|
|
177
177
|
def _kind_badge(kind: str, language: str | None = None) -> str:
|
|
178
178
|
marker = html.escape(_kind_marker(kind, language))
|
|
179
|
-
return
|
|
179
|
+
return (
|
|
180
|
+
f'<span class="api-kind" title="{html.escape(_kind_label(kind, language))}">{marker}</span>'
|
|
181
|
+
)
|
|
180
182
|
|
|
181
183
|
|
|
182
184
|
def _language_label(language: str) -> str:
|
|
@@ -209,7 +211,7 @@ def _feature_set_inline(graph: ApiGraph, key: str) -> str:
|
|
|
209
211
|
features = _feature_set_features(graph, key)
|
|
210
212
|
if not features:
|
|
211
213
|
return '<span class="api-feature-set-empty">default (no features enabled)</span>'
|
|
212
|
-
return " ".join(f
|
|
214
|
+
return " ".join(f"<code>{html.escape(feature)}</code>" for feature in features)
|
|
213
215
|
|
|
214
216
|
|
|
215
217
|
def _legend(graph: ApiGraph) -> str:
|
|
@@ -522,9 +524,7 @@ def _availability(
|
|
|
522
524
|
)
|
|
523
525
|
return (
|
|
524
526
|
'<div class="api-availability"><strong>Available in feature sets</strong>'
|
|
525
|
-
'<ul class="api-availability-list">'
|
|
526
|
-
+ "".join(rows)
|
|
527
|
-
+ "</ul></div>"
|
|
527
|
+
'<ul class="api-availability-list">' + "".join(rows) + "</ul></div>"
|
|
528
528
|
)
|
|
529
529
|
|
|
530
530
|
|
|
@@ -1030,19 +1030,20 @@ def _feature_sets_page(graph: ApiGraph, document: Path) -> tuple[str, list[tuple
|
|
|
1030
1030
|
"</tbody></table></section>",
|
|
1031
1031
|
'<section id="feature-sets" class="api-section"><h2>Feature Sets</h2>',
|
|
1032
1032
|
'<table class="api-feature-set-table">',
|
|
1033
|
-
|
|
1034
|
-
|
|
1033
|
+
"<thead><tr><th>Feature set</th><th>Enabled features</th></tr></thead>",
|
|
1034
|
+
"<tbody>",
|
|
1035
1035
|
]
|
|
1036
1036
|
)
|
|
1037
|
-
toc: list[tuple[str, str, int]] = [
|
|
1037
|
+
toc: list[tuple[str, str, int]] = [
|
|
1038
|
+
("Overview", "overview", 1),
|
|
1039
|
+
("Feature Sets", "feature-sets", 1),
|
|
1040
|
+
]
|
|
1038
1041
|
for index, key in enumerate(graph.feature_sets, 1):
|
|
1039
1042
|
anchor = _feature_set_anchor(key)
|
|
1040
1043
|
body.append(
|
|
1041
1044
|
f'<tr id="{html.escape(anchor)}">'
|
|
1042
1045
|
f'<th scope="row">{index}</th>'
|
|
1043
|
-
|
|
1044
|
-
+ _feature_set_inline(graph, key)
|
|
1045
|
-
+ '</td></tr>'
|
|
1046
|
+
"<td>" + _feature_set_inline(graph, key) + "</td></tr>"
|
|
1046
1047
|
)
|
|
1047
1048
|
body.append("</tbody></table></section>")
|
|
1048
1049
|
# Option metadata are documentation of each resolved build, not extra feature axes.
|
|
@@ -1052,18 +1053,25 @@ def _feature_sets_page(graph: ApiGraph, document: Path) -> tuple[str, list[tuple
|
|
|
1052
1053
|
first = next(iter(graph.feature_sets), None)
|
|
1053
1054
|
options = configurations.get(first, [])
|
|
1054
1055
|
if isinstance(options, list) and options:
|
|
1055
|
-
body.extend(
|
|
1056
|
-
|
|
1057
|
-
|
|
1058
|
-
|
|
1059
|
-
|
|
1060
|
-
|
|
1061
|
-
|
|
1056
|
+
body.extend(
|
|
1057
|
+
[
|
|
1058
|
+
'<section id="configuration-options" class="api-section">',
|
|
1059
|
+
"<h2>Configuration options</h2>",
|
|
1060
|
+
"<p>Effective CMake cache values from the first documented feature set. "
|
|
1061
|
+
"Only project features determine the feature-set combinations above.</p>",
|
|
1062
|
+
"<table><thead><tr><th>Group</th><th>Option</th><th>Value</th><th>Description</th></tr></thead><tbody>",
|
|
1063
|
+
]
|
|
1064
|
+
)
|
|
1062
1065
|
for option in options:
|
|
1063
1066
|
if not isinstance(option, dict):
|
|
1064
1067
|
continue
|
|
1065
|
-
cells = [
|
|
1066
|
-
|
|
1068
|
+
cells = [
|
|
1069
|
+
str(option.get(field, ""))
|
|
1070
|
+
for field in ("group", "name", "value", "description")
|
|
1071
|
+
]
|
|
1072
|
+
body.append(
|
|
1073
|
+
"<tr>" + "".join(f"<td>{html.escape(value)}</td>" for value in cells) + "</tr>"
|
|
1074
|
+
)
|
|
1067
1075
|
body.append("</tbody></table></section>")
|
|
1068
1076
|
toc.append(("Configuration options", "configuration-options", 1))
|
|
1069
1077
|
return "".join(body), toc
|
|
@@ -1100,9 +1108,8 @@ def _source_page(
|
|
|
1100
1108
|
display_path = _display_source_path(source_path, graph)
|
|
1101
1109
|
generated_sources = graph.metadata.get("generated_sources", [])
|
|
1102
1110
|
generated_files = graph.metadata.get("generated_files", [])
|
|
1103
|
-
generated = (
|
|
1104
|
-
|
|
1105
|
-
or (isinstance(generated_files, list) and source_path in generated_files)
|
|
1111
|
+
generated = (isinstance(generated_sources, list) and source_path in generated_sources) or (
|
|
1112
|
+
isinstance(generated_files, list) and source_path in generated_files
|
|
1106
1113
|
)
|
|
1107
1114
|
note = (
|
|
1108
1115
|
'<p class="api-section-intro">Generated by the build; not part of the repository.</p>'
|
|
@@ -293,7 +293,10 @@ def test_renderer_generates_standalone_code_oriented_html_site(tmp_path: Path) -
|
|
|
293
293
|
graph.add(package)
|
|
294
294
|
graph.add(macro)
|
|
295
295
|
graph.sources["dice/version.hpp"] = "#pragma once\nnamespace dice { namespace meta {} }\n"
|
|
296
|
-
graph.feature_sets["feature-set-001"] = {
|
|
296
|
+
graph.feature_sets["feature-set-001"] = {
|
|
297
|
+
"features": ["cpu"],
|
|
298
|
+
"selection": {"features": ["cpu"]},
|
|
299
|
+
}
|
|
297
300
|
graph.metadata = {
|
|
298
301
|
"units": [{"id": "dice", "language": "cpp"}],
|
|
299
302
|
"generator": "test",
|
|
@@ -395,7 +398,10 @@ def test_renderer_generates_standalone_code_oriented_html_site(tmp_path: Path) -
|
|
|
395
398
|
assert "grid-template-columns: 1.45rem minmax(0, 1fr) auto auto" in css
|
|
396
399
|
assert ".api-outline-language { min-width: 0; justify-self: end; overflow: hidden; }" in css
|
|
397
400
|
assert "text-overflow: ellipsis" in css
|
|
398
|
-
assert
|
|
401
|
+
assert (
|
|
402
|
+
'<span class="api-outline-language"><span class="api-language-badge">C++</span></span>'
|
|
403
|
+
in home_page
|
|
404
|
+
)
|
|
399
405
|
assert "border: 1px solid var(--api-border)" in css
|
|
400
406
|
assert '"dice::foo"' in (site / "symbols.json").read_text(encoding="utf-8")
|
|
401
407
|
|
|
@@ -40,7 +40,9 @@ def test_semantic_file_layout_flattens_manifest_roots(tmp_path: Path) -> None:
|
|
|
40
40
|
source.write_text("// source\n", encoding="utf-8")
|
|
41
41
|
|
|
42
42
|
assert _semantic_display_path(header, root=include, generated=False) == "include/kprof/cuda.hpp"
|
|
43
|
-
assert
|
|
43
|
+
assert (
|
|
44
|
+
_semantic_display_path(source, root=library, generated=False) == "lib/kprof/synchronize.cu"
|
|
45
|
+
)
|
|
44
46
|
assert (
|
|
45
47
|
_semantic_display_path(header, root=include, generated=True)
|
|
46
48
|
== "_generated/include/kprof/cuda.hpp"
|
|
@@ -86,7 +88,7 @@ def test_failing_build_command_reports_its_output(tmp_path: Path) -> None:
|
|
|
86
88
|
(project / "docs" / "cpdocs.yml").write_text(
|
|
87
89
|
"contract: 3\nbuild:\n"
|
|
88
90
|
" feature-sets: >-\n python -c \"import sys; print('boom'); sys.exit(3)\"\n"
|
|
89
|
-
|
|
91
|
+
' build: "true"\n',
|
|
90
92
|
encoding="utf-8",
|
|
91
93
|
)
|
|
92
94
|
with pytest.raises(RuntimeError, match="boom"):
|
|
@@ -81,10 +81,22 @@ checks:
|
|
|
81
81
|
("build:\n feature-sets: make\n build: make\n", "contract must be 3"),
|
|
82
82
|
("contract: 3\n", "build.feature-sets"),
|
|
83
83
|
("contract: 3\nbuild:\n feature-sets: [make]\n build: make\n", "command string"),
|
|
84
|
-
(
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
84
|
+
(
|
|
85
|
+
"contract: 3\nbuild:\n feature-sets: make\n build: make\n manifest: make\n",
|
|
86
|
+
"unknown build keys",
|
|
87
|
+
),
|
|
88
|
+
(
|
|
89
|
+
"contract: 3\nbuild:\n feature-sets: make\n build: make\nversions: {tags: all}\n",
|
|
90
|
+
"versions must be a list",
|
|
91
|
+
),
|
|
92
|
+
(
|
|
93
|
+
"contract: 3\nbuild:\n feature-sets: make\n build: make\nversions: [main, main]\n",
|
|
94
|
+
"duplicates",
|
|
95
|
+
),
|
|
96
|
+
(
|
|
97
|
+
"contract: 3\nbuild:\n feature-sets: make\n build: make\nversions: []\n",
|
|
98
|
+
"at least one version",
|
|
99
|
+
),
|
|
88
100
|
],
|
|
89
101
|
)
|
|
90
102
|
def test_invalid_configs_are_rejected(tmp_path: Path, text: str, message: str) -> None:
|
|
@@ -50,14 +50,17 @@ def test_cpp_features_example_documents_every_feature_set(tmp_path: Path) -> Non
|
|
|
50
50
|
return {tuple(graph.feature_sets[key]["features"]) for key in entity.feature_sets}
|
|
51
51
|
|
|
52
52
|
assert feature_sets("struct", "demo::settings") == {(), ("mpi",), ("mpi", "cuda")}
|
|
53
|
-
assert feature_sets("struct", "demo::communicator") == {(
|
|
54
|
-
assert feature_sets("struct", "demo::device") == {(
|
|
53
|
+
assert feature_sets("struct", "demo::communicator") == {("mpi",), ("mpi", "cuda")}
|
|
54
|
+
assert feature_sets("struct", "demo::device") == {("mpi", "cuda")}
|
|
55
55
|
solve = graph.entities[stable_entity_id("cpp", "function", "demo::solve")]
|
|
56
56
|
assert len(solve.signatures) == 3
|
|
57
57
|
by_parameters = {
|
|
58
58
|
signature.compact: (set(feature_sets), signature.documentation)
|
|
59
|
-
for signature, feature_sets in zip(
|
|
59
|
+
for signature, feature_sets in zip(
|
|
60
|
+
solve.signatures, solve.signature_feature_sets, strict=True
|
|
61
|
+
)
|
|
60
62
|
}
|
|
63
|
+
|
|
61
64
|
def resolved(keys: set[str]) -> set[tuple[str, ...]]:
|
|
62
65
|
return {tuple(graph.feature_sets[key]["features"]) for key in keys}
|
|
63
66
|
|
|
@@ -74,13 +77,7 @@ def test_cpp_features_example_documents_every_feature_set(tmp_path: Path) -> Non
|
|
|
74
77
|
|
|
75
78
|
feature_sets = json.loads(
|
|
76
79
|
(
|
|
77
|
-
project
|
|
78
|
-
/ "build"
|
|
79
|
-
/ "cpdocs"
|
|
80
|
-
/ "work"
|
|
81
|
-
/ "current"
|
|
82
|
-
/ "feature-sets"
|
|
83
|
-
/ "feature-sets.json"
|
|
80
|
+
project / "build" / "cpdocs" / "work" / "current" / "feature-sets" / "feature-sets.json"
|
|
84
81
|
).read_text()
|
|
85
82
|
)
|
|
86
83
|
selected = [item["features"] for item in feature_sets["feature-sets"]]
|
|
@@ -202,14 +199,7 @@ def test_cpp_file_hierarchy_includes_implementation_sources(tmp_path: Path) -> N
|
|
|
202
199
|
project, graph = _build(tmp_path, "basic-cpp")
|
|
203
200
|
assert "src/math.cpp" in graph.files
|
|
204
201
|
implementation = (
|
|
205
|
-
project
|
|
206
|
-
/ "build"
|
|
207
|
-
/ "cpdocs"
|
|
208
|
-
/ "current"
|
|
209
|
-
/ "_sources"
|
|
210
|
-
/ "src"
|
|
211
|
-
/ "math.cpp"
|
|
212
|
-
/ "index.html"
|
|
202
|
+
project / "build" / "cpdocs" / "current" / "_sources" / "src" / "math.cpp" / "index.html"
|
|
213
203
|
)
|
|
214
204
|
assert implementation.is_file()
|
|
215
205
|
assert "File: src/math.cpp" in implementation.read_text(encoding="utf-8")
|
|
@@ -16,7 +16,7 @@ from cpdocs.config import load_config
|
|
|
16
16
|
from cpdocs.model import stable_entity_id
|
|
17
17
|
from cpdocs.rendering.common import entity_document
|
|
18
18
|
|
|
19
|
-
PROVIDER = r
|
|
19
|
+
PROVIDER = r"""
|
|
20
20
|
import json, pathlib, sys
|
|
21
21
|
|
|
22
22
|
command = sys.argv[1]
|
|
@@ -48,7 +48,7 @@ else:
|
|
|
48
48
|
}
|
|
49
49
|
output.parent.mkdir(parents=True, exist_ok=True)
|
|
50
50
|
output.write_text(json.dumps(value), encoding="utf-8")
|
|
51
|
-
|
|
51
|
+
"""
|
|
52
52
|
|
|
53
53
|
|
|
54
54
|
def test_same_function_can_have_cpp_and_cuda_definitions(tmp_path: Path) -> None:
|
|
@@ -135,9 +135,7 @@ def test_serve_reuses_cached_subsites_until_their_inputs_change(
|
|
|
135
135
|
del project_arg, mount, strict
|
|
136
136
|
builds.append(destination)
|
|
137
137
|
destination.mkdir(parents=True, exist_ok=True)
|
|
138
|
-
(destination / "index.html").write_text(
|
|
139
|
-
f"build {len(builds)}\n", encoding="utf-8"
|
|
140
|
-
)
|
|
138
|
+
(destination / "index.html").write_text(f"build {len(builds)}\n", encoding="utf-8")
|
|
141
139
|
|
|
142
140
|
monkeypatch.setattr(plugin, "_run_subsite_build", fake_build)
|
|
143
141
|
|
|
@@ -44,39 +44,28 @@ def test_rust_example_uses_disjoint_cargo_features_and_rustdoc_json(tmp_path: Pa
|
|
|
44
44
|
["checked"],
|
|
45
45
|
]
|
|
46
46
|
|
|
47
|
-
vector = graph.entities[
|
|
48
|
-
stable_entity_id("rust", "struct", "rust_geometry::geometry::Vector3")
|
|
49
|
-
]
|
|
47
|
+
vector = graph.entities[stable_entity_id("rust", "struct", "rust_geometry::geometry::Vector3")]
|
|
50
48
|
assert vector.documentation == "A three-dimensional vector."
|
|
51
|
-
dot = graph.entities[
|
|
52
|
-
stable_entity_id("rust", "function", "rust_geometry::geometry::dot")
|
|
53
|
-
]
|
|
49
|
+
dot = graph.entities[stable_entity_id("rust", "function", "rust_geometry::geometry::dot")]
|
|
54
50
|
assert dot.documentation == "Return the dot product of two vectors."
|
|
55
51
|
|
|
56
52
|
dot_many = graph.entities[
|
|
57
53
|
stable_entity_id("rust", "function", "rust_geometry::geometry::dot_many")
|
|
58
54
|
]
|
|
59
|
-
assert {
|
|
60
|
-
|
|
61
|
-
}
|
|
55
|
+
assert {tuple(graph.feature_sets[key]["features"]) for key in dot_many.feature_sets} == {
|
|
56
|
+
("batch",)
|
|
57
|
+
}
|
|
62
58
|
checked_dot = graph.entities[
|
|
63
59
|
stable_entity_id("rust", "function", "rust_geometry::geometry::checked_dot")
|
|
64
60
|
]
|
|
65
|
-
assert {
|
|
66
|
-
|
|
67
|
-
}
|
|
61
|
+
assert {tuple(graph.feature_sets[key]["features"]) for key in checked_dot.feature_sets} == {
|
|
62
|
+
("checked",)
|
|
63
|
+
}
|
|
68
64
|
|
|
69
65
|
assert "src/internal.rs" in graph.files
|
|
70
66
|
assert not any(entity.name == "norm_squared" for entity in graph.entities.values())
|
|
71
67
|
source_page = (
|
|
72
|
-
project
|
|
73
|
-
/ "build"
|
|
74
|
-
/ "cpdocs"
|
|
75
|
-
/ "current"
|
|
76
|
-
/ "_sources"
|
|
77
|
-
/ "src"
|
|
78
|
-
/ "internal.rs"
|
|
79
|
-
/ "index.html"
|
|
68
|
+
project / "build" / "cpdocs" / "current" / "_sources" / "src" / "internal.rs" / "index.html"
|
|
80
69
|
)
|
|
81
70
|
assert source_page.is_file()
|
|
82
71
|
assert "norm_squared" in source_page.read_text(encoding="utf-8")
|