Skip to content

Match the whole value in env2bool - #11082

Open
shashvat-singham wants to merge 1 commit into
treeverse:mainfrom
shashvat-singham:fix/env2bool-whole-value
Open

Match the whole value in env2bool#11082
shashvat-singham wants to merge 1 commit into
treeverse:mainfrom
shashvat-singham:fix/env2bool-whole-value

Conversation

@shashvat-singham

Copy link
Copy Markdown

Fixes #11080

env2bool decided truthiness with an unanchored re.search, so any value that merely contained 1, y, yes or true was treated as true:

DVC_EXP_AUTO_PUSH=my_path   -> True    # contains "y"
DVC_EXP_AUTO_PUSH=anything  -> True    # contains "y"
DVC_EXP_AUTO_PUSH=v1.0      -> True    # contains "1"
DVC_EXP_AUTO_PUSH=nay       -> True    # contains "y"

It was also asymmetric in a way that's hard to reason about: no is correctly false, but nay is true.

This matters because these are user-facing environment variables where the input is arbitrary text — DVC_EXP_AUTO_PUSH, DVC_SQLALCHEMY_ECHO, DVC_IGNORE_ISATTY, DVC_TEST. The likely way to hit it is a value meant to be negative that happens to contain a matching letter, or a non-boolean value put in one of these by mistake, which silently switches the feature on instead of being ignored.

Change

Compare the whole value, after strip() and lower(), against the set of accepted affirmatives.

Every value that was intentionally supported still works (1, y, yes, true, and case/whitespace variants); only substring matches stop being truthy. The undefined= behaviour for an unset variable is unchanged.

Note this is technically a behaviour change for anyone currently relying on a loose value being truthy — but since that path is indistinguishable from "user set something that isn't a boolean", tightening it seems clearly right. Happy to add a warning on unrecognised values instead if you'd prefer a softer landing.

Tests

test_env2bool is parametrised over the accepted affirmatives, the common negatives, and the five substring cases above; test_env2bool_undefined pins the unset behaviour.

$ pytest tests/unit/utils/test_utils.py -k env2bool
17 passed

Five of them fail on main.

Fixes treeverse#11080

env2bool used re.search, so any value merely containing "1", "y", "yes"
or "true" was truthy:

    DVC_EXP_AUTO_PUSH=my_path   -> True   (contains "y")
    DVC_EXP_AUTO_PUSH=v1.0      -> True   (contains "1")
    DVC_EXP_AUTO_PUSH=nay       -> True   (contains "y")

while "no" was correctly false, so the behaviour was also asymmetric in
a confusing way. These are user-facing environment variables
(DVC_EXP_AUTO_PUSH, DVC_SQLALCHEMY_ECHO, DVC_IGNORE_ISATTY, DVC_TEST),
so the input really is arbitrary user text.

Compare the whole value instead, after stripping and lowercasing. Every
value that was intentionally supported still works; only substring
matches stop being truthy.
@github-project-automation github-project-automation Bot moved this to Backlog in DVC Aug 16, 2026
@CLAassistant

CLAassistant commented Aug 16, 2026

Copy link
Copy Markdown

CLA assistant check
All committers have signed the CLA.

@codecov

codecov Bot commented Aug 16, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 90.98%. Comparing base (2431ec6) to head (b4499a1).
⚠️ Report is 213 commits behind head on main.

Additional details and impacted files
@@            Coverage Diff             @@
##             main   #11082      +/-   ##
==========================================
+ Coverage   90.68%   90.98%   +0.30%     
==========================================
  Files         504      505       +1     
  Lines       39795    41146    +1351     
  Branches     3141     3263     +122     
==========================================
+ Hits        36087    37436    +1349     
- Misses       3042     3071      +29     
+ Partials      666      639      -27     

☔ View full report in Codecov by Harness.
📢 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.

@shashvat-singham

Copy link
Copy Markdown
Author

On the red lint checks — they're pre-existing on main, not from this PR.

The failing pre-commit hook is mypy, and the error is in a file this PR doesn't touch:

dvc/commands/completion.py:20:63: error: Argument "preamble" to "complete" has ...

The same hook fails with the same error on main's latest run (job 95098111969), across all three OSes.

Everything else in pre-commit passes on the changed files here — ruff check, ruff format, codespell, end-of-file/line-ending/whitespace hooks. Happy to rebase once main is green if you'd like a clean run.

@shashvat-singham

Copy link
Copy Markdown
Author

Note on the red lint jobs: they are not from this change.

pre-commit fails at the mypy hook on dvc/commands/completion.py:20Argument "preamble" to "complete" has incompatible type "dict[str, str]"; expected "str" — a file this PR does not touch. The same three lint jobs (ubuntu/macos/windows) fail identically on main at the base commit, so it is pre-existing rather than something the branch introduced.

Everything else in the run, including ruff check, ruff format and the env2bool tests, passes.

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.

env2bool matches its truthy pattern as a substring, so unrelated values read as true

2 participants