Skip to content

fix(util): log an unsupported enum value once, not on every poll - #897

Open
proscar87 wants to merge 3 commits into
joostlek:mainfrom
proscar87:fix/dedup-unsupported-enum-warnings
Open

proscar87 wants to merge 3 commits into
joostlek:mainfrom
proscar87:fix/dedup-unsupported-enum-warnings

Conversation

@proscar87

@proscar87 proscar87 commented Aug 20, 2026 •

Copy link
Copy Markdown

Addresses the log-spam half of #86.

The problem

to_enum warns every time it sees a value none of DeviceModel,
MeasurementAttribution, WorkoutCategory, etc. can parse — correctly,
since falling back to a default is the right behaviour. On a polled account
with one unmapped device or attribution, that means the identical warning
on every single poll. From #86: rahe71 reported 1,250 occurrences in
5 days
for one undocumented MeasurementAttribution value.

What I checked before proposing this

#86 already has a suggested fix in a comment (UNNAMED_MA_10 = 10, a
placeholder name for the unmapped value). I read the full thread first
rather than take that at face value, and it goes against a stance you've
stated repeatedly across three years there: you keep asking what the value
actually means, and once emailed Withings directly rather than guess —

I need to know what 10 means, but they don't update their docs on time.

So I haven't touched the enum itself, and this doesn't require knowing what
any of these undocumented values mean. What's independently fixable is the
repetition: to_enum now logs a given (enum_class, value) pair once for
the life of the process and silences the repeats, letting the first
occurrence through so it's still there for diagnostics/bug reports.

Validation

  • New tests in tests/test_util.py assert the count of warning records via
    caplog, not just that the call doesn't raise: first occurrence warns,
    repeats of the same value don't, a different value still warns, and a
    different enum class sharing the same numeric value still warns (dedup
    keys on (enum_class, value), not on the value alone).
  • Checked each assertion is load-bearing by reverting the fix: only
    test_to_enum_does_not_repeat_the_same_warning fails against the
    previous version of to_enum, the rest still pass.
  • Tests use a private, throwaway IntEnum rather than a real one from the
    library, and an autouse fixture clears the module-level dedup set before
    each test — otherwise one test's dedup state could silently change
    another's result, since the set is process-global.
  • uv run pytest --cov src tests: 65 passed (was 60), 100% coverage, on
    Python 3.13 and 3.14; same with current main merged in.
  • uv run ruff check / ruff format --check: clean.
  • uv run mypy src tests: clean.
  • The prek hooks the linting workflow runs (codespell, check-ast,
    check-docstring-first, pylint and the builtin checks) and yamllint:
    clean.

🤖 Generated with Claude Code

Fixes the log-spam half of joostlek#86, without guessing at what the value means.

`to_enum` warns every time it sees a value none of DeviceModel,
MeasurementAttribution, WorkoutCategory, etc. can parse -- correctly, since
falling back to a default is the right behaviour. On a polled account with
one unmapped device or attribution, that means the identical warning every
poll: one user reported 1,250 occurrences in 5 days for a single
undocumented value.

Checked before proposing a fix that "just add a placeholder name for it"
(suggested in joostlek#86 as `UNNAMED_MA_10 = 10`) is not what the maintainer wants:
across three years of that thread, joostlek repeatedly asks what the value
actually means and once emailed Withings directly rather than adopt a
guessed name -- "I need to know what 10 means, but they don't update their
docs on time." A placeholder would go against that stance. The complaint
that's actually actionable without knowing the meaning is the repetition,
so this dedupes on (enum_class, value) and lets the first occurrence
through for diagnostics, silencing only the repeats.

Every test asserts the count of warning records, not just that the call
doesn't raise, and checked by reverting the fix: the repeat-suppression
test is the only one that fails against the version without the dedup set.
A private, throwaway enum is used in the tests rather than a real one from
the library, so the dedup state one test populates can't silently change
another test's result -- the module-level set is also reset in an autouse
fixture for the same reason.

Coverage: 100% (65 tests, was 60). ruff, mypy, `uv run pytest --cov`: clean.

Co-Authored-By: Claude Opus 5 (1M context) <noreply@anthropic.com>
@proscar87

Copy link
Copy Markdown
Author

Heads-up: Verify fails only because the PR carries no label, same as #888 before it — I don't have permission to add one. Precedent is bugfix (used for #888, #511). Everything else is green.

@gillmar

gillmar commented Aug 26, 2026

Copy link
Copy Markdown

Heads-up: Verify fails only because the PR carries no label, same as #888 before it — I don't have permission to add one. Precedent is bugfix (used for #888, #511). Everything else is green.

I have the same issue ... I can't add anything, as PR are not labelled ...

@proscar87

Copy link
Copy Markdown
Author

Re-checked against today's main (177611f), since #915 moved the suite from aioresponses to aiointercept after this was opened: it still applies cleanly and the full suite passes — 65 passed with this PR vs 60 on main, the difference being the five new to_enum tests. No change needed on this side.

The only red check is still Verify, which wants a label I can't add (bugfix, as with #888). @gillmar hit the same thing above.

@proscar87
proscar87 force-pushed the fix/dedup-unsupported-enum-warnings branch from 34d48d4 to ed35c8d Compare September 23, 2026 19:13
proscar87 and others added 2 commits October 2, 2026 19:43
The _Color docstring attributed the isolation to a warning in the
project's contribution notes; there is no such text. Say what the
private enum actually guards against: the process-global dedup set
making warning counts depend on test order if a real enum were used.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
The previous wording said a value logged by another test file would
already be in the set when these tests run; the autouse fixture in this
file clears it before each test, so that cannot happen. The real risk is
the other direction: nothing clears the set after these tests, so a real
enum entry left here would silence that warning in later tests.

Co-Authored-By: Claude Opus 5.5 (1M context) <noreply@anthropic.com>
@proscar87

Copy link
Copy Markdown
Author

Correction to my 2026-08-20 comment above: "Everything else is green" was wrong. The Linting, Testing and Typing workflows have not run on this PR; their runs for the current head are waiting for approval (action_required, 0 jobs). Also, #888 carries no label, so it is not a precedent for bugfix; #511 is.

Local results on the current head: uv run pytest --cov src tests gives 65 passed vs 60 on main, with 100% coverage on Python 3.13 and 3.14; ruff check, ruff format --check and mypy src tests are clean.

@joostlek, could you approve the workflow run so CI checks it for real?

This branch has not been deployed

No deployments
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