Skip to content
Merged

2025.12.4 #159460

Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
42 commits
Select commit Hold shift + click to select a range
6755073
Prevent empty aliases in registries (#156061)
FI-153 Dec 15, 2025
d0aaac0
Do not check Reolink firmware at start (#158275)
starkillerOG Dec 16, 2025
73484cb
Update pynintendoparental to 2.0.0 (#158285)
pantherale0 Dec 9, 2025
81d10d0
Enable volvo engine status for all engine types (#158437)
thomasddn Dec 9, 2025
4cced81
Update pynintendoparental to 2.1.0 (#158487)
pantherale0 Dec 9, 2025
5d30fc3
Suppress roborock failures under some unavailability threshold (#158673)
allenporter Dec 13, 2025
b7d4c3c
Suppress verbose UPnP subscription error logs (#158677)
ptarjan Dec 18, 2025
73734d2
Fix Sonos speaker async_offline assertion failure (#158764)
ptarjan Dec 18, 2025
8ee94f8
Bump pynintendoparental to 2.1.1 (#158779)
pantherale0 Dec 12, 2025
7714b51
Bump aioasuswrt 1.5.3 (#158882)
kennedyshead Dec 13, 2025
581919c
Revert adding entity_category to Plugwise thermostat schedule select …
bouwew Dec 13, 2025
8902ba9
Bump aiomealie to 1.1.1 and statically define mealplan entry types (#…
andrew-codechimp Dec 13, 2025
b0fac94
Update systembridgeconnector to 5.2.4, fix media source (#158917)
timmo001 Dec 15, 2025
96d2ecf
Assume cover or valve is always "running" in google assistant when th…
jbouwh Dec 14, 2025
e0fa5db
Bump ical to 12.1.2 (#158965)
allenporter Dec 15, 2025
b608dcb
Update unnecessary error logging of unknown and unavailable source st…
Petro31 Dec 14, 2025
d64313c
Add exception handling for rate limited or unauthorized MQTT requests…
allenporter Dec 14, 2025
108d94a
Bump aioasuswrt to 1.5.4 (#159038)
upsuper Dec 15, 2025
af72bc4
Bump blinkpy to 0.25.2 (#159049)
fronzbot Dec 14, 2025
63cb220
Fix slow event state updates for remote calendar (#159058)
allenporter Dec 15, 2025
0dac52c
Bump aiodns to 3.6.1 (#159073)
bramkragten Dec 19, 2025
1a56855
Bump pysmlight to v0.2.13 (#159075)
tl-sl Dec 15, 2025
1b464e7
Improve icloud reauth flow (#159081)
PaulCavill Dec 18, 2025
00b7138
Sonos fix media player join to avoid race condition (#159106)
PeteRager Dec 15, 2025
37a32bf
Sonos increase wait for groups timeout (#159108)
PeteRager Dec 15, 2025
7275be4
Bump pynintendoparental 2.1.3 (#159120)
pantherale0 Dec 16, 2025
7bbeb2a
Bump soco to 0.30.13 for Sonos (#159123)
PeteRager Dec 15, 2025
d17ed3e
Handle missing Miele status codes gracefully (#159124)
astrandb Dec 15, 2025
31785bf
Bump ekey-bionyxpy to version 1.0.1 (#159196)
richardpolzer Dec 16, 2025
692847d
Fix incorrect status updates for lcn (#159251)
alengwenus Dec 18, 2025
793877b
Bump python-roborock to 3.18.0 (#159271)
Lash-L Dec 17, 2025
d5cbc6e
Bump pypck to 0.9.8 (#159277)
alengwenus Dec 18, 2025
9f31d95
Fix AttributeError in Roborock Empty Mode entity (#159278)
allenporter Dec 19, 2025
3c20df9
Add missing strings for Shelly voltmeter sensor (#159332)
chemelli74 Dec 18, 2025
e086e01
Do not trigger reauth for addon in Music Assistant (#159372)
arturpragacz Dec 18, 2025
188c98f
Align format of voltmeter strings for Shelly (#159394)
chemelli74 Dec 18, 2025
80f2889
Bump ZHA to 0.0.81 (#159396)
puddly Dec 19, 2025
cec5134
Bump python-roborock to 3.19.0 (#159404)
allenporter Dec 19, 2025
3001dcb
Remove users refresh tokens when the user get's deactivated (#159443)
edenhaus Dec 19, 2025
52630cc
Update frontend to 20251203.3 (#159451)
bramkragten Dec 19, 2025
e098acf
Bump version to 2025.12.4
bramkragten Dec 19, 2025
cbc6306
Merge branch 'master' into rc
bramkragten Dec 19, 2025
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 2 additions & 0 deletions homeassistant/auth/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -402,6 +402,8 @@ async def async_deactivate_user(self, user: models.User) -> None:
if user.is_owner:
raise ValueError("Unable to deactivate the owner")
await self._store.async_deactivate_user(user)
for refresh_token in list(user.refresh_tokens.values()):
self.async_remove_refresh_token(refresh_token)

async def async_remove_credentials(self, credentials: models.Credentials) -> None:
"""Remove credentials."""
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/asuswrt/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,5 +7,5 @@
"integration_type": "hub",
"iot_class": "local_polling",
"loggers": ["aioasuswrt", "asusrouter", "asyncssh"],
"requirements": ["aioasuswrt==1.5.2", "asusrouter==1.21.3"]
"requirements": ["aioasuswrt==1.5.4", "asusrouter==1.21.3"]
}
2 changes: 1 addition & 1 deletion homeassistant/components/blink/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -20,5 +20,5 @@
"documentation": "https://www.home-assistant.io/integrations/blink",
"iot_class": "cloud_polling",
"loggers": ["blinkpy"],
"requirements": ["blinkpy==0.25.1"]
"requirements": ["blinkpy==0.25.2"]
}
12 changes: 8 additions & 4 deletions homeassistant/components/config/area_registry.py
Original file line number Diff line number Diff line change
Expand Up @@ -65,8 +65,10 @@ def websocket_create_area(
data.pop("id")

if "aliases" in data:
# Convert aliases to a set
data["aliases"] = set(data["aliases"])
# Create a set for the aliases without:
# - Empty strings
# - Trailing and leading whitespace characters in the individual aliases
data["aliases"] = {s_strip for s in data["aliases"] if (s_strip := s.strip())}

if "labels" in data:
# Convert labels to a set
Expand Down Expand Up @@ -133,8 +135,10 @@ def websocket_update_area(
data.pop("id")

if "aliases" in data:
# Convert aliases to a set
data["aliases"] = set(data["aliases"])
# Create a set for the aliases without:
# - Empty strings
# - Trailing and leading whitespace characters in the individual aliases
data["aliases"] = {s_strip for s in data["aliases"] if (s_strip := s.strip())}

if "labels" in data:
# Convert labels to a set
Expand Down
6 changes: 4 additions & 2 deletions homeassistant/components/config/entity_registry.py
Original file line number Diff line number Diff line change
Expand Up @@ -227,8 +227,10 @@ def websocket_update_entity(
changes[key] = msg[key]

if "aliases" in msg:
# Convert aliases to a set
changes["aliases"] = set(msg["aliases"])
# Create a set for the aliases without:
# - Empty strings
# - Trailing and leading whitespace characters in the individual aliases
changes["aliases"] = {s_strip for s in msg["aliases"] if (s_strip := s.strip())}

if "labels" in msg:
# Convert labels to a set
Expand Down
12 changes: 8 additions & 4 deletions homeassistant/components/config/floor_registry.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,8 +61,10 @@ def websocket_create_floor(
data.pop("id")

if "aliases" in data:
# Convert aliases to a set
data["aliases"] = set(data["aliases"])
# Create a set for the aliases without:
# - Empty strings
# - Trailing and leading whitespace characters in the individual aliases
data["aliases"] = {s_strip for s in data["aliases"] if (s_strip := s.strip())}

try:
entry = registry.async_create(**data)
Expand Down Expand Up @@ -117,8 +119,10 @@ def websocket_update_floor(
data.pop("id")

if "aliases" in data:
# Convert aliases to a set
data["aliases"] = set(data["aliases"])
# Create a set for the aliases without:
# - Empty strings
# - Trailing and leading whitespace characters in the individual aliases
data["aliases"] = {s_strip for s in data["aliases"] if (s_strip := s.strip())}

try:
entry = registry.async_update(**data)
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/dlna_dmr/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
"integration_type": "device",
"iot_class": "local_push",
"loggers": ["async_upnp_client"],
"requirements": ["async-upnp-client==0.46.0", "getmac==0.9.5"],
"requirements": ["async-upnp-client==0.46.1", "getmac==0.9.5"],
"ssdp": [
{
"deviceType": "urn:schemas-upnp-org:device:MediaRenderer:1",
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/dlna_dms/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@
"documentation": "https://www.home-assistant.io/integrations/dlna_dms",
"integration_type": "service",
"iot_class": "local_polling",
"requirements": ["async-upnp-client==0.46.0"],
"requirements": ["async-upnp-client==0.46.1"],
"ssdp": [
{
"deviceType": "urn:schemas-upnp-org:device:MediaServer:1",
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/dnsip/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,5 @@
"config_flow": true,
"documentation": "https://www.home-assistant.io/integrations/dnsip",
"iot_class": "cloud_polling",
"requirements": ["aiodns==3.5.0"]
"requirements": ["aiodns==3.6.1"]
}
2 changes: 1 addition & 1 deletion homeassistant/components/ekeybionyx/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,5 +7,5 @@
"documentation": "https://www.home-assistant.io/integrations/ekeybionyx",
"iot_class": "local_push",
"quality_scale": "bronze",
"requirements": ["ekey-bionyxpy==1.0.0"]
"requirements": ["ekey-bionyxpy==1.0.1"]
}
2 changes: 1 addition & 1 deletion homeassistant/components/frontend/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -23,5 +23,5 @@
"winter_mode": {}
},
"quality_scale": "internal",
"requirements": ["home-assistant-frontend==20251203.2"]
"requirements": ["home-assistant-frontend==20251203.3"]
}
2 changes: 1 addition & 1 deletion homeassistant/components/google/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -8,5 +8,5 @@
"integration_type": "service",
"iot_class": "cloud_polling",
"loggers": ["googleapiclient"],
"requirements": ["gcal-sync==8.0.0", "oauth2client==4.1.3", "ical==12.1.1"]
"requirements": ["gcal-sync==8.0.0", "oauth2client==4.1.3", "ical==12.1.2"]
}
38 changes: 33 additions & 5 deletions homeassistant/components/google_assistant/trait.py
Original file line number Diff line number Diff line change
Expand Up @@ -908,12 +908,21 @@ def query_attributes(self) -> dict[str, Any]:
}

if domain in COVER_VALVE_DOMAINS:
assumed_state_or_set_position = bool(
(
self.state.attributes.get(ATTR_SUPPORTED_FEATURES, 0)
& COVER_VALVE_SET_POSITION_FEATURE[domain]
)
or self.state.attributes.get(ATTR_ASSUMED_STATE)
)

return {
"isRunning": state
in (
COVER_VALVE_STATES[domain]["closing"],
COVER_VALVE_STATES[domain]["opening"],
)
or assumed_state_or_set_position
}

raise NotImplementedError(f"Unsupported domain {domain}")
Expand Down Expand Up @@ -975,11 +984,23 @@ async def _execute_cover_or_valve(self, command, data, params, challenge):
"""Execute a StartStop command."""
domain = self.state.domain
if command == COMMAND_START_STOP:
assumed_state_or_set_position = bool(
(
self.state.attributes.get(ATTR_SUPPORTED_FEATURES, 0)
& COVER_VALVE_SET_POSITION_FEATURE[domain]
)
or self.state.attributes.get(ATTR_ASSUMED_STATE)
)

if params["start"] is False:
if self.state.state in (
COVER_VALVE_STATES[domain]["closing"],
COVER_VALVE_STATES[domain]["opening"],
) or self.state.attributes.get(ATTR_ASSUMED_STATE):
if (
self.state.state
in (
COVER_VALVE_STATES[domain]["closing"],
COVER_VALVE_STATES[domain]["opening"],
)
or assumed_state_or_set_position
):
await self.hass.services.async_call(
domain,
SERVICE_STOP_COVER_VALVE[domain],
Expand All @@ -992,7 +1013,14 @@ async def _execute_cover_or_valve(self, command, data, params, challenge):
ERR_ALREADY_STOPPED,
f"{FRIENDLY_DOMAIN[domain]} is already stopped",
)
else:
elif (
self.state.state
in (
COVER_VALVE_STATES[domain]["open"],
COVER_VALVE_STATES[domain]["closed"],
)
or assumed_state_or_set_position
):
await self.hass.services.async_call(
domain,
SERVICE_TOGGLE_COVER_VALVE[domain],
Expand Down
6 changes: 3 additions & 3 deletions homeassistant/components/icloud/config_flow.py
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@
)
import voluptuous as vol

from homeassistant.config_entries import ConfigFlow, ConfigFlowResult
from homeassistant.config_entries import SOURCE_USER, ConfigFlow, ConfigFlowResult
from homeassistant.const import CONF_PASSWORD, CONF_USERNAME
from homeassistant.helpers.storage import Store

Expand Down Expand Up @@ -155,8 +155,8 @@ async def _validate_and_create_entry(self, user_input, step_id):
CONF_GPS_ACCURACY_THRESHOLD: self._gps_accuracy_threshold,
}

# If this is a password update attempt, update the entry instead of creating one
if step_id == "user":
# If this is a password update attempt, don't try and creating one
if self.source == SOURCE_USER:
return self.async_create_entry(title=self._username, data=data)

entry = await self.async_set_unique_id(self.unique_id)
Expand Down
4 changes: 2 additions & 2 deletions homeassistant/components/lcn/binary_sensor.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,8 @@
from .entity import LcnEntity
from .helpers import InputType, LcnConfigEntry

PARALLEL_UPDATES = 0
SCAN_INTERVAL = timedelta(minutes=1)
PARALLEL_UPDATES = 2
SCAN_INTERVAL = timedelta(minutes=10)


def add_lcn_entities(
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/lcn/climate.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,7 +37,7 @@
from .entity import LcnEntity
from .helpers import InputType, LcnConfigEntry

PARALLEL_UPDATES = 0
PARALLEL_UPDATES = 2
SCAN_INTERVAL = timedelta(minutes=1)


Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/lcn/cover.py
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@
from .entity import LcnEntity
from .helpers import InputType, LcnConfigEntry

PARALLEL_UPDATES = 0
PARALLEL_UPDATES = 2
SCAN_INTERVAL = timedelta(minutes=1)


Expand Down
4 changes: 2 additions & 2 deletions homeassistant/components/lcn/light.py
Original file line number Diff line number Diff line change
Expand Up @@ -33,8 +33,8 @@

BRIGHTNESS_SCALE = (1, 100)

PARALLEL_UPDATES = 0
SCAN_INTERVAL = timedelta(minutes=1)
PARALLEL_UPDATES = 2
SCAN_INTERVAL = timedelta(minutes=10)


def add_lcn_entities(
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/lcn/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -9,5 +9,5 @@
"iot_class": "local_polling",
"loggers": ["pypck"],
"quality_scale": "silver",
"requirements": ["pypck==0.9.7", "lcn-frontend==0.2.7"]
"requirements": ["pypck==0.9.8", "lcn-frontend==0.2.7"]
}
2 changes: 1 addition & 1 deletion homeassistant/components/lcn/scene.py
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@
from .entity import LcnEntity
from .helpers import LcnConfigEntry

PARALLEL_UPDATES = 0
PARALLEL_UPDATES = 2


def add_lcn_entities(
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/lcn/sensor.py
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@
from .entity import LcnEntity
from .helpers import InputType, LcnConfigEntry

PARALLEL_UPDATES = 0
PARALLEL_UPDATES = 2
SCAN_INTERVAL = timedelta(minutes=1)


Expand Down
4 changes: 2 additions & 2 deletions homeassistant/components/lcn/switch.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,8 +17,8 @@
from .entity import LcnEntity
from .helpers import InputType, LcnConfigEntry

PARALLEL_UPDATES = 0
SCAN_INTERVAL = timedelta(minutes=1)
PARALLEL_UPDATES = 2
SCAN_INTERVAL = timedelta(minutes=10)


def add_lcn_switch_entities(
Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/local_calendar/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,5 +7,5 @@
"documentation": "https://www.home-assistant.io/integrations/local_calendar",
"iot_class": "local_polling",
"loggers": ["ical"],
"requirements": ["ical==12.1.1"]
"requirements": ["ical==12.1.2"]
}
2 changes: 1 addition & 1 deletion homeassistant/components/local_todo/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,5 @@
"config_flow": true,
"documentation": "https://www.home-assistant.io/integrations/local_todo",
"iot_class": "local_polling",
"requirements": ["ical==12.1.1"]
"requirements": ["ical==12.1.2"]
}
9 changes: 8 additions & 1 deletion homeassistant/components/mealie/calendar.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,6 +15,13 @@

PARALLEL_UPDATES = 0

SUPPORTED_MEALPLAN_ENTRY_TYPES = [
MealplanEntryType.BREAKFAST,
MealplanEntryType.DINNER,
MealplanEntryType.LUNCH,
MealplanEntryType.SIDE,
]


async def async_setup_entry(
hass: HomeAssistant,
Expand All @@ -26,7 +33,7 @@ async def async_setup_entry(

async_add_entities(
MealieMealplanCalendarEntity(coordinator, entry_type)
for entry_type in MealplanEntryType
for entry_type in SUPPORTED_MEALPLAN_ENTRY_TYPES
)


Expand Down
2 changes: 1 addition & 1 deletion homeassistant/components/mealie/manifest.json
Original file line number Diff line number Diff line change
Expand Up @@ -7,5 +7,5 @@
"integration_type": "service",
"iot_class": "local_polling",
"quality_scale": "platinum",
"requirements": ["aiomealie==1.1.0"]
"requirements": ["aiomealie==1.1.1"]
}
Loading
Loading