Skip to content

Commit 0ea887d

Browse files
authored
Merge branch 'main' into diagnostics
2 parents 631cd0a + df183d1 commit 0ea887d

31 files changed

+829
-163
lines changed

CHANGELOG.md

Lines changed: 140 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -2,6 +2,146 @@
22

33
<!-- version list -->
44

5+
## v3.16.1 (2025-12-14)
6+
7+
### Bug Fixes
8+
9+
- Share a HealthManager instance across all mqtt channels
10+
([#672](https://github.com/Python-roborock/python-roborock/pull/672),
11+
[`4ad95dd`](https://github.com/Python-roborock/python-roborock/commit/4ad95ddee4d4d4cd64c7908f150c71d81f45e705))
12+
13+
14+
## v3.16.0 (2025-12-14)
15+
16+
### Bug Fixes
17+
18+
- Fix bugs in the subscription idle timeout
19+
([#665](https://github.com/Python-roborock/python-roborock/pull/665),
20+
[`85b7bee`](https://github.com/Python-roborock/python-roborock/commit/85b7beeb810cfb3d501658cd44f06b2c0052ca33))
21+
22+
- Harden the device connection logic used in startup
23+
([#666](https://github.com/Python-roborock/python-roborock/pull/666),
24+
[`19703f4`](https://github.com/Python-roborock/python-roborock/commit/19703f42fe692a38f8f8639b1136a7585eae76fc))
25+
26+
- Harden the initial startup logic
27+
([#666](https://github.com/Python-roborock/python-roborock/pull/666),
28+
[`19703f4`](https://github.com/Python-roborock/python-roborock/commit/19703f42fe692a38f8f8639b1136a7585eae76fc))
29+
30+
### Chores
31+
32+
- Apply suggestions from code review
33+
([#675](https://github.com/Python-roborock/python-roborock/pull/675),
34+
[`ab2de5b`](https://github.com/Python-roborock/python-roborock/commit/ab2de5bda7b8e1ff1ad46c7f2bf3b39dc9af4ace))
35+
36+
- Clarify comments and docstrings
37+
([#666](https://github.com/Python-roborock/python-roborock/pull/666),
38+
[`19703f4`](https://github.com/Python-roborock/python-roborock/commit/19703f42fe692a38f8f8639b1136a7585eae76fc))
39+
40+
- Fix logging ([#666](https://github.com/Python-roborock/python-roborock/pull/666),
41+
[`19703f4`](https://github.com/Python-roborock/python-roborock/commit/19703f42fe692a38f8f8639b1136a7585eae76fc))
42+
43+
- Reduce whitespace changes ([#666](https://github.com/Python-roborock/python-roborock/pull/666),
44+
[`19703f4`](https://github.com/Python-roborock/python-roborock/commit/19703f42fe692a38f8f8639b1136a7585eae76fc))
45+
46+
- Revert whitespace change ([#666](https://github.com/Python-roborock/python-roborock/pull/666),
47+
[`19703f4`](https://github.com/Python-roborock/python-roborock/commit/19703f42fe692a38f8f8639b1136a7585eae76fc))
48+
49+
### Features
50+
51+
- Add basic schedule getting ([#675](https://github.com/Python-roborock/python-roborock/pull/675),
52+
[`ab2de5b`](https://github.com/Python-roborock/python-roborock/commit/ab2de5bda7b8e1ff1ad46c7f2bf3b39dc9af4ace))
53+
54+
55+
## v3.15.0 (2025-12-14)
56+
57+
### Chores
58+
59+
- Address some comments ([#662](https://github.com/Python-roborock/python-roborock/pull/662),
60+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
61+
62+
- Apply suggestions from code review
63+
([#662](https://github.com/Python-roborock/python-roborock/pull/662),
64+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
65+
66+
- Fix test naming ([#662](https://github.com/Python-roborock/python-roborock/pull/662),
67+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
68+
69+
- Small tweaks ([#662](https://github.com/Python-roborock/python-roborock/pull/662),
70+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
71+
72+
- Update roborock/devices/b01_channel.py
73+
([#662](https://github.com/Python-roborock/python-roborock/pull/662),
74+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
75+
76+
- Update snapshot ([#662](https://github.com/Python-roborock/python-roborock/pull/662),
77+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
78+
79+
### Features
80+
81+
- Add b01 Q7 basic getter support
82+
([#662](https://github.com/Python-roborock/python-roborock/pull/662),
83+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
84+
85+
- Add b01 Q7 support ([#662](https://github.com/Python-roborock/python-roborock/pull/662),
86+
[`b3664bc`](https://github.com/Python-roborock/python-roborock/commit/b3664bcc0764d1dfbde2af9588dc0821c3ca1317))
87+
88+
89+
## v3.14.3 (2025-12-14)
90+
91+
### Bug Fixes
92+
93+
- Allow firmware version as an optional field
94+
([#670](https://github.com/Python-roborock/python-roborock/pull/670),
95+
[`0f70bf9`](https://github.com/Python-roborock/python-roborock/commit/0f70bf9dd2010c2c72b3b9543d891a1071dc22c4))
96+
97+
### Chores
98+
99+
- Add test for example offline device
100+
([#670](https://github.com/Python-roborock/python-roborock/pull/670),
101+
[`0f70bf9`](https://github.com/Python-roborock/python-roborock/commit/0f70bf9dd2010c2c72b3b9543d891a1071dc22c4))
102+
103+
104+
## v3.14.2 (2025-12-14)
105+
106+
### Bug Fixes
107+
108+
- Additional device logging improvements
109+
([#668](https://github.com/Python-roborock/python-roborock/pull/668),
110+
[`a86db71`](https://github.com/Python-roborock/python-roborock/commit/a86db717a07d24b0e6ab471ee814b0853b523918))
111+
112+
- Improve device logging ([#668](https://github.com/Python-roborock/python-roborock/pull/668),
113+
[`a86db71`](https://github.com/Python-roborock/python-roborock/commit/a86db717a07d24b0e6ab471ee814b0853b523918))
114+
115+
### Chores
116+
117+
- Further readability improvements to device logging
118+
([#668](https://github.com/Python-roborock/python-roborock/pull/668),
119+
[`a86db71`](https://github.com/Python-roborock/python-roborock/commit/a86db717a07d24b0e6ab471ee814b0853b523918))
120+
121+
- Improve device logging container summary string
122+
([#668](https://github.com/Python-roborock/python-roborock/pull/668),
123+
[`a86db71`](https://github.com/Python-roborock/python-roborock/commit/a86db717a07d24b0e6ab471ee814b0853b523918))
124+
125+
126+
## v3.14.1 (2025-12-14)
127+
128+
### Bug Fixes
129+
130+
- Fix diagnostic data redaction to use camelized keys
131+
([#669](https://github.com/Python-roborock/python-roborock/pull/669),
132+
[`6a20e27`](https://github.com/Python-roborock/python-roborock/commit/6a20e27506d01fbb30683c2d74d26ab073aa3036))
133+
134+
### Chores
135+
136+
- Remove redundant/broken part of the readme
137+
([#667](https://github.com/Python-roborock/python-roborock/pull/667),
138+
[`b629a61`](https://github.com/Python-roborock/python-roborock/commit/b629a61f28f3bb64914a9bc461ce9f7a27a30c35))
139+
140+
- **deps**: Bump pdoc from 15.0.4 to 16.0.0
141+
([#652](https://github.com/Python-roborock/python-roborock/pull/652),
142+
[`5f4c14e`](https://github.com/Python-roborock/python-roborock/commit/5f4c14ead4eda21cd6954e3898d79a6eaa983f62))
143+
144+
5145
## v3.14.0 (2025-12-14)
6146

7147
### Bug Fixes

pyproject.toml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
[project]
22
name = "python-roborock"
3-
version = "3.14.0"
3+
version = "3.16.1"
44
description = "A package to control Roborock vacuums."
55
authors = [{ name = "humbertogontijo", email = "humbertogontijo@users.noreply.github.com" }, {name="Lash-L"}, {name="allenporter"}]
66
requires-python = ">=3.11, <4"
@@ -51,7 +51,7 @@ dev = [
5151
"freezegun>=1.5.1,<2",
5252
"pytest-timeout>=2.3.1,<3",
5353
"syrupy>=4.9.1,<6",
54-
"pdoc>=15.0.4,<16",
54+
"pdoc>=15.0.4,<17",
5555
"pyyaml>=6.0.3",
5656
"pyshark>=0.6",
5757
"pytest-cov>=7.0.0",

roborock/data/b01_q7/b01_q7_containers.py

Lines changed: 59 additions & 59 deletions
Original file line numberDiff line numberDiff line change
@@ -69,62 +69,62 @@ class B01Props(RoborockBase):
6969
This dataclass is generated based on the device's status JSON object.
7070
"""
7171

72-
status: WorkStatusMapping
73-
fault: B01Fault
74-
wind: SCWindMapping
75-
water: int
76-
mode: int
77-
quantity: int
78-
alarm: int
79-
volume: int
80-
hypa: int
81-
main_brush: int
82-
side_brush: int
83-
mop_life: int
84-
main_sensor: int
85-
net_status: NetStatus
86-
repeat_state: int
87-
tank_state: int
88-
sweep_type: int
89-
clean_path_preference: int
90-
cloth_state: int
91-
time_zone: int
92-
time_zone_info: str
93-
language: int
94-
cleaning_time: int
95-
real_clean_time: int
96-
cleaning_area: int
97-
custom_type: int
98-
sound: int
99-
work_mode: WorkModeMapping
100-
station_act: int
101-
charge_state: int
102-
current_map_id: int
103-
map_num: int
104-
dust_action: int
105-
quiet_is_open: int
106-
quiet_begin_time: int
107-
quiet_end_time: int
108-
clean_finish: int
109-
voice_type: int
110-
voice_type_version: int
111-
order_total: OrderTotal
112-
build_map: int
113-
privacy: Privacy
114-
dust_auto_state: int
115-
dust_frequency: int
116-
child_lock: int
117-
multi_floor: int
118-
map_save: int
119-
light_mode: int
120-
green_laser: int
121-
dust_bag_used: int
122-
order_save_mode: int
123-
manufacturer: str
124-
back_to_wash: int
125-
charge_station_type: int
126-
pv_cut_charge: int
127-
pv_charging: PvCharging
128-
serial_number: str
129-
recommend: Recommend
130-
add_sweep_status: int
72+
status: WorkStatusMapping | None = None
73+
fault: B01Fault | None = None
74+
wind: SCWindMapping | None = None
75+
water: int | None = None
76+
mode: int | None = None
77+
quantity: int | None = None
78+
alarm: int | None = None
79+
volume: int | None = None
80+
hypa: int | None = None
81+
main_brush: int | None = None
82+
side_brush: int | None = None
83+
mop_life: int | None = None
84+
main_sensor: int | None = None
85+
net_status: NetStatus | None = None
86+
repeat_state: int | None = None
87+
tank_state: int | None = None
88+
sweep_type: int | None = None
89+
clean_path_preference: int | None = None
90+
cloth_state: int | None = None
91+
time_zone: int | None = None
92+
time_zone_info: str | None = None
93+
language: int | None = None
94+
cleaning_time: int | None = None
95+
real_clean_time: int | None = None
96+
cleaning_area: int | None = None
97+
custom_type: int | None = None
98+
sound: int | None = None
99+
work_mode: WorkModeMapping | None = None
100+
station_act: int | None = None
101+
charge_state: int | None = None
102+
current_map_id: int | None = None
103+
map_num: int | None = None
104+
dust_action: int | None = None
105+
quiet_is_open: int | None = None
106+
quiet_begin_time: int | None = None
107+
quiet_end_time: int | None = None
108+
clean_finish: int | None = None
109+
voice_type: int | None = None
110+
voice_type_version: int | None = None
111+
order_total: OrderTotal | None = None
112+
build_map: int | None = None
113+
privacy: Privacy | None = None
114+
dust_auto_state: int | None = None
115+
dust_frequency: int | None = None
116+
child_lock: int | None = None
117+
multi_floor: int | None = None
118+
map_save: int | None = None
119+
light_mode: int | None = None
120+
green_laser: int | None = None
121+
dust_bag_used: int | None = None
122+
order_save_mode: int | None = None
123+
manufacturer: str | None = None
124+
back_to_wash: int | None = None
125+
charge_station_type: int | None = None
126+
pv_cut_charge: int | None = None
127+
pv_charging: PvCharging | None = None
128+
serial_number: str | None = None
129+
recommend: Recommend | None = None
130+
add_sweep_status: int | None = None

roborock/data/containers.py

Lines changed: 18 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -228,14 +228,18 @@ class HomeDataProduct(RoborockBase):
228228
def product_nickname(self) -> RoborockProductNickname:
229229
return SHORT_MODEL_TO_ENUM.get(self.model.split(".")[-1], RoborockProductNickname.PEARLPLUS)
230230

231+
def summary_info(self) -> str:
232+
"""Return a string with key product information for logging purposes."""
233+
return f"{self.name} (model={self.model}, category={self.category})"
234+
231235

232236
@dataclass
233237
class HomeDataDevice(RoborockBase):
234238
duid: str
235239
name: str
236240
local_key: str
237-
fv: str
238241
product_id: str
242+
fv: str | None = None
239243
attribute: Any | None = None
240244
active_time: int | None = None
241245
runtime_env: Any | None = None
@@ -263,6 +267,10 @@ class HomeDataDevice(RoborockBase):
263267
share_type: Any | None = None
264268
share_expired_time: int | None = None
265269

270+
def summary_info(self) -> str:
271+
"""Return a string with key device information for logging purposes."""
272+
return f"{self.name} (pv={self.pv}, fv={self.fv}, online={self.online})"
273+
266274

267275
@dataclass
268276
class HomeDataRoom(RoborockBase):
@@ -276,6 +284,15 @@ class HomeDataScene(RoborockBase):
276284
name: str
277285

278286

287+
@dataclass
288+
class HomeDataSchedule(RoborockBase):
289+
id: int
290+
cron: str
291+
repeated: bool
292+
enabled: bool
293+
param: dict | None = None
294+
295+
279296
@dataclass
280297
class HomeData(RoborockBase):
281298
id: int

roborock/devices/README.md

Lines changed: 0 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -124,38 +124,6 @@ graph TB
124124
- **LocalSession**: Factory for creating device-specific local connections
125125
6. **Protocol Layer**: Message encoding/decoding for different device versions
126126
7. **Transport Layer**: Low-level MQTT and TCP communication
127-
LC --> V1P
128-
129-
MS --> MQTT
130-
LC --> TCP
131-
MQTT <--> TCP
132-
133-
style User fill:#e1f5ff
134-
style DM fill:#fff4e1
135-
style V1C fill:#ffe1e1
136-
style RPC fill:#ffe1e1
137-
style MS fill:#e1ffe1
138-
style V1P fill:#f0e1ff
139-
style A01P fill:#f0e1ff
140-
style B01P fill:#f0e1ff
141-
```
142-
143-
### Layer Responsibilities
144-
145-
1. **Device Management Layer**: Detects protocol version (`pv` field) and creates appropriate channels
146-
2. **Device Types**: Different devices based on protocol version (V1, A01, B01)
147-
3. **Traits Layer**: Protocol-specific device capabilities and commands
148-
4. **Channel Layer**: Protocol-specific communication patterns
149-
- **V1**: Full RPC channel with local + MQTT fallback
150-
- **A01/B01**: Helper functions wrapping MqttChannel (MQTT only)
151-
- **MqttChannel**: Per-device wrapper (each device has its own `MqttChannel` instance)
152-
5. **Session Layer**: Connection pooling and subscription management
153-
- **MqttSession**: **Single shared connection** for ALL devices (efficiency!)
154-
- **LocalSession**: Factory for creating device-specific local connections
155-
6. **Protocol Layer**: Message encoding/decoding for different device versions
156-
7. **Transport Layer**: Low-level MQTT and TCP communication
157-
158-
159127

160128
**Important:** All `MqttChannel` instances share the same `MqttSession`, which maintains a single MQTT connection to the broker. This means:
161129
- Only one TCP connection to the MQTT broker regardless of device count

0 commit comments

Comments
 (0)