Remove deprecated PI-Hole YAML config (#84803)

This commit is contained in:
Michael 2023-01-02 10:57:16 +01:00 committed by GitHub
parent f740312247
commit bcbae1388d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
9 changed files with 82 additions and 185 deletions

View File

@ -5,9 +5,8 @@ import logging
from hole import Hole
from hole.exceptions import HoleError
import voluptuous as vol
from homeassistant.config_entries import SOURCE_IMPORT, ConfigEntry
from homeassistant.config_entries import ConfigEntry
from homeassistant.const import (
CONF_API_KEY,
CONF_HOST,
@ -21,8 +20,6 @@ from homeassistant.core import HomeAssistant, callback
from homeassistant.helpers import config_validation as cv
from homeassistant.helpers.aiohttp_client import async_get_clientsession
from homeassistant.helpers.entity import DeviceInfo
from homeassistant.helpers.issue_registry import IssueSeverity, async_create_issue
from homeassistant.helpers.typing import ConfigType
from homeassistant.helpers.update_coordinator import (
CoordinatorEntity,
DataUpdateCoordinator,
@ -33,65 +30,13 @@ from .const import (
CONF_STATISTICS_ONLY,
DATA_KEY_API,
DATA_KEY_COORDINATOR,
DEFAULT_LOCATION,
DEFAULT_NAME,
DEFAULT_SSL,
DEFAULT_VERIFY_SSL,
DOMAIN,
MIN_TIME_BETWEEN_UPDATES,
)
_LOGGER = logging.getLogger(__name__)
PI_HOLE_SCHEMA = vol.Schema(
vol.All(
{
vol.Required(CONF_HOST): cv.string,
vol.Optional(CONF_NAME, default=DEFAULT_NAME): cv.string,
vol.Optional(CONF_API_KEY): cv.string,
vol.Optional(CONF_SSL, default=DEFAULT_SSL): cv.boolean,
vol.Optional(CONF_LOCATION, default=DEFAULT_LOCATION): cv.string,
vol.Optional(CONF_VERIFY_SSL, default=DEFAULT_VERIFY_SSL): cv.boolean,
},
)
)
CONFIG_SCHEMA = vol.Schema(
vol.All(
cv.deprecated(DOMAIN),
{DOMAIN: vol.Schema(vol.All(cv.ensure_list, [PI_HOLE_SCHEMA]))},
),
extra=vol.ALLOW_EXTRA,
)
async def async_setup(hass: HomeAssistant, config: ConfigType) -> bool:
"""Set up the Pi-hole integration."""
hass.data[DOMAIN] = {}
if DOMAIN not in config:
return True
async_create_issue(
hass,
DOMAIN,
"deprecated_yaml",
breaks_in_ha_version="2023.2.0",
is_fixable=False,
severity=IssueSeverity.WARNING,
translation_key="deprecated_yaml",
)
# import
for conf in config[DOMAIN]:
hass.async_create_task(
hass.config_entries.flow.async_init(
DOMAIN, context={"source": SOURCE_IMPORT}, data=conf
)
)
return True
CONFIG_SCHEMA = cv.removed(DOMAIN, raise_if_present=False)
async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
@ -135,6 +80,8 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
update_method=async_update_data,
update_interval=MIN_TIME_BETWEEN_UPDATES,
)
hass.data.setdefault(DOMAIN, {})
hass.data[DOMAIN][entry.entry_id] = {
DATA_KEY_API: api,
DATA_KEY_COORDINATOR: coordinator,

View File

@ -49,12 +49,6 @@ class PiHoleFlowHandler(config_entries.ConfigFlow, domain=DOMAIN):
"""Handle a flow initiated by the user."""
return await self.async_step_init(user_input)
async def async_step_import(
self, user_input: dict[str, Any] | None = None
) -> FlowResult:
"""Handle a flow initiated by import."""
return await self.async_step_init(user_input, is_import=True)
async def async_step_init(
self, user_input: dict[str, Any] | None, is_import: bool = False
) -> FlowResult:

View File

@ -25,11 +25,5 @@
"abort": {
"already_configured": "[%key:common::config_flow::abort::already_configured_service%]"
}
},
"issues": {
"deprecated_yaml": {
"title": "The PI-Hole YAML configuration is being removed",
"description": "Configuring PI-Hole using YAML is being removed.\n\nYour existing YAML configuration has been imported into the UI automatically.\n\nRemove the PI-Hole YAML configuration from your configuration.yaml file and restart Home Assistant to fix this issue."
}
}
}

View File

@ -25,11 +25,5 @@
}
}
}
},
"issues": {
"deprecated_yaml": {
"description": "Die Konfiguration von PI-Hole mittels YAML wird entfernt.\n\nDeine bestehende YAML-Konfiguration wurde automatisch in die Benutzeroberfl\u00e4che importiert.\n\nEntferne die PI-Hole YAML-Konfiguration aus deiner configuration.yaml-Datei und starte den Home Assistant neu, um dieses Problem zu beheben.",
"title": "Die PI-Hole YAML-Konfiguration wird entfernt"
}
}
}

View File

@ -25,11 +25,5 @@
}
}
}
},
"issues": {
"deprecated_yaml": {
"description": "Configuring PI-Hole using YAML is being removed.\n\nYour existing YAML configuration has been imported into the UI automatically.\n\nRemove the PI-Hole YAML configuration from your configuration.yaml file and restart Home Assistant to fix this issue.",
"title": "The PI-Hole YAML configuration is being removed"
}
}
}

View File

@ -3,7 +3,14 @@ from unittest.mock import AsyncMock, MagicMock, patch
from hole.exceptions import HoleError
from homeassistant.components.pi_hole.const import CONF_STATISTICS_ONLY
from homeassistant.components.pi_hole.const import (
CONF_STATISTICS_ONLY,
DEFAULT_LOCATION,
DEFAULT_NAME,
DEFAULT_SSL,
DEFAULT_STATISTICS_ONLY,
DEFAULT_VERIFY_SSL,
)
from homeassistant.const import (
CONF_API_KEY,
CONF_HOST,
@ -47,6 +54,15 @@ API_KEY = "apikey"
SSL = False
VERIFY_SSL = True
CONF_DATA_DEFAULTS = {
CONF_HOST: f"{HOST}:{PORT}",
CONF_LOCATION: DEFAULT_LOCATION,
CONF_NAME: DEFAULT_NAME,
CONF_STATISTICS_ONLY: DEFAULT_STATISTICS_ONLY,
CONF_SSL: DEFAULT_SSL,
CONF_VERIFY_SSL: DEFAULT_VERIFY_SSL,
}
CONF_DATA = {
CONF_HOST: f"{HOST}:{PORT}",
CONF_LOCATION: LOCATION,

View File

@ -1,24 +1,21 @@
"""Test pi_hole config flow."""
import logging
from unittest.mock import patch
from homeassistant.components.pi_hole.const import CONF_STATISTICS_ONLY, DOMAIN
from homeassistant.config_entries import SOURCE_IMPORT, SOURCE_USER
from homeassistant.config_entries import SOURCE_USER
from homeassistant.const import CONF_API_KEY
from homeassistant.core import HomeAssistant
from homeassistant.data_entry_flow import FlowResultType
from . import (
CONF_CONFIG_ENTRY,
CONF_CONFIG_FLOW_API_KEY,
CONF_CONFIG_FLOW_USER,
CONF_DATA,
NAME,
_create_mocked_hole,
_patch_config_flow_hole,
)
def _flow_next(hass, flow_id):
def _flow_next(hass: HomeAssistant, flow_id: str):
return next(
flow
for flow in hass.config_entries.flow.async_progress()
@ -26,48 +23,10 @@ def _flow_next(hass, flow_id):
)
def _patch_setup():
return patch(
"homeassistant.components.pi_hole.async_setup_entry",
return_value=True,
)
async def test_flow_import(hass, caplog):
"""Test import flow."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_setup():
result = await hass.config_entries.flow.async_init(
DOMAIN, context={"source": SOURCE_IMPORT}, data=CONF_DATA
)
assert result["type"] == FlowResultType.CREATE_ENTRY
assert result["title"] == NAME
assert result["data"] == CONF_CONFIG_ENTRY
# duplicated server
result = await hass.config_entries.flow.async_init(
DOMAIN, context={"source": SOURCE_IMPORT}, data=CONF_DATA
)
assert result["type"] == FlowResultType.ABORT
assert result["reason"] == "already_configured"
async def test_flow_import_invalid(hass, caplog):
"""Test import flow with invalid server."""
mocked_hole = _create_mocked_hole(True)
with _patch_config_flow_hole(mocked_hole), _patch_setup():
result = await hass.config_entries.flow.async_init(
DOMAIN, context={"source": SOURCE_IMPORT}, data=CONF_DATA
)
assert result["type"] == FlowResultType.ABORT
assert result["reason"] == "cannot_connect"
assert len([x for x in caplog.records if x.levelno == logging.ERROR]) == 1
async def test_flow_user(hass):
async def test_flow_user(hass: HomeAssistant):
"""Test user initialized flow."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_setup():
with _patch_config_flow_hole(mocked_hole):
result = await hass.config_entries.flow.async_init(
DOMAIN,
context={"source": SOURCE_USER},
@ -104,10 +63,10 @@ async def test_flow_user(hass):
assert result["reason"] == "already_configured"
async def test_flow_statistics_only(hass):
async def test_flow_statistics_only(hass: HomeAssistant):
"""Test user initialized flow with statistics only."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_setup():
with _patch_config_flow_hole(mocked_hole):
result = await hass.config_entries.flow.async_init(
DOMAIN,
context={"source": SOURCE_USER},
@ -131,10 +90,10 @@ async def test_flow_statistics_only(hass):
assert result["data"] == config_entry_data
async def test_flow_user_invalid(hass):
async def test_flow_user_invalid(hass: HomeAssistant):
"""Test user initialized flow with invalid server."""
mocked_hole = _create_mocked_hole(True)
with _patch_config_flow_hole(mocked_hole), _patch_setup():
with _patch_config_flow_hole(mocked_hole):
result = await hass.config_entries.flow.async_init(
DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW_USER
)

View File

@ -23,29 +23,27 @@ from homeassistant.const import (
CONF_SSL,
CONF_VERIFY_SSL,
)
from homeassistant.setup import async_setup_component
from homeassistant.core import HomeAssistant
from . import (
CONF_CONFIG_ENTRY,
CONF_DATA,
CONF_DATA_DEFAULTS,
SWITCH_ENTITY_ID,
_create_mocked_hole,
_patch_config_flow_hole,
_patch_init_hole,
)
from tests.common import MockConfigEntry
async def test_setup_minimal_config(hass):
"""Tests component setup with minimal config."""
async def test_setup_with_defaults(hass: HomeAssistant):
"""Tests component setup with default config."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
assert await async_setup_component(
hass, pi_hole.DOMAIN, {pi_hole.DOMAIN: [{"host": "pi.hole"}]}
)
await hass.async_block_till_done()
entry = MockConfigEntry(domain=pi_hole.DOMAIN, data=CONF_DATA_DEFAULTS)
entry.add_to_hass(hass)
with _patch_init_hole(mocked_hole):
assert await hass.config_entries.async_setup(entry.entry_id)
state = hass.states.get("sensor.pi_hole_ads_blocked_today")
assert state.name == "Pi-Hole Ads Blocked Today"
@ -88,15 +86,15 @@ async def test_setup_minimal_config(hass):
assert state.state == "off"
async def test_setup_name_config(hass):
async def test_setup_name_config(hass: HomeAssistant):
"""Tests component setup with a custom name."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
assert await async_setup_component(
hass,
pi_hole.DOMAIN,
{pi_hole.DOMAIN: [{"host": "pi.hole", "name": "Custom"}]},
)
entry = MockConfigEntry(
domain=pi_hole.DOMAIN, data={**CONF_DATA_DEFAULTS, CONF_NAME: "Custom"}
)
entry.add_to_hass(hass)
with _patch_init_hole(mocked_hole):
assert await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()
@ -106,15 +104,14 @@ async def test_setup_name_config(hass):
)
async def test_switch(hass, caplog):
async def test_switch(hass: HomeAssistant, caplog):
"""Test Pi-hole switch."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
assert await async_setup_component(
hass,
pi_hole.DOMAIN,
{pi_hole.DOMAIN: [{"host": "pi.hole1", "api_key": "1"}]},
)
entry = MockConfigEntry(domain=pi_hole.DOMAIN, data=CONF_DATA)
entry.add_to_hass(hass)
with _patch_init_hole(mocked_hole):
assert await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()
@ -154,20 +151,20 @@ async def test_switch(hass, caplog):
assert errors[-1].message == "Unable to disable Pi-hole: Error2"
async def test_disable_service_call(hass):
async def test_disable_service_call(hass: HomeAssistant):
"""Test disable service call with no Pi-hole named."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
assert await async_setup_component(
hass,
pi_hole.DOMAIN,
{
pi_hole.DOMAIN: [
{"host": "pi.hole1", "api_key": "1"},
{"host": "pi.hole2", "name": "Custom"},
]
},
with _patch_init_hole(mocked_hole):
entry = MockConfigEntry(domain=pi_hole.DOMAIN, data=CONF_DATA)
entry.add_to_hass(hass)
assert await hass.config_entries.async_setup(entry.entry_id)
entry = MockConfigEntry(
domain=pi_hole.DOMAIN, data={**CONF_DATA_DEFAULTS, CONF_NAME: "Custom"}
)
entry.add_to_hass(hass)
assert await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()
@ -183,7 +180,7 @@ async def test_disable_service_call(hass):
mocked_hole.disable.assert_called_once_with(1)
async def test_unload(hass):
async def test_unload(hass: HomeAssistant):
"""Test unload entities."""
entry = MockConfigEntry(
domain=pi_hole.DOMAIN,
@ -198,7 +195,7 @@ async def test_unload(hass):
)
entry.add_to_hass(hass)
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
with _patch_init_hole(mocked_hole):
await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()
assert entry.entry_id in hass.data[pi_hole.DOMAIN]
@ -208,20 +205,20 @@ async def test_unload(hass):
assert entry.entry_id not in hass.data[pi_hole.DOMAIN]
async def test_migrate(hass):
async def test_migrate(hass: HomeAssistant):
"""Test migrate from old config entry."""
entry = MockConfigEntry(domain=pi_hole.DOMAIN, data=CONF_DATA)
entry.add_to_hass(hass)
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
with _patch_init_hole(mocked_hole):
await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()
assert entry.data == CONF_CONFIG_ENTRY
async def test_migrate_statistics_only(hass):
async def test_migrate_statistics_only(hass: HomeAssistant):
"""Test migrate from old config entry with statistics only."""
conf_data = {**CONF_DATA}
conf_data[CONF_API_KEY] = ""
@ -229,7 +226,7 @@ async def test_migrate_statistics_only(hass):
entry.add_to_hass(hass)
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
with _patch_init_hole(mocked_hole):
await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()

View File

@ -2,18 +2,20 @@
from homeassistant.components import pi_hole
from homeassistant.const import STATE_ON, STATE_UNKNOWN
from homeassistant.setup import async_setup_component
from homeassistant.core import HomeAssistant
from . import _create_mocked_hole, _patch_config_flow_hole, _patch_init_hole
from . import CONF_DATA_DEFAULTS, _create_mocked_hole, _patch_init_hole
from tests.common import MockConfigEntry
async def test_update(hass):
async def test_update(hass: HomeAssistant):
"""Tests update entity."""
mocked_hole = _create_mocked_hole()
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
assert await async_setup_component(
hass, pi_hole.DOMAIN, {pi_hole.DOMAIN: [{"host": "pi.hole"}]}
)
entry = MockConfigEntry(domain=pi_hole.DOMAIN, data=CONF_DATA_DEFAULTS)
entry.add_to_hass(hass)
with _patch_init_hole(mocked_hole):
assert await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()
@ -48,13 +50,13 @@ async def test_update(hass):
)
async def test_update_no_versions(hass):
async def test_update_no_versions(hass: HomeAssistant):
"""Tests update entity when no version data available."""
mocked_hole = _create_mocked_hole(has_versions=False)
with _patch_config_flow_hole(mocked_hole), _patch_init_hole(mocked_hole):
assert await async_setup_component(
hass, pi_hole.DOMAIN, {pi_hole.DOMAIN: [{"host": "pi.hole"}]}
)
entry = MockConfigEntry(domain=pi_hole.DOMAIN, data=CONF_DATA_DEFAULTS)
entry.add_to_hass(hass)
with _patch_init_hole(mocked_hole):
assert await hass.config_entries.async_setup(entry.entry_id)
await hass.async_block_till_done()