Skip to content

refactor: split enumerator.py into a subpackage (#197) - #265

Open
iabaako wants to merge 3 commits into
mainfrom
refactor/197-split-enumerator-module
Open

refactor: split enumerator.py into a subpackage (#197)#265
iabaako wants to merge 3 commits into
mainfrom
refactor/197-split-enumerator-module

Conversation

@iabaako

@iabaako iabaako commented Aug 7, 2026

Copy link
Copy Markdown
Contributor

Pull Request Summary 🚀

What does this PR do? 📝

Splits src/datasure/checks/enumerator.py (2,674 lines) into a subpackage, src/datasure/checks/enumerator/:

  • models.py — Pydantic settings/result models and module constants
  • compute.py — pure compute_* data-processing functions (no Streamlit calls)
  • settings_ui.pyenumerator_report_settings and its config-UI helpers
  • report_ui.pyenumerator_report and its report-rendering UI helpers
  • __init__.py — re-exports enumerator_report and enumerator_report_settings

Tests are mirrored into tests/checks/enumerator/{conftest,test_models,test_compute,test_settings_ui,test_report_ui}.py, replacing the 1,921-line tests/checks/test_enumerator.py.

This is the first of four planned splits tracked by #197 (enumerator → gpschecks → outliers → backchecks, smallest to largest), closing out the enumerator portion of that issue.

Why is this change needed? 🤔

Per #197: the largest check modules are hard to navigate and review. enumerator.py mixed settings models, pure computation, and two distinct Streamlit UI flows (settings vs. report) in one file, making it hard to find or safely change any one piece.

How was this implemented? 🛠️

Pure mechanical reorganization — no logic changes. I confirmed by grepping the full src/ tree that only enumerator_report is imported outside this module (by output_view_template.py and generated output_view_N.py files), so __init__.py re-exports it (and enumerator_report_settings, for symmetry) to keep from datasure.checks.enumerator import enumerator_report working with zero changes needed elsewhere. All other functions were module-private and could move freely.

One test needed retargeting: enumerator_report_settings (now in settings_ui.py) calls _render_consent_outcome_settings (now in report_ui.py) — a test that patched that function on the single original module now patches it on settings_ui directly instead. Same test intent, just pointed at the module that now owns the function.

How to test or reproduce ? 🧪

  1. uv run python -m pytest tests/checks/enumerator --cov=datasure.checks.enumerator --cov-report=term-missing -q — 116 tests pass, 99.86% coverage (identical to pre-split numbers)
  2. uv run python -m pytest -q -m "not slow" — full suite passes, same pre-existing skips
  3. Confirm the Enumerator report page in the app still renders and its settings still save/load correctly

Screenshots (if applicable) 📷

N/A — no UI or behavior changes.

Checklist ✅

  • I have run and tested my changes locally
  • I have limit this PR to less than 1000 lines of code change (if not, explain why) — this PR is ~4,700 lines changed, but it is a pure file-move/reorganization with no logic changes; splitting it further would fragment a single mechanical refactor across multiple PRs for no review benefit
  • I have updated/added tests to cover my changes (if applicable)
  • I have updated/added requirements to cover my changes (if applicable)
  • I have run linting and formatting on any code changes (if applicable)
  • I have updated the documentation (README, etc.) accordingly
  • I have reviewed and resolved any merge conflict

🤖 Generated with Claude Code

Splits the 2,674-line checks/enumerator.py into models/compute/
settings_ui/report_ui submodules so it's easier to navigate and
review. The public entry points (enumerator_report,
enumerator_report_settings) stay importable from
datasure.checks.enumerator unchanged. Tests are mirrored into
tests/checks/enumerator/ with no logic changes.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
@iabaako
iabaako requested a review from a team as a code owner August 7, 2026 16:30
Comment thread tests/checks/enumerator/test_report_ui.py Dismissed
Comment thread tests/checks/enumerator/test_settings_ui.py Dismissed
iabaako and others added 2 commits August 7, 2026 16:52
…e __init__

Every other package __init__.py in this repo is empty; re-exporting
symbols there hides which submodule actually defines them. Import
enumerator_report directly from checks.enumerator.report_ui instead.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
…r module

Sonar flagged code duplication above the 3% threshold in compute.py
(10.4%) and settings_ui.py (3.6%). Extracts the shared "TIME PERIOD"
column logic used by both productivity and statistics-overtime
computation into _add_time_period_column, and the repeated
selectbox/save patterns in the settings UI into _render_column_select
and _render_category_settings. No behavior change.

Co-Authored-By: Claude Sonnet 5 <noreply@anthropic.com>
@sonarqubecloud

sonarqubecloud Bot commented Aug 7, 2026

Copy link
Copy Markdown

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.

Split oversized check modules (post-1.0)

1 participant