test: pin two-solver distribution contract + transforms/gauss/ply-angles coverage - #193
Merged
Merged
Conversation
…ranches The shared ply-angle resolver (porosity_fe/_ply_angles.py) was the lowest-covered module at 78%: lines 74-80 — the ``ply_angles=None`` + ``none_means='UD'`` / ``'UD_legacy'`` / unsupported-value branches — were reached by no caller and no test, since EmpiricalSolver, CompositeMesh and FESolver all funnel through the helper with the production ``none_means='QI'`` (#44 item 2). Add tests/test_ply_angles.py: a direct unit test of the helper that pins its full documented contract — the 'QI'/'UD' sentinels (incl. case-insensitivity), the unknown-sentinel ValueError (with caller/value in the message), explicit list/tuple -> list-of-floats conversion, the fresh-copy guarantee, the warning-free non-None paths, and the None back-compat shim across every ``none_means`` value (QI default, UD, UD_legacy -> None, and the internal-error guard for an unsupported value). Brings porosity_fe/_ply_angles.py to 100% line coverage. Test-only change; full suite 679 passed, 1 skipped. https://claude.ai/code/session_01UNYASptPBqZmWLZe2h9fi9
…y tests Add behavioural and property tests for three thinly-covered areas: - tests/test_solver_distribution_contract.py — pins the architectural "two solver paths, one mesh" claim. EmpiricalSolver.get_failure_load is bitwise-identical across uniform/clustered/interface at a fixed mean Vp (the knockdown is evaluated at the specimen-average Vp), while FESolver.max_failure_index is distribution-sensitive because per-element degradation picks up the clustered / interface hot-spots. Guards both directions so a refactor can't make the empirical path shape-sensitive or the FE path shape-blind. - tests/test_transforms.py — property tests for the 3D rotation helpers: rotation-matrix orthonormality and unit determinant, the negative-angle inverse, the Reuter stress/strain energy-conjugacy duality, stiffness round-trip recovery, preserved symmetry, isotropic rotation-invariance, and the 90-degree in-plane axis swap. - tests/test_gauss.py — property tests for Gauss-Legendre quadrature: weights sum to the domain measure, symmetric interior abscissae, exact to degree 2n-1 and inexact at 2n, and the tensor-product hex rule. Net: 153 new tests. gauss.py 95%->100%; transforms.py pinned at 100% with a dedicated module. Full suite 832 passed, 1 skipped; ruff clean. https://claude.ai/code/session_013VsFb2DFwpNaEvXo2VC6hy
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
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
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.
Summary
Adds four test modules that harden the repository's most architecturally load-bearing and thinly-covered areas. Test-only change — no production code touched.
1.
tests/test_solver_distribution_contract.py— the two-solver contractPorosityFE runs two solver paths over the same mesh that are designed to disagree on the effect of porosity distribution shape (CLAUDE.md, "Two solver paths, one mesh"). These tests pin that contract:
EmpiricalSolveris distribution-invariant —get_failure_loadevaluates the knockdown at the specimen-averageVp, souniform/clustered/interfacegive bitwise-identical failure stress and knockdown at fixed meanVp(verified across 5 loading modes).FESolveris distribution-sensitive — per-element degradation picks up clustered/interface hot-spots, somax_failure_indexmaterially differs (clustered/interface worse than uniform).2.
tests/test_transforms.py— rotation property testsThe 3D rotation helpers were exercised only indirectly through the FE path. Pins: rotation-matrix orthonormality + unit determinant, negative-angle inverse, the Reuter stress/strain energy-conjugacy duality (
T_ε^T = T_σ⁻¹), stiffness round-trip recovery, preserved symmetry, isotropic rotation-invariance, and the 90° in-plane axis swap (C₁₁↔C₂₂).3.
tests/test_gauss.py— quadrature property testsPins the defining Gauss-Legendre contract: weights sum to the domain measure, symmetric interior abscissae, exact to degree 2n−1 and inexact at 2n, and the tensor-product hex rule. Covers the previously-untested
n=1branch.4.
tests/test_ply_angles.py— recovered from stale branchesDirect unit test of the shared
_resolve_ply_angleshelper (_ply_angles.py78%→100%, previously the largest coverage gap). Recovered byte-identical from the duplicate branchesclaude/ply-angles-tests/claude/blissful-albattani-lsj98h, which can be deleted once this lands.Coverage / verification
gauss.py95%→100%,transforms.pyand_ply_angles.pypinned at 100% with dedicated modules.ruff check .clean.https://claude.ai/code/session_013VsFb2DFwpNaEvXo2VC6hy
Generated by Claude Code