feat(domains): add Fan domain (#37)#69
Merged
Merged
Conversation
Add a typed Fan domain accessor exposing intent-specific methods for fan control rather than raw service calls. State properties: is_on, percentage, preset_mode, preset_modes, oscillating, direction, plus supports_set_speed / supports_oscillate / supports_direction / supports_preset_mode for capability introspection. Actions: on, off, toggle, set_percentage, set_preset_mode, set_direction, oscillate. set_percentage validates the 0-100 range; set_direction validates against forward/reverse; set_preset_mode rejects modes not in preset_modes. Listener decorators: on_turn_on, on_turn_off, on_speed_change, on_direction_change. Optional actions degrade safely against FanEntityFeature bits in supported_features (SET_SPEED, OSCILLATE, DIRECTION, PRESET_MODE): calls become a debug-logged no-op rather than raising when the feature is not advertised, keeping user code portable across heterogeneous fan hardware.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Closes #37.
Issue validity assessment
Valid and clearly actionable. The request fits the project's design priorities (typed domain accessors, intent-specific methods, graceful degradation) and matches the structure used by existing domains such as
Humidifier,Vacuum, andCover. No ambiguity required clarification.Fix
New
Fandomain insrc/haclient/domains/fan.py, registered throughDomainSpecsoclient.fan("...")resolves automatically.State properties
is_on,percentage,preset_mode,preset_modes,oscillating,directionsupports_set_speed,supports_oscillate,supports_direction,supports_preset_modefor capability introspectionActions
on(),off(),toggle()— unconditional, like every other on/off domainset_percentage(int)— validates 0–100, gated onSET_SPEEDset_preset_mode(str)— gated onPRESET_MODEandpreset_modes, raisesValueErrorfor modes not in the listset_direction(str)— validatesforward/reverse, gated onDIRECTIONoscillate(bool)— gated onOSCILLATEListener decorators
on_turn_on,on_turn_off,on_speed_change,on_direction_changeGraceful degradation
Optional actions check the
FanEntityFeaturebitmask insupported_features(SET_SPEED=1,OSCILLATE=2,DIRECTION=4,PRESET_MODE=8) before dispatching. When the feature is missing they emit a debug log and return without raising, matching the pattern already used byVacuum.Tests / checks run
pytest tests/ --cov=haclient --cov-report=term-missing --cov-fail-under=95— 285 passed, total coverage 97.08%,domains/fan.pyat 100% (covers full-featured actions, range / direction / preset-mode validation, all degradation no-op paths, missing/malformed attribute handling, and listener decorators).ruff check src tests— clean.ruff format --check src tests— clean.mypy src— clean (strict mode, no issues found in 37 source files).