Summary
Deferred follow-up from #95 (comprehensive repo evaluation, batch 6: architecture cleanup).
Pydantic computed_field properties in src/nwp500/models/status.py, models/feature.py, models/schedule.py, and models/tou.py read the current unit-system preference from the module-level contextvars.ContextVar in unit_system.py at access time. This makes the computed values implicitly dependent on ambient async-context state rather than being pure functions of the model's own fields, which can be surprising: reading the same model instance's computed field from two different contexts (e.g. two concurrent async tasks with different unit preferences) yields different results, and the coupling makes the models harder to test/reason about in isolation.
Suggested approach
- Consider making unit preference an explicit, model-level or call-site parameter (e.g.
status.temperature(unit_system=...) as a method) rather than an implicit computed_field reading ambient context.
- Alternatively, if the contextvars-based approach is kept for ergonomics, document the async-context-aware behavior prominently on each affected model and add tests that exercise cross-context reads to lock in the intended semantics.
- Evaluate whether this is a breaking change requiring a major version bump per the project's versioning policy.
Acceptance criteria
- Clear, intentional design for how unit-system preference flows into computed fields (either removed as an implicit dependency, or explicitly documented and tested).
- Existing computed-field behavior covered by tests reflecting the chosen design.
ruff/mypy clean.
Summary
Deferred follow-up from #95 (comprehensive repo evaluation, batch 6: architecture cleanup).
Pydantic
computed_fieldproperties insrc/nwp500/models/status.py,models/feature.py,models/schedule.py, andmodels/tou.pyread the current unit-system preference from the module-levelcontextvars.ContextVarinunit_system.pyat access time. This makes the computed values implicitly dependent on ambient async-context state rather than being pure functions of the model's own fields, which can be surprising: reading the same model instance's computed field from two different contexts (e.g. two concurrent async tasks with different unit preferences) yields different results, and the coupling makes the models harder to test/reason about in isolation.Suggested approach
status.temperature(unit_system=...)as a method) rather than an implicitcomputed_fieldreading ambient context.Acceptance criteria
ruff/mypyclean.