mirror of
https://github.com/home-assistant/core.git
synced 2025-07-17 02:07:09 +00:00
Add port to plugwise (#40017)
This commit is contained in:
parent
b175adae53
commit
5832184304
@ -10,7 +10,7 @@ import async_timeout
|
|||||||
import voluptuous as vol
|
import voluptuous as vol
|
||||||
|
|
||||||
from homeassistant.config_entries import ConfigEntry
|
from homeassistant.config_entries import ConfigEntry
|
||||||
from homeassistant.const import CONF_HOST, CONF_PASSWORD, CONF_SCAN_INTERVAL
|
from homeassistant.const import CONF_HOST, CONF_PASSWORD, CONF_PORT, CONF_SCAN_INTERVAL
|
||||||
from homeassistant.core import HomeAssistant, callback
|
from homeassistant.core import HomeAssistant, callback
|
||||||
from homeassistant.exceptions import ConfigEntryNotReady
|
from homeassistant.exceptions import ConfigEntryNotReady
|
||||||
from homeassistant.helpers import device_registry as dr
|
from homeassistant.helpers import device_registry as dr
|
||||||
@ -21,7 +21,13 @@ from homeassistant.helpers.update_coordinator import (
|
|||||||
UpdateFailed,
|
UpdateFailed,
|
||||||
)
|
)
|
||||||
|
|
||||||
from .const import COORDINATOR, DEFAULT_SCAN_INTERVAL, DOMAIN, UNDO_UPDATE_LISTENER
|
from .const import (
|
||||||
|
COORDINATOR,
|
||||||
|
DEFAULT_PORT,
|
||||||
|
DEFAULT_SCAN_INTERVAL,
|
||||||
|
DOMAIN,
|
||||||
|
UNDO_UPDATE_LISTENER,
|
||||||
|
)
|
||||||
|
|
||||||
CONFIG_SCHEMA = vol.Schema({DOMAIN: vol.Schema({})}, extra=vol.ALLOW_EXTRA)
|
CONFIG_SCHEMA = vol.Schema({DOMAIN: vol.Schema({})}, extra=vol.ALLOW_EXTRA)
|
||||||
|
|
||||||
@ -39,9 +45,12 @@ async def async_setup(hass: HomeAssistant, config: dict):
|
|||||||
async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
|
async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
|
||||||
"""Set up Plugwise Smiles from a config entry."""
|
"""Set up Plugwise Smiles from a config entry."""
|
||||||
websession = async_get_clientsession(hass, verify_ssl=False)
|
websession = async_get_clientsession(hass, verify_ssl=False)
|
||||||
|
|
||||||
api = Smile(
|
api = Smile(
|
||||||
host=entry.data[CONF_HOST],
|
host=entry.data[CONF_HOST],
|
||||||
password=entry.data[CONF_PASSWORD],
|
password=entry.data[CONF_PASSWORD],
|
||||||
|
port=entry.data.get(CONF_PORT, DEFAULT_PORT),
|
||||||
|
timeout=30,
|
||||||
websession=websession,
|
websession=websession,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
@ -5,12 +5,16 @@ from Plugwise_Smile.Smile import Smile
|
|||||||
import voluptuous as vol
|
import voluptuous as vol
|
||||||
|
|
||||||
from homeassistant import config_entries, core, exceptions
|
from homeassistant import config_entries, core, exceptions
|
||||||
from homeassistant.const import CONF_HOST, CONF_PASSWORD, CONF_SCAN_INTERVAL
|
from homeassistant.const import CONF_HOST, CONF_PASSWORD, CONF_PORT, CONF_SCAN_INTERVAL
|
||||||
from homeassistant.core import callback
|
from homeassistant.core import callback
|
||||||
from homeassistant.helpers.aiohttp_client import async_get_clientsession
|
from homeassistant.helpers.aiohttp_client import async_get_clientsession
|
||||||
from homeassistant.helpers.typing import DiscoveryInfoType
|
from homeassistant.helpers.typing import DiscoveryInfoType
|
||||||
|
|
||||||
from .const import DEFAULT_SCAN_INTERVAL, DOMAIN # pylint:disable=unused-import
|
from .const import ( # pylint:disable=unused-import
|
||||||
|
DEFAULT_PORT,
|
||||||
|
DEFAULT_SCAN_INTERVAL,
|
||||||
|
DOMAIN,
|
||||||
|
)
|
||||||
|
|
||||||
_LOGGER = logging.getLogger(__name__)
|
_LOGGER = logging.getLogger(__name__)
|
||||||
|
|
||||||
@ -27,6 +31,7 @@ def _base_schema(discovery_info):
|
|||||||
|
|
||||||
if not discovery_info:
|
if not discovery_info:
|
||||||
base_schema[vol.Required(CONF_HOST)] = str
|
base_schema[vol.Required(CONF_HOST)] = str
|
||||||
|
base_schema[vol.Optional(CONF_PORT, default=DEFAULT_PORT)] = int
|
||||||
|
|
||||||
base_schema[vol.Required(CONF_PASSWORD)] = str
|
base_schema[vol.Required(CONF_PASSWORD)] = str
|
||||||
|
|
||||||
@ -40,9 +45,11 @@ async def validate_input(hass: core.HomeAssistant, data):
|
|||||||
Data has the keys from _base_schema() with values provided by the user.
|
Data has the keys from _base_schema() with values provided by the user.
|
||||||
"""
|
"""
|
||||||
websession = async_get_clientsession(hass, verify_ssl=False)
|
websession = async_get_clientsession(hass, verify_ssl=False)
|
||||||
|
|
||||||
api = Smile(
|
api = Smile(
|
||||||
host=data[CONF_HOST],
|
host=data[CONF_HOST],
|
||||||
password=data[CONF_PASSWORD],
|
password=data[CONF_PASSWORD],
|
||||||
|
port=data[CONF_PORT],
|
||||||
timeout=30,
|
timeout=30,
|
||||||
websession=websession,
|
websession=websession,
|
||||||
)
|
)
|
||||||
@ -83,6 +90,7 @@ class PlugwiseConfigFlow(config_entries.ConfigFlow, domain=DOMAIN):
|
|||||||
# pylint: disable=no-member # https://github.com/PyCQA/pylint/issues/3167
|
# pylint: disable=no-member # https://github.com/PyCQA/pylint/issues/3167
|
||||||
self.context["title_placeholders"] = {
|
self.context["title_placeholders"] = {
|
||||||
CONF_HOST: discovery_info[CONF_HOST],
|
CONF_HOST: discovery_info[CONF_HOST],
|
||||||
|
CONF_PORT: discovery_info.get(CONF_PORT, DEFAULT_PORT),
|
||||||
"name": _name,
|
"name": _name,
|
||||||
}
|
}
|
||||||
return await self.async_step_user()
|
return await self.async_step_user()
|
||||||
@ -95,6 +103,7 @@ class PlugwiseConfigFlow(config_entries.ConfigFlow, domain=DOMAIN):
|
|||||||
|
|
||||||
if self.discovery_info:
|
if self.discovery_info:
|
||||||
user_input[CONF_HOST] = self.discovery_info[CONF_HOST]
|
user_input[CONF_HOST] = self.discovery_info[CONF_HOST]
|
||||||
|
user_input[CONF_PORT] = self.discovery_info.get(CONF_PORT, DEFAULT_PORT)
|
||||||
|
|
||||||
for entry in self._async_current_entries():
|
for entry in self._async_current_entries():
|
||||||
if entry.data.get(CONF_HOST) == user_input[CONF_HOST]:
|
if entry.data.get(CONF_HOST) == user_input[CONF_HOST]:
|
||||||
|
@ -13,10 +13,11 @@
|
|||||||
"step": {
|
"step": {
|
||||||
"user": {
|
"user": {
|
||||||
"title": "Connect to the Smile",
|
"title": "Connect to the Smile",
|
||||||
"description": "Details",
|
"description": "Please enter:",
|
||||||
"data": {
|
"data": {
|
||||||
|
"password": "Smile ID",
|
||||||
"host": "Smile IP address",
|
"host": "Smile IP address",
|
||||||
"password": "Smile ID"
|
"port": "Smile port number"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
@ -3,7 +3,11 @@ from Plugwise_Smile.Smile import Smile
|
|||||||
import pytest
|
import pytest
|
||||||
|
|
||||||
from homeassistant import config_entries, data_entry_flow, setup
|
from homeassistant import config_entries, data_entry_flow, setup
|
||||||
from homeassistant.components.plugwise.const import DEFAULT_SCAN_INTERVAL, DOMAIN
|
from homeassistant.components.plugwise.const import (
|
||||||
|
DEFAULT_PORT,
|
||||||
|
DEFAULT_SCAN_INTERVAL,
|
||||||
|
DOMAIN,
|
||||||
|
)
|
||||||
from homeassistant.config_entries import SOURCE_USER, SOURCE_ZEROCONF
|
from homeassistant.config_entries import SOURCE_USER, SOURCE_ZEROCONF
|
||||||
from homeassistant.const import CONF_HOST, CONF_NAME, CONF_PASSWORD, CONF_SCAN_INTERVAL
|
from homeassistant.const import CONF_HOST, CONF_NAME, CONF_PASSWORD, CONF_SCAN_INTERVAL
|
||||||
|
|
||||||
@ -13,8 +17,11 @@ from tests.common import MockConfigEntry
|
|||||||
TEST_HOST = "1.1.1.1"
|
TEST_HOST = "1.1.1.1"
|
||||||
TEST_HOSTNAME = "smileabcdef"
|
TEST_HOSTNAME = "smileabcdef"
|
||||||
TEST_PASSWORD = "test_password"
|
TEST_PASSWORD = "test_password"
|
||||||
|
TEST_PORT = 81
|
||||||
|
|
||||||
TEST_DISCOVERY = {
|
TEST_DISCOVERY = {
|
||||||
"host": TEST_HOST,
|
"host": TEST_HOST,
|
||||||
|
"port": DEFAULT_PORT,
|
||||||
"hostname": f"{TEST_HOSTNAME}.local.",
|
"hostname": f"{TEST_HOSTNAME}.local.",
|
||||||
"server": f"{TEST_HOSTNAME}.local.",
|
"server": f"{TEST_HOSTNAME}.local.",
|
||||||
"properties": {
|
"properties": {
|
||||||
@ -68,6 +75,7 @@ async def test_form(hass):
|
|||||||
assert result2["data"] == {
|
assert result2["data"] == {
|
||||||
"host": TEST_HOST,
|
"host": TEST_HOST,
|
||||||
"password": TEST_PASSWORD,
|
"password": TEST_PASSWORD,
|
||||||
|
"port": DEFAULT_PORT,
|
||||||
}
|
}
|
||||||
|
|
||||||
assert len(mock_setup.mock_calls) == 1
|
assert len(mock_setup.mock_calls) == 1
|
||||||
@ -106,6 +114,7 @@ async def test_zeroconf_form(hass):
|
|||||||
assert result2["data"] == {
|
assert result2["data"] == {
|
||||||
"host": TEST_HOST,
|
"host": TEST_HOST,
|
||||||
"password": TEST_PASSWORD,
|
"password": TEST_PASSWORD,
|
||||||
|
"port": DEFAULT_PORT,
|
||||||
}
|
}
|
||||||
|
|
||||||
assert len(mock_setup.mock_calls) == 1
|
assert len(mock_setup.mock_calls) == 1
|
||||||
@ -176,6 +185,24 @@ async def test_form_cannot_connect(hass, mock_smile):
|
|||||||
assert result2["errors"] == {"base": "cannot_connect"}
|
assert result2["errors"] == {"base": "cannot_connect"}
|
||||||
|
|
||||||
|
|
||||||
|
async def test_form_cannot_connect_port(hass, mock_smile):
|
||||||
|
"""Test we handle cannot connect to port error."""
|
||||||
|
result = await hass.config_entries.flow.async_init(
|
||||||
|
DOMAIN, context={"source": config_entries.SOURCE_USER}
|
||||||
|
)
|
||||||
|
|
||||||
|
mock_smile.connect.side_effect = Smile.ConnectionFailedError
|
||||||
|
mock_smile.gateway_id = "0a636a4fc1704ab4a24e4f7e37fb187a"
|
||||||
|
|
||||||
|
result2 = await hass.config_entries.flow.async_configure(
|
||||||
|
result["flow_id"],
|
||||||
|
{"host": TEST_HOST, "password": TEST_PASSWORD, "port": TEST_PORT},
|
||||||
|
)
|
||||||
|
|
||||||
|
assert result2["type"] == data_entry_flow.RESULT_TYPE_FORM
|
||||||
|
assert result2["errors"] == {"base": "cannot_connect"}
|
||||||
|
|
||||||
|
|
||||||
async def test_form_other_problem(hass, mock_smile):
|
async def test_form_other_problem(hass, mock_smile):
|
||||||
"""Test we handle cannot connect error."""
|
"""Test we handle cannot connect error."""
|
||||||
result = await hass.config_entries.flow.async_init(
|
result = await hass.config_entries.flow.async_init(
|
||||||
|
Loading…
x
Reference in New Issue
Block a user