diff --git a/homeassistant/components/lupusec/__init__.py b/homeassistant/components/lupusec/__init__.py index bf7c30845a3c..f937c7edd10c 100644 --- a/homeassistant/components/lupusec/__init__.py +++ b/homeassistant/components/lupusec/__init__.py @@ -1,4 +1,5 @@ """Support for Lupusec Home Security system.""" +from json import JSONDecodeError import logging import lupupy @@ -111,16 +112,11 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: lupusec_system = await hass.async_add_executor_job( lupupy.Lupusec, username, password, host ) - except LupusecException: _LOGGER.error("Failed to connect to Lupusec device at %s", host) return False - except Exception as ex: # pylint: disable=broad-except - _LOGGER.error( - "Unknown error while trying to connect to Lupusec device at %s: %s", - host, - ex, - ) + except JSONDecodeError: + _LOGGER.error("Failed to connect to Lupusec device at %s", host) return False hass.data.setdefault(DOMAIN, {})[entry.entry_id] = lupusec_system diff --git a/homeassistant/components/lupusec/alarm_control_panel.py b/homeassistant/components/lupusec/alarm_control_panel.py index 2e4ca5cab63c..cd4e433bd5dd 100644 --- a/homeassistant/components/lupusec/alarm_control_panel.py +++ b/homeassistant/components/lupusec/alarm_control_panel.py @@ -29,14 +29,14 @@ SCAN_INTERVAL = timedelta(seconds=2) async def async_setup_entry( hass: HomeAssistant, config_entry: ConfigEntry, - async_add_devices: AddEntitiesCallback, + async_add_entities: AddEntitiesCallback, ) -> None: """Set up an alarm control panel for a Lupusec device.""" data = hass.data[DOMAIN][config_entry.entry_id] - alarm_devices = [LupusecAlarm(data, data.get_alarm(), config_entry.entry_id)] + alarm = await hass.async_add_executor_job(data.get_alarm) - async_add_devices(alarm_devices) + async_add_entities([LupusecAlarm(data, alarm, config_entry.entry_id)]) class LupusecAlarm(LupusecDevice, AlarmControlPanelEntity): diff --git a/homeassistant/components/lupusec/binary_sensor.py b/homeassistant/components/lupusec/binary_sensor.py index ecff9a6266d0..5cf63579984c 100644 --- a/homeassistant/components/lupusec/binary_sensor.py +++ b/homeassistant/components/lupusec/binary_sensor.py @@ -2,6 +2,7 @@ from __future__ import annotations from datetime import timedelta +from functools import partial import logging import lupupy.constants as CONST @@ -25,7 +26,7 @@ _LOGGER = logging.getLogger(__name__) async def async_setup_entry( hass: HomeAssistant, config_entry: ConfigEntry, - async_add_devices: AddEntitiesCallback, + async_add_entities: AddEntitiesCallback, ) -> None: """Set up a binary sensors for a Lupusec device.""" @@ -34,10 +35,12 @@ async def async_setup_entry( device_types = CONST.TYPE_OPENING + CONST.TYPE_SENSOR sensors = [] - for device in data.get_devices(generic_type=device_types): + partial_func = partial(data.get_devices, generic_type=device_types) + devices = await hass.async_add_executor_job(partial_func) + for device in devices: sensors.append(LupusecBinarySensor(device, config_entry.entry_id)) - async_add_devices(sensors) + async_add_entities(sensors) class LupusecBinarySensor(LupusecBaseSensor, BinarySensorEntity): diff --git a/homeassistant/components/lupusec/config_flow.py b/homeassistant/components/lupusec/config_flow.py index 64d53ce51f45..aad57897c91e 100644 --- a/homeassistant/components/lupusec/config_flow.py +++ b/homeassistant/components/lupusec/config_flow.py @@ -1,5 +1,6 @@ """"Config flow for Lupusec integration.""" +from json import JSONDecodeError import logging from typing import Any @@ -50,6 +51,8 @@ class LupusecConfigFlowHandler(config_entries.ConfigFlow, domain=DOMAIN): await test_host_connection(self.hass, host, username, password) except CannotConnect: errors["base"] = "cannot_connect" + except JSONDecodeError: + errors["base"] = "cannot_connect" except Exception: # pylint: disable=broad-except _LOGGER.exception("Unexpected exception") errors["base"] = "unknown" @@ -80,6 +83,8 @@ class LupusecConfigFlowHandler(config_entries.ConfigFlow, domain=DOMAIN): await test_host_connection(self.hass, host, username, password) except CannotConnect: return self.async_abort(reason="cannot_connect") + except JSONDecodeError: + return self.async_abort(reason="cannot_connect") except Exception: # pylint: disable=broad-except _LOGGER.exception("Unexpected exception") return self.async_abort(reason="unknown") diff --git a/homeassistant/components/lupusec/strings.json b/homeassistant/components/lupusec/strings.json index 53f84c8b8729..6fa59aaeb3db 100644 --- a/homeassistant/components/lupusec/strings.json +++ b/homeassistant/components/lupusec/strings.json @@ -21,7 +21,7 @@ "issues": { "deprecated_yaml_import_issue_cannot_connect": { "title": "The Lupus Electronics LUPUSEC YAML configuration import failed", - "description": "Configuring Lupus Electronics LUPUSEC using YAML is being removed but there was an connection error importing your YAML configuration.\n\nEnsure connection to Lupus Electronics LUPUSEC works and restart Home Assistant to try again or remove the Lupus Electronics LUPUSEC YAML configuration from your configuration.yaml file and continue to [set up the integration]({url}) manually." + "description": "Configuring Lupus Electronics LUPUSEC using YAML is being removed but there was a connection error importing your YAML configuration.\n\nEnsure connection to Lupus Electronics LUPUSEC works and restart Home Assistant to try again or remove the Lupus Electronics LUPUSEC YAML configuration from your configuration.yaml file and continue to [set up the integration]({url}) manually." }, "deprecated_yaml_import_issue_unknown": { "title": "The Lupus Electronics LUPUSEC YAML configuration import failed", diff --git a/homeassistant/components/lupusec/switch.py b/homeassistant/components/lupusec/switch.py index a2b3796ef5bb..e07c974f033e 100644 --- a/homeassistant/components/lupusec/switch.py +++ b/homeassistant/components/lupusec/switch.py @@ -2,6 +2,7 @@ from __future__ import annotations from datetime import timedelta +from functools import partial from typing import Any import lupupy.constants as CONST @@ -20,7 +21,7 @@ SCAN_INTERVAL = timedelta(seconds=2) async def async_setup_entry( hass: HomeAssistant, config_entry: ConfigEntry, - async_add_devices: AddEntitiesCallback, + async_add_entities: AddEntitiesCallback, ) -> None: """Set up Lupusec switch devices.""" @@ -29,10 +30,12 @@ async def async_setup_entry( device_types = CONST.TYPE_SWITCH switches = [] - for device in data.get_devices(generic_type=device_types): + partial_func = partial(data.get_devices, generic_type=device_types) + devices = await hass.async_add_executor_job(partial_func) + for device in devices: switches.append(LupusecSwitch(device, config_entry.entry_id)) - async_add_devices(switches) + async_add_entities(switches) class LupusecSwitch(LupusecBaseSensor, SwitchEntity): diff --git a/tests/components/lupusec/test_config_flow.py b/tests/components/lupusec/test_config_flow.py index 5ef5f98ea000..6b07952ff544 100644 --- a/tests/components/lupusec/test_config_flow.py +++ b/tests/components/lupusec/test_config_flow.py @@ -1,5 +1,6 @@ """"Unit tests for the Lupusec config flow.""" +from json import JSONDecodeError from unittest.mock import patch from lupupy import LupusecException @@ -51,8 +52,7 @@ async def test_form_valid_input(hass: HomeAssistant) -> None: "homeassistant.components.lupusec.async_setup_entry", return_value=True, ) as mock_setup_entry, patch( - "homeassistant.components.lupusec.config_flow.lupupy.Lupusec.__init__", - return_value=None, + "homeassistant.components.lupusec.config_flow.lupupy.Lupusec", ) as mock_initialize_lupusec: result2 = await hass.config_entries.flow.async_configure( result["flow_id"], @@ -71,6 +71,7 @@ async def test_form_valid_input(hass: HomeAssistant) -> None: ("raise_error", "text_error"), [ (LupusecException("Test lupusec exception"), "cannot_connect"), + (JSONDecodeError("Test JSONDecodeError", "test", 1), "cannot_connect"), (Exception("Test unknown exception"), "unknown"), ], ) @@ -85,7 +86,7 @@ async def test_flow_user_init_data_error_and_recover( assert result["errors"] == {} with patch( - "homeassistant.components.lupusec.config_flow.lupupy.Lupusec.__init__", + "homeassistant.components.lupusec.config_flow.lupupy.Lupusec", side_effect=raise_error, ) as mock_initialize_lupusec: result2 = await hass.config_entries.flow.async_configure( @@ -104,8 +105,7 @@ async def test_flow_user_init_data_error_and_recover( "homeassistant.components.lupusec.async_setup_entry", return_value=True, ) as mock_setup_entry, patch( - "homeassistant.components.lupusec.config_flow.lupupy.Lupusec.__init__", - return_value=None, + "homeassistant.components.lupusec.config_flow.lupupy.Lupusec", ) as mock_initialize_lupusec: result3 = await hass.config_entries.flow.async_configure( result["flow_id"], @@ -164,8 +164,7 @@ async def test_flow_source_import( "homeassistant.components.lupusec.async_setup_entry", return_value=True, ) as mock_setup_entry, patch( - "homeassistant.components.lupusec.config_flow.lupupy.Lupusec.__init__", - return_value=None, + "homeassistant.components.lupusec.config_flow.lupupy.Lupusec", ) as mock_initialize_lupusec: result = await hass.config_entries.flow.async_init( DOMAIN, @@ -186,6 +185,7 @@ async def test_flow_source_import( ("raise_error", "text_error"), [ (LupusecException("Test lupusec exception"), "cannot_connect"), + (JSONDecodeError("Test JSONDecodeError", "test", 1), "cannot_connect"), (Exception("Test unknown exception"), "unknown"), ], ) @@ -195,7 +195,7 @@ async def test_flow_source_import_error_and_recover( """Test exceptions and recovery.""" with patch( - "homeassistant.components.lupusec.config_flow.lupupy.Lupusec.__init__", + "homeassistant.components.lupusec.config_flow.lupupy.Lupusec", side_effect=raise_error, ) as mock_initialize_lupusec: result = await hass.config_entries.flow.async_init(