Skip to content

fix(strategies): use is not None for strategy presence checks (#2307)#2328

Closed
jbbqqf wants to merge 1 commit into
unionai-oss:mainfrom
jbbqqf:bugfix/2307-strategy-is-not-none
Closed

fix(strategies): use is not None for strategy presence checks (#2307)#2328
jbbqqf wants to merge 1 commit into
unionai-oss:mainfrom
jbbqqf:bugfix/2307-strategy-is-not-none

Conversation

@jbbqqf
Copy link
Copy Markdown

@jbbqqf jbbqqf commented May 9, 2026

Summary

Three remaining if strategy: truthiness checks in pandera/strategies/pandas_strategies.py test for a chained parent strategy. Hypothesis strategies implement __bool__ to raise HypothesisWarning ("bool(from_dtype(...)) is always True, did you mean to draw a value?"), so the truthy form is incorrect (and silently emits the warning) when a real strategy is supplied. Switch the three sites to the explicit is not None form, matching the convention already used elsewhere in the same module.

Resolves #2307.

Context

The reporter (#2307) cited two sites at lines 832 and 1055 that have already been migrated to is None / is not None. Three remained:

  • pandera/strategies/pandas_strategies.py:1244series_strategy entry-point
  • pandera/strategies/pandas_strategies.py:1571dataframe_strategy entry-point
  • pandera/strategies/pandas_strategies.py:1843multiindex_strategy entry-point

These are base-strategy entry-points that raise BaseStrategyOnlyError when a parent strategy is supplied (it's a usage error to chain a parent onto a base strategy). The fix is one-token-per-site: if strategy:if strategy is not None:.

Changes

  • pandera/strategies/pandas_strategies.py: three if strategy:if strategy is not None: rewrites, plus a one-shot comment at the first site explaining why (so a future contributor doesn't "simplify" it back).
  • tests/strategies/test_strategies.py: structural regression test that scans the module source and asserts no if strategy: lines remain. The test fails on origin/main and passes on this branch.

A behavioural test would only fire when a caller passes a parent strategy (which is itself a usage error) — the structural test is a closer fit for the actual contract this PR enforces.

Reproduce BEFORE/AFTER yourself (copy-paste)

# --- one-time setup ---
git clone https://github.com/unionai-oss/pandera.git /tmp/repro && cd /tmp/repro

# --- BEFORE (origin/main) ---
git checkout origin/main
grep -nE "^\s*if strategy:\s*$" pandera/strategies/pandas_strategies.py | wc -l
# Expected: 3 (three remaining truthiness checks)

# --- AFTER (this PR) ---
git fetch https://github.com/jbbqqf/pandera.git bugfix/2307-strategy-is-not-none
git checkout FETCH_HEAD
grep -nE "^\s*if strategy:\s*$" pandera/strategies/pandas_strategies.py | wc -l
# Expected: 0 (all three migrated to ``if strategy is not None:``)

What I ran locally

  • pytest tests/strategies/test_strategies.py::test_strategy_truthiness_check_uses_is_not_none -v → 1/1 passed.
  • Verified the same test fails on origin/main (3 remaining matches reported).

The pre-existing with pytest.raises(BaseStrategyOnlyError) cases at lines 532, 692, 731 of tests/strategies/test_strategies.py exercise the non-None code path and continue to pass — is not None is logically equivalent to truthiness for the only valid input shape (a real SearchStrategy instance).

Edge cases tested

# Scenario Expected Verified by
1 All three migrated sites use is not None structural scan returns 0 matches new regression test
2 Existing parent-strategy callers still raise BaseStrategyOnlyError unchanged behaviour pre-existing tests at lines 532, 692, 731
3 Default-argument call (strategy=None) doesn't raise no warning, no error pre-existing strategy-draw tests

Risk / blast radius

Three identical edits in one module. The new condition is logically equivalent for all observed inputs (None and a SearchStrategy subclass), the latter being the only thing that ever reaches these branches.


PR drafted with assistance from Claude Code. The change was reviewed manually against pandera's strategies module and against the HypothesisWarning quoted in #2307.

…ionai-oss#2307)

Hypothesis strategies implement ``__bool__`` to raise HypothesisWarning
("bool(from_dtype(...)) is always True, did you mean to draw a value?").
Three remaining call sites in pandera/strategies/pandas_strategies.py
write ``if strategy:`` to test whether a chained parent strategy was
supplied. While harmless when called with the default ``strategy=None``,
the truthiness check is incorrect when a caller passes a real hypothesis
strategy (the entry-points are base-strategy-only and raise
BaseStrategyOnlyError in that case anyway) and silently emits the
warning before the error fires.

Switch to the explicit ``is not None`` form, matching the convention
already used elsewhere in the same module. Add a structural regression
test that fails on origin/main and passes on this branch.

Co-Authored-By: Claude Code <noreply@anthropic.com>
Signed-off-by: jbb <jbaptiste.braun@gmail.com>
@codecov
Copy link
Copy Markdown

codecov Bot commented May 10, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 83.51%. Comparing base (378b2de) to head (e027fa3).

Additional details and impacted files
@@           Coverage Diff           @@
##             main    #2328   +/-   ##
=======================================
  Coverage   83.51%   83.51%           
=======================================
  Files         190      190           
  Lines       16613    16613           
=======================================
  Hits        13875    13875           
  Misses       2738     2738           

☔ 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.

@jbbqqf jbbqqf closed this May 24, 2026
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.

Avoid strategy truthiness checks in pandas_strategies to prevent HypothesisWarning

1 participant