Skip to content

feat(cdt): implement explicit CDT strip construction#114

Merged
acgetchell merged 3 commits intomainfrom
feat/84-strict-cell-classification
May 5, 2026
Merged

feat(cdt): implement explicit CDT strip construction#114
acgetchell merged 3 commits intomainfrom
feat/84-strict-cell-classification

Conversation

@acgetchell
Copy link
Copy Markdown
Owner

  • Replace the placeholder strip constructor with deterministic layered connectivity, direct time labels, overflow checks, and strict CDT validation.
  • Persist Up/Down cell classifications for explicit strip and toroidal constructors while preserving backend payloads on mutation failures.
  • Update foliation documentation for explicit open-boundary strips and toroidal meshes.
  • Tighten benchmark tooling diagnostics and Python exception boundaries so stdout remains data-only and broad support-script catches stay blocked.

Closes #84

- Replace the placeholder strip constructor with deterministic layered connectivity, direct time labels, overflow checks, and strict CDT validation.
- Persist Up/Down cell classifications for explicit strip and toroidal constructors while preserving backend payloads on mutation failures.
- Update foliation documentation for explicit open-boundary strips and toroidal meshes.
- Tighten benchmark tooling diagnostics and Python exception boundaries so stdout remains data-only and broad support-script catches stay blocked.
@acgetchell acgetchell self-assigned this May 5, 2026
@acgetchell acgetchell enabled auto-merge May 5, 2026 09:01
@codecov
Copy link
Copy Markdown

codecov Bot commented May 5, 2026

Codecov Report

❌ Patch coverage is 78.28162% with 91 lines in your changes missing coverage. Please review.
✅ Project coverage is 92.50%. Comparing base (e3a5504) to head (cdbf363).
⚠️ Report is 4 commits behind head on main.

Files with missing lines Patch % Lines
src/cdt/triangulation.rs 78.17% 91 Missing ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##             main     #114      +/-   ##
==========================================
- Coverage   93.20%   92.50%   -0.71%     
==========================================
  Files          13       13              
  Lines        7625     7883     +258     
==========================================
+ Hits         7107     7292     +185     
- Misses        518      591      +73     
Flag Coverage Δ
unittests 92.50% <78.28%> (-0.71%) ⬇️

Flags with carried forward coverage won't be shown. Click here to find out more.

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.

@coderabbitai
Copy link
Copy Markdown

coderabbitai Bot commented May 5, 2026

Walkthrough

This PR adds an explicit deterministic from_cdt_strip() CDT constructor and strict per-face cell classification/validation, tightens classification and rollback semantics, narrows many broad Python except handlers in benchmark tooling, updates tests/docs, and expands Semgrep scope to cover all scripts/**/*.py.

Changes

Explicit CDT Strip & Strict Cell Classification

Layer / File(s) Summary
Error Normalization / Helpers
src/cdt/triangulation.rs
Adds remap_strip_generation_error() and strip_generation_error() to map explicit-strip/Delaunay failures into CDT-level errors.
Core Constructor
src/cdt/triangulation.rs
Implements from_cdt_strip(vertices_per_slice, num_slices) to build deterministic vertex grid (time labels), explicit Up/Down triangle cells, construct a Delaunay backend from cells, derive foliation, and run full validation.
Count/Validation Utilities
src/cdt/triangulation.rs
Adds validate_strip_counts() to verify produced vertex/face counts and surface detailed mismatches as strip-generation errors.
Classification Logic
src/cdt/triangulation.rs
Adds validate_cell_classification() (public). Rewrites classify_all_cells() to compute all face classifications, clear existing cell payloads, write Up/Down payloads transactionally, and rollback on failure.
Validation Wiring & Accessors
src/cdt/triangulation.rs
validate() now calls validate_cell_classification(); from_foliated_cylinder() delegates to from_cdt_strip() (ignores seed); toroidal path invokes classify_all_cells(). time_label(), edge_type(), cell_type() now guard via self.foliation.as_ref()?.
Tests / Proptests
tests/proptest_foliation.rs, tests in src/cdt/triangulation.rs
Unignores and strengthens unit/property tests: active strip construction test, invariants, edge classification, determinism; adds tests for validation failure cases and foliation/mutation scenarios.
Numeric Conversion
src/cdt/ergodic_moves.rs
Replaces ToPrimitive-based u64→f64 conversion with const fn count as f64, annotated to suppress clippy precision-loss lint.

Python Tooling, Tests & Semgrep

Layer / File(s) Summary
Tooling Warning Output
scripts/benchmark_models.py
Adds import sys and emits the incomplete-benchmark warning to sys.stderr (multi-line).
Exception Narrowing (Core)
scripts/benchmark_utils.py, scripts/performance_analysis.py
Replaces many broad except Exception handlers with site-appropriate exception tuples (e.g., OSError, subprocess.CalledProcessError, subprocess.TimeoutExpired, ExecutableNotFoundError, ValueError, KeyError, json.JSONDecodeError, TypeError, UnicodeError, packaging.version.InvalidVersion, ProjectRootNotFoundError). PerformanceAnalyzer.run_benchmarks now catches OSError instead of all exceptions.
Tests Updated
scripts/tests/test_benchmark_models.py, scripts/tests/test_benchmark_utils.py
Adjusts tests to assert warning output on stderr and replaces generic Exception mocks with subprocess.CalledProcessError instances where appropriate.
Linting Rules & Docs
semgrep.yaml, docs/dev/tooling-alignment.md, docs/foliation.md, docs/project.md
Expands Python Semgrep include scope from /scripts/tests/**/*.py to /scripts/**/*.py; Rust semgrep rule updated to std::f64::.... Docs updated to document from_cdt_strip, from_toroidal_cdt, vertex time-label assignment, face-level causality rules, and stricter classification/validation semantics; tooling-alignment doc now states full scripts/**/*.py coverage.

Sequence Diagram(s)

sequenceDiagram
    participant Caller as Caller
    participant StripCtor as from_cdt_strip()
    participant Delaunay as Delaunay Backend
    participant Foliation as Foliation/Validator
    participant Backend as Backend Cell Storage

    Caller->>StripCtor: request strip(vertices_per_slice, num_slices)
    StripCtor->>StripCtor: build deterministic vertex grid (assign time labels)
    StripCtor->>StripCtor: generate explicit Up/Down cell connectivity
    StripCtor->>Delaunay: build_delaunay2_from_cells(cells)
    Delaunay-->>StripCtor: success / DelaunayGenerationFailed
    StripCtor->>Foliation: construct foliation (fixed slice sizes)
    Foliation->>Foliation: run topology/causality validation
    Foliation->>StripCtor: validation result
    StripCtor->>StripCtor: classify_all_cells() -> compute per-face classification
    StripCtor->>Backend: clear existing cell payloads (transactional)
    Backend-->>StripCtor: success / mutation failure
    StripCtor->>Backend: write Up/Down payloads (rollback on failure)
    Backend-->>StripCtor: final success
    StripCtor-->>Caller: return validated CdtTriangulation
Loading

Estimated code review effort

🎯 4 (Complex) | ⏱️ ~60 minutes

Possibly related PRs

Poem

🐰 I stitched a strip with careful paws,
Up and Down each triangle draws.
Exceptions trimmed, warnings sent to stderr,
Semgrep watches every script and error.
Hopping through tests with joyous cheer,
Our causal mesh stands firm and clear.

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title 'feat(cdt): implement explicit CDT strip construction' clearly and specifically summarizes the main implementation change in the PR.
Description check ✅ Passed The description relates to the changeset by listing specific changes: strip constructor replacement, cell classification persistence, foliation docs updates, and exception boundary tightening.
Linked Issues check ✅ Passed The PR implements strict cell classification by adding validate_cell_classification(), ensuring every triangle classifies as Up or Down, and validating this constraint from CDT construction.
Out of Scope Changes check ✅ Passed All changes align with issue #84 objectives: explicit strip construction, cell classification, foliation documentation updates, and benchmark tooling exception boundary tightening are all within scope.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.

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

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch feat/84-strict-cell-classification

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

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

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: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
docs/project.md (1)

55-60: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

Add validate_cell_classification() to this summary.

CdtTriangulation::validate() now includes the strict Up/Down pass, but this overview still lists only topology/foliation/causality validation. That leaves the project map out of sync with the public API.

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@docs/project.md` around lines 55 - 60, The docs summary is missing
validate_cell_classification() which is now part of
CdtTriangulation::validate(); update the list of Validation methods to include
validate_cell_classification() alongside validate_topology(),
validate_foliation(), and validate_causality(), and briefly describe it as the
strict Up/Down cell classification/validation pass so the documentation matches
the public API.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@docs/foliation.md`:
- Line 16: The intro paragraph contradicts the earlier topology bullets: update
the topology bullets (or their heading) to explicitly state they describe the
periodic case (S¹/cylinder/torus) or expand them to include open-boundary strip
variants; specifically reference the functions from_cdt_strip() and
from_toroidal_cdt() in the text so readers understand from_toroidal_cdt() builds
the periodic S¹×S¹/toroidal case while from_cdt_strip() builds open
spatial-interval (strip) geometries, and adjust the surrounding sentences to
consistently label bullets as “periodic” or “open-boundary” accordingly.

In `@src/cdt/triangulation.rs`:
- Around line 2152-2154: Replace guards that call has_foliation() with direct
checks against the foliation option so stale bookkeeping doesn’t hide an
existing foliation: change any early-return or gate like `if
!self.has_foliation() { return Ok(()); }` (and the other occurrence near the
classify_all_cells()/validate() paths) to `if self.foliation.is_none() { return
Ok(()); }` (or equivalently gate on `self.foliation.is_some()` when proceeding),
since geometry_mut() only clears foliation_synced_at_modification and does not
drop `self.foliation`; update the checks in the methods validate(),
classify_all_cells(), and any similar branches that currently rely on
has_foliation().

---

Outside diff comments:
In `@docs/project.md`:
- Around line 55-60: The docs summary is missing validate_cell_classification()
which is now part of CdtTriangulation::validate(); update the list of Validation
methods to include validate_cell_classification() alongside validate_topology(),
validate_foliation(), and validate_causality(), and briefly describe it as the
strict Up/Down cell classification/validation pass so the documentation matches
the public API.
🪄 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.yml

Review profile: CHILL

Plan: Pro

Run ID: dea87fc9-90b9-411c-b3aa-4bfaabdb70fa

📥 Commits

Reviewing files that changed from the base of the PR and between e3a5504 and ed4b7e6.

📒 Files selected for processing (12)
  • docs/dev/tooling-alignment.md
  • docs/foliation.md
  • docs/project.md
  • scripts/benchmark_models.py
  • scripts/benchmark_utils.py
  • scripts/performance_analysis.py
  • scripts/tests/test_benchmark_models.py
  • scripts/tests/test_benchmark_utils.py
  • semgrep.yaml
  • src/cdt/ergodic_moves.rs
  • src/cdt/triangulation.rs
  • tests/proptest_foliation.rs

Comment thread docs/foliation.md Outdated
Comment thread src/cdt/triangulation.rs Outdated
@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 5, 2026

🔴 Performance Regression Detected

Performance Analysis Report

CDT Performance Analysis Report

Generated: 2026-05-05T09:10:15+00:00

Summary

  • Total benchmarks: 40
  • Regressions: 38
  • Improvements: 1
  • Stable: 1
  • New benchmarks: 0
  • Average change: 19.8%
  • Median change: 19.3%

🔴 Performance Regressions

Benchmark Change Current Baseline Ratio
geometry_queries/iterate_faces +62.9% 313.3ns 192.4ns 1.63x
action_calculations/calculate_action/10 +37.3% 6.8ns 4.9ns 1.37x
edge_counting/uncached/25 +32.6% 1.0µs 755.2ns 1.33x
action_calculations/calculate_action/100 +29.3% 6.4ns 4.9ns 1.29x
geometry_queries/iterate_vertices +29.0% 157.1ns 121.8ns 1.29x
edge_counting/uncached/200 +27.7% 9.0µs 7.1µs 1.28x
simulation_analysis/average_action +27.0% 3.1ns 2.5ns 1.27x
edge_counting/uncached/50 +27.0% 2.0µs 1.6µs 1.27x
edge_counting/uncached/100 +26.5% 4.3µs 3.4µs 1.27x
ergodic_moves/move/EdgeFlip +26.4% 8.8µs 7.0µs 1.26x
triangulation_creation/delaunay_backend/5 +24.4% 71.2µs 57.3µs 1.24x
geometry_queries/euler_characteristic +23.3% 2.1µs 1.7µs 1.23x
ergodic_moves/random_move_attempt +23.0% 8.5µs 6.9µs 1.23x
ergodic_moves/move/Move31Remove +20.8% 7.4µs 6.1µs 1.21x
action_calculations/calculate_action/50 +20.5% 5.9ns 4.9ns 1.20x
triangulation_creation/delaunay_backend/10 +20.1% 384.9µs 320.4µs 1.20x
metropolis_simulation/metropolis_steps/100 +20.0% 11.4ms 9.5ms 1.20x
ergodic_moves/move/Move13Add +19.7% 8.0µs 6.7µs 1.20x
ergodic_moves/move/Move22 +19.5% 8.4µs 7.0µs 1.20x
geometry_queries/iterate_edges +19.4% 3.2µs 2.7µs 1.19x
metropolis_simulation/metropolis_steps/50 +19.3% 4.4ms 3.7ms 1.19x
metropolis_simulation/metropolis_steps/10 +18.4% 1.9ms 1.6ms 1.18x
triangulation_creation/delaunay_backend/20 +15.9% 1.6ms 1.3ms 1.16x
validation/validate +14.6% 374.2µs 326.4µs 1.15x
ergodic_moves/random_move_selection +14.5% 79.0ns 69.0ns 1.15x
geometry_queries/vertex_count +14.2% 0.6ns 0.5ns 1.14x
edge_counting/cached/25 +14.2% 0.6ns 0.5ns 1.14x
edge_counting/cached/50 +14.2% 0.6ns 0.5ns 1.14x
edge_counting/cached/10 +14.2% 0.6ns 0.5ns 1.14x
edge_counting/cached/100 +14.2% 0.6ns 0.5ns 1.14x
edge_counting/cached/200 +14.1% 0.6ns 0.5ns 1.14x
edge_counting/uncached/10 +14.1% 328.1ns 287.6ns 1.14x
geometry_queries/face_count +14.0% 0.6ns 0.5ns 1.14x
triangulation_creation/delaunay_backend/50 +13.5% 8.8ms 7.7ms 1.13x
triangulation_creation/delaunay_backend/100 +13.2% 32.1ms 28.4ms 1.13x
cache_operations/cache_invalidation +13.0% 8.8ms 7.7ms 1.13x
geometry_queries/is_valid +12.9% 280.4µs 248.3µs 1.13x
cache_operations/refresh_cache +12.9% 8.7ms 7.8ms 1.13x

🟢 Performance Improvements

Benchmark Change Current Baseline Ratio
simulation_analysis/equilibrium_measurements -10.4% 23.9ns 26.6ns 1.12x

✅ Stable Benchmarks

No significant changes detected in 1 benchmarks.

⚠️ This PR introduces performance regressions that exceed the threshold. Please review the changes.


Performance analysis powered by Criterion.rs

- Keep live foliation queries and cell classification active when mutable backend access invalidates sync bookkeeping without removing the foliation.
- Clarify periodic and open-boundary CDT foliation docs, including `from_toroidal_cdt()` and `from_cdt_strip()` behavior.
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: 2

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/cdt/triangulation.rs`:
- Around line 1384-1401: The loop still builds huge allocations (vertex_specs
and cells) and creates one heap allocation per triangle; before any pushes use
checked arithmetic on total_vertices/total_cells and call try_reserve on
vertex_specs and cells (or validate against an explicit upper bound) and map
failures to the appropriate CdtError so allocation failures return an error
instead of aborting; replace Vec<Vec<usize>> cells with a flat representation
(e.g., Vec<[usize;3]> or Vec<usize> with 3-per-triangle chunks) to avoid
per-cell heap allocations, and update uses of index, t_count, n,
vertices_per_slice, total_vertices and total_cells accordingly.
- Around line 1410-1420: The check in from_cdt_strip() currently only validates
backend.vertex_count(); also verify the face count matches by asserting
backend.face_count() == total_cells as usize before accepting the strip. Update
the error path (the Err(CdtError::DelaunayGenerationFailed { ... })) to return a
clear message when face_count() differs (similar structure to the existing
vertex_count error), and reference backend.face_count(), total_cells, and the
caller build_delaunay2_from_cells()/from_cdt_strip() to ensure the returned
strip matches the requested vertices_per_slice and num_slices.
🪄 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.yml

Review profile: CHILL

Plan: Pro

Run ID: c46b03d3-a481-476e-964b-66d2b6ed2eac

📥 Commits

Reviewing files that changed from the base of the PR and between ed4b7e6 and 7040ff9.

📒 Files selected for processing (3)
  • docs/foliation.md
  • docs/project.md
  • src/cdt/triangulation.rs
✅ Files skipped from review due to trivial changes (1)
  • docs/project.md
🚧 Files skipped from review as they are similar to previous changes (1)
  • docs/foliation.md

Comment thread src/cdt/triangulation.rs Outdated
Comment thread src/cdt/triangulation.rs Outdated
@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 5, 2026

🔴 Performance Regression Detected

Performance Analysis Report

CDT Performance Analysis Report

Generated: 2026-05-05T15:15:04+00:00

Summary

  • Total benchmarks: 40
  • Regressions: 13
  • Improvements: 2
  • Stable: 25
  • New benchmarks: 0
  • Average change: 9.5%
  • Median change: 5.8%

🔴 Performance Regressions

Benchmark Change Current Baseline Ratio
simulation_analysis/acceptance_rate +142.6% 6.6ns 2.7ns 2.43x
edge_counting/uncached/200 +31.4% 9.3µs 7.1µs 1.31x
edge_counting/uncached/100 +29.8% 4.4µs 3.4µs 1.30x
edge_counting/uncached/50 +27.8% 2.0µs 1.6µs 1.28x
geometry_queries/euler_characteristic +24.3% 2.1µs 1.7µs 1.24x
simulation_analysis/average_action +23.5% 3.0ns 2.5ns 1.23x
edge_counting/uncached/25 +21.5% 917.6ns 755.2ns 1.21x
ergodic_moves/random_move_selection +19.9% 82.7ns 69.0ns 1.20x
action_calculations/calculate_action/100 +17.7% 5.8ns 4.9ns 1.18x
geometry_queries/iterate_edges +17.2% 3.1µs 2.7µs 1.17x
action_calculations/calculate_action/10 +16.6% 5.8ns 4.9ns 1.17x
action_calculations/calculate_action/50 +16.5% 5.7ns 4.9ns 1.17x
edge_counting/uncached/10 +16.3% 334.4ns 287.6ns 1.16x

🟢 Performance Improvements

Benchmark Change Current Baseline Ratio
geometry_queries/face_count -42.1% 0.3ns 0.5ns 1.73x
simulation_analysis/equilibrium_measurements -20.3% 21.2ns 26.6ns 1.26x

✅ Stable Benchmarks

No significant changes detected in 25 benchmarks.

⚠️ This PR introduces performance regressions that exceed the threshold. Please review the changes.


Performance analysis powered by Criterion.rs

- Reserve explicit strip construction buffers fallibly and report CDT generation errors with strip context when allocation fails.
- Keep strip triangles in fixed-size cells until the backend boundary and reject generated backends whose vertex or face counts differ from the requested strip.
@github-actions
Copy link
Copy Markdown

github-actions Bot commented May 5, 2026

🔴 Performance Regression Detected

Performance Analysis Report

CDT Performance Analysis Report

Generated: 2026-05-05T22:17:43+00:00

Summary

  • Total benchmarks: 40
  • Regressions: 40
  • Improvements: 0
  • Stable: 0
  • New benchmarks: 0
  • Average change: 28.1%
  • Median change: 28.6%

🔴 Performance Regressions

Benchmark Change Current Baseline Ratio
edge_counting/uncached/10 +41.4% 406.7ns 287.6ns 1.41x
ergodic_moves/random_move_selection +32.9% 91.7ns 69.0ns 1.33x
ergodic_moves/move/Move31Remove +32.8% 8.1µs 6.1µs 1.33x
ergodic_moves/move/Move13Add +32.6% 8.9µs 6.7µs 1.33x
edge_counting/uncached/50 +32.0% 2.1µs 1.6µs 1.32x
ergodic_moves/move/Move22 +30.5% 9.1µs 7.0µs 1.31x
simulation_analysis/equilibrium_measurements +30.3% 34.7ns 26.6ns 1.30x
edge_counting/uncached/100 +29.7% 4.4µs 3.4µs 1.30x
simulation_analysis/average_action +29.0% 3.2ns 2.5ns 1.29x
edge_counting/cached/50 +28.9% 0.7ns 0.5ns 1.29x
geometry_queries/vertex_count +28.9% 0.7ns 0.5ns 1.29x
ergodic_moves/random_move_attempt +28.9% 8.9µs 6.9µs 1.29x
edge_counting/cached/200 +28.9% 0.7ns 0.5ns 1.29x
edge_counting/cached/100 +28.9% 0.7ns 0.5ns 1.29x
edge_counting/cached/10 +28.9% 0.7ns 0.5ns 1.29x
action_calculations/calculate_action/50 +28.9% 6.3ns 4.9ns 1.29x
edge_counting/cached/25 +28.9% 0.7ns 0.5ns 1.29x
geometry_queries/face_count +28.8% 0.7ns 0.5ns 1.29x
simulation_analysis/acceptance_rate +28.8% 3.5ns 2.7ns 1.29x
triangulation_creation/delaunay_backend/5 +28.7% 73.7µs 57.3µs 1.29x
action_calculations/calculate_action/10 +28.5% 6.3ns 4.9ns 1.28x
geometry_queries/iterate_vertices +28.2% 156.2ns 121.8ns 1.28x
action_calculations/calculate_action/100 +28.2% 6.3ns 4.9ns 1.28x
geometry_queries/iterate_faces +28.1% 246.5ns 192.4ns 1.28x
geometry_queries/iterate_edges +27.9% 3.4µs 2.7µs 1.28x
geometry_queries/euler_characteristic +27.8% 2.1µs 1.7µs 1.28x
edge_counting/uncached/200 +27.7% 9.0µs 7.1µs 1.28x
ergodic_moves/move/EdgeFlip +27.4% 8.9µs 7.0µs 1.27x
edge_counting/uncached/25 +26.8% 957.4ns 755.2ns 1.27x
triangulation_creation/delaunay_backend/10 +26.3% 404.7µs 320.4µs 1.26x
metropolis_simulation/metropolis_steps/50 +25.9% 4.7ms 3.7ms 1.26x
metropolis_simulation/metropolis_steps/100 +25.4% 11.9ms 9.5ms 1.25x
metropolis_simulation/metropolis_steps/10 +25.1% 2.0ms 1.6ms 1.25x
validation/validate +25.1% 408.3µs 326.4µs 1.25x
triangulation_creation/delaunay_backend/20 +24.3% 1.7ms 1.3ms 1.24x
geometry_queries/is_valid +23.5% 306.6µs 248.3µs 1.23x
triangulation_creation/delaunay_backend/100 +22.5% 34.8ms 28.4ms 1.23x
triangulation_creation/delaunay_backend/50 +22.4% 9.5ms 7.7ms 1.22x
cache_operations/refresh_cache +22.3% 9.5ms 7.8ms 1.22x
cache_operations/cache_invalidation +22.3% 9.5ms 7.7ms 1.22x

⚠️ This PR introduces performance regressions that exceed the threshold. Please review the changes.


Performance analysis powered by Criterion.rs

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: 1

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
src/cdt/triangulation.rs (1)

1659-1670: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win

from_toroidal_cdt checks vertex count but skips the face count postcondition.

from_cdt_strip now uses validate_strip_counts to assert both vertex_count() and face_count() match expectations. The toroidal path only verifies the vertex count: if build_toroidal_delaunay2 returns a topologically valid mesh with wrong face count (e.g., merged triangles), the constructor accepts it silently. For a regular N × T torus the invariant is face_count == 2 * total_vertices.

🐛 Proposed fix
     let backend = DelaunayBackend2D::from_triangulation(dt);
     if backend.vertex_count() != total_vertices as usize {
         return Err(CdtError::DelaunayGenerationFailed {
             vertex_count: total_vertices,
             coordinate_range: (0.0, 1.0),
             attempt: 1,
             underlying_error: format!(
                 "explicit toroidal builder produced {} vertices, expected {}",
                 backend.vertex_count(),
                 total_vertices,
             ),
         });
     }
+    let expected_toroidal_faces = 2 * total_vertices as usize;
+    if backend.face_count() != expected_toroidal_faces {
+        return Err(CdtError::DelaunayGenerationFailed {
+            vertex_count: total_vertices,
+            coordinate_range: (0.0, 1.0),
+            attempt: 1,
+            underlying_error: format!(
+                "explicit toroidal builder produced {} faces, expected {}",
+                backend.face_count(),
+                expected_toroidal_faces,
+            ),
+        });
+    }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@src/cdt/triangulation.rs` around lines 1659 - 1670, from_toroidal_cdt
currently only checks backend.vertex_count() but must also assert the expected
face count like from_cdt_strip does via validate_strip_counts; update
from_toroidal_cdt (the path that calls build_toroidal_delaunay2 and inspects
backend) to call validate_strip_counts or manually compare backend.face_count()
against 2 * total_vertices and return a DelaunayGenerationFailed with a
descriptive underlying_error if it mismatches; reference the same error variant
CdtError::DelaunayGenerationFailed and include both vertex_count and face_count
expectations in the error text so failures on merged/incorrect triangles are
caught.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@src/cdt/triangulation.rs`:
- Around line 118-129: strip_generation_error is incorrectly declared as const
fn but moves a heap-allocated String (unsupported in stable Rust); change its
signature to plain fn strip_generation_error(...) -> CdtError and remove the
const qualifier so the function can construct CdtError::DelaunayGenerationFailed
with the underlying_error String at runtime (mirror the non-const pattern used
by remap_toroidal_generation_error and keep the same parameter names and return
type).

---

Outside diff comments:
In `@src/cdt/triangulation.rs`:
- Around line 1659-1670: from_toroidal_cdt currently only checks
backend.vertex_count() but must also assert the expected face count like
from_cdt_strip does via validate_strip_counts; update from_toroidal_cdt (the
path that calls build_toroidal_delaunay2 and inspects backend) to call
validate_strip_counts or manually compare backend.face_count() against 2 *
total_vertices and return a DelaunayGenerationFailed with a descriptive
underlying_error if it mismatches; reference the same error variant
CdtError::DelaunayGenerationFailed and include both vertex_count and face_count
expectations in the error text so failures on merged/incorrect triangles are
caught.
🪄 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.yml

Review profile: CHILL

Plan: Pro

Run ID: 26af1b57-c2d7-438e-be73-620f64cfc3f2

📥 Commits

Reviewing files that changed from the base of the PR and between 7040ff9 and cdbf363.

📒 Files selected for processing (1)
  • src/cdt/triangulation.rs

Comment thread src/cdt/triangulation.rs
@acgetchell acgetchell merged commit ad86eea into main May 5, 2026
15 checks passed
@acgetchell acgetchell deleted the feat/84-strict-cell-classification branch May 5, 2026 22:27
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

feat: strict cell classification (all triangles Up or Down)

1 participant