Skip to content

Expose designed-mode comparison as the sensory_compare_products agent tool#473

Open
kgdunn wants to merge 3 commits into
mainfrom
claude/stability-study-analysis-lrk3u0
Open

Expose designed-mode comparison as the sensory_compare_products agent tool#473
kgdunn wants to merge 3 commits into
mainfrom
claude/stability-study-analysis-lrk3u0

Conversation

@kgdunn

@kgdunn kgdunn commented Jul 24, 2026

Copy link
Copy Markdown
Owner

Summary

  • Adds sensory_compare_products, a @tool_spec agent-callable wrapper over process_improve.sensory.compare_products (merged in Add designed-mode panel comparison (factorial ANOVA + Tukey/Dunnett post-hoc) #471), so the designed-treatment factorial ANOVA + Tukey HSD / Dunnett-vs-control post-hoc is available as a JSON-in / JSON-out tool alongside the existing sensory_reshape_to_long / sensory_validate_descriptive / sensory_analyze_descriptive / sensory_panel_check tools, and through the MCP server (get_sensory_tool_specs()).
  • Inputs are panel row-records plus factors / block / primary / within / control / interactions / alpha / conf_level; the result carries the ANOVA table, Tukey and Dunnett contrasts, the compact-letter display, per-level means, and the resolved config. NaN cells (e.g. the Residual row's F/p) are cleaned to null so the payload is JSON-serialisable.
  • Missing required columns return {ok: false, errors: [...]} (mirroring sensory_panel_check); factor/level errors from the underlying call are surfaced the same way.

Test plan

  • uv run pytest tests/test_sensory.py -k compare_products --no-cov (2 tests): drives the tool through execute_tool_call, asserts the payload is JSON-serialisable, that it recovers a planted formulation-by-condition interaction (T2 collapses only under HB in the letter display) and the Dunnett-vs-control flags, and that missing columns are rejected.
  • sensory_compare_products appears in get_sensory_tool_specs() (MCP discovery).
  • uv run ruff check . -> All checks passed; uv run mypy src/process_improve clean.
  • Note: tests/test_tool_spec.py::...::test_registered_in_registry is a pre-existing xdist + --new-first ordering flake (fails identically on clean main in a local run, green in CI); this PR does not touch it.

Checklist

  • Version bumped in pyproject.toml (MINOR: new agent-tool API surface), 1.60.0 -> 1.61.0
  • Tests added or updated where relevant
  • ruff check . passes
  • CHANGELOG.md updated (and CITATION.cff version synced)

Generated by Claude Code

… tool

Add a @tool_spec wrapper (sensory_compare_products) over
process_improve.sensory.compare_products, so the designed-treatment factorial
ANOVA + Tukey/Dunnett post-hoc is callable as a JSON-in / JSON-out agentic
tool alongside the existing sensory_* tools and through the MCP server. Inputs
are panel row-records plus the factor/block/within/control arguments; the
result carries the ANOVA table, Tukey and Dunnett contrasts, the compact-letter
display and per-level means (NaN cleaned to null for JSON).

Tests in tests/test_sensory.py drive it through execute_tool_call and assert it
recovers a planted formulation-by-condition interaction and the Dunnett flags.
Version bump 1.60.0 -> 1.61.0 with matching CITATION.cff and CHANGELOG entry.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018Ra2KAdJeGtnUzi68yDFaR
@codecov

codecov Bot commented Jul 24, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

claude added 2 commits July 24, 2026 07:50
…anches

Include the optional `within` column in the missing-columns guard so a bad
`within` returns a clean {ok: false} error instead of raising outside the
try/except. Add tests for the pooled single-factor / no-block path (empty
Dunnett, 'stratum' column) and the bad-within error path, lifting patch
coverage over the previously untested branches.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018Ra2KAdJeGtnUzi68yDFaR
Add a test where a bad 'primary' passes the column guard but makes the
underlying compare_products raise, exercising the tool's (KeyError, ValueError)
handler that returns {ok: false}. Closes the last uncovered lines in the wrapper.

Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
Claude-Session: https://claude.ai/code/session_018Ra2KAdJeGtnUzi68yDFaR
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.

2 participants