Compare commits
4 commits
dev
...
gj-2024110
Author | SHA1 | Date | |
---|---|---|---|
|
6c2adda23a | ||
|
d4cedcb4f8 | ||
|
e1dd5543e4 | ||
|
35c95a1c2b |
7 changed files with 639 additions and 1 deletions
|
@ -4,13 +4,25 @@ from __future__ import annotations
|
|||
|
||||
from homeassistant.config_entries import ConfigEntry
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.helpers import config_validation as cv
|
||||
from homeassistant.helpers.typing import ConfigType
|
||||
from homeassistant.util import dt as dt_util
|
||||
|
||||
from .const import PLATFORMS
|
||||
from .const import DOMAIN, PLATFORMS
|
||||
from .coordinator import NordPoolDataUpdateCoordinator
|
||||
from .services import async_setup_services
|
||||
|
||||
type NordPoolConfigEntry = ConfigEntry[NordPoolDataUpdateCoordinator]
|
||||
|
||||
CONFIG_SCHEMA = cv.config_entry_only_config_schema(DOMAIN)
|
||||
|
||||
|
||||
async def async_setup(hass: HomeAssistant, config: ConfigType) -> bool:
|
||||
"""Set up the Habitica service."""
|
||||
|
||||
async_setup_services(hass)
|
||||
return True
|
||||
|
||||
|
||||
async def async_setup_entry(hass: HomeAssistant, entry: NordPoolConfigEntry) -> bool:
|
||||
"""Set up Nord Pool from a config entry."""
|
||||
|
|
|
@ -38,5 +38,10 @@
|
|||
"default": "mdi:cash-multiple"
|
||||
}
|
||||
}
|
||||
},
|
||||
"services": {
|
||||
"get_prices_for_date": {
|
||||
"service": "mdi:cash-multiple"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
127
homeassistant/components/nordpool/services.py
Normal file
127
homeassistant/components/nordpool/services.py
Normal file
|
@ -0,0 +1,127 @@
|
|||
"""Services for Nord Pool integration."""
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from datetime import date, datetime
|
||||
import logging
|
||||
from typing import TYPE_CHECKING
|
||||
|
||||
from pynordpool import (
|
||||
Currency,
|
||||
NordPoolAuthenticationError,
|
||||
NordPoolEmptyResponseError,
|
||||
NordPoolError,
|
||||
)
|
||||
import voluptuous as vol
|
||||
|
||||
from homeassistant.config_entries import ConfigEntryState
|
||||
from homeassistant.const import ATTR_DATE
|
||||
from homeassistant.core import (
|
||||
HomeAssistant,
|
||||
ServiceCall,
|
||||
ServiceResponse,
|
||||
SupportsResponse,
|
||||
)
|
||||
from homeassistant.exceptions import ServiceValidationError
|
||||
from homeassistant.helpers import config_validation as cv
|
||||
from homeassistant.helpers.selector import ConfigEntrySelector
|
||||
from homeassistant.util import dt as dt_util
|
||||
from homeassistant.util.json import JsonValueType
|
||||
|
||||
if TYPE_CHECKING:
|
||||
from . import NordPoolConfigEntry
|
||||
from .const import DOMAIN
|
||||
|
||||
_LOGGER = logging.getLogger(__name__)
|
||||
ATTR_CONFIG_ENTRY = "config_entry"
|
||||
ATTR_AREAS = "areas"
|
||||
ATTR_CURRENCY = "currency"
|
||||
|
||||
SERVICE_GET_PRICES_FOR_DATE = "get_prices_for_date"
|
||||
SERVICE_GET_PRICES_SCHEMA = vol.Schema(
|
||||
{
|
||||
vol.Required(ATTR_CONFIG_ENTRY): ConfigEntrySelector(),
|
||||
vol.Required(ATTR_DATE): cv.date,
|
||||
vol.Optional(ATTR_AREAS, default=[]): cv.ensure_list,
|
||||
vol.Optional(ATTR_CURRENCY): cv.string,
|
||||
}
|
||||
)
|
||||
|
||||
|
||||
def get_config_entry(hass: HomeAssistant, entry_id: str) -> NordPoolConfigEntry:
|
||||
"""Return config entry."""
|
||||
if not (entry := hass.config_entries.async_get_entry(entry_id)):
|
||||
raise ServiceValidationError(
|
||||
translation_domain=DOMAIN,
|
||||
translation_key="entry_not_found",
|
||||
)
|
||||
if entry.state is not ConfigEntryState.LOADED:
|
||||
raise ServiceValidationError(
|
||||
translation_domain=DOMAIN,
|
||||
translation_key="entry_not_loaded",
|
||||
)
|
||||
return entry
|
||||
|
||||
|
||||
def async_setup_services(hass: HomeAssistant) -> None:
|
||||
"""Set up services for Nord Pool integration."""
|
||||
|
||||
async def get_prices_for_date(call: ServiceCall) -> ServiceResponse:
|
||||
"""Get price service."""
|
||||
entry = get_config_entry(hass, call.data[ATTR_CONFIG_ENTRY])
|
||||
asked_date: date = call.data[ATTR_DATE]
|
||||
client = entry.runtime_data.client
|
||||
areas: list[str] | None = call.data.get(ATTR_AREAS)
|
||||
if not areas:
|
||||
areas = entry.data[ATTR_AREAS]
|
||||
currency: str | None = call.data.get(ATTR_CURRENCY)
|
||||
if not currency:
|
||||
currency = entry.data[ATTR_CURRENCY]
|
||||
|
||||
if TYPE_CHECKING:
|
||||
assert isinstance(areas, list)
|
||||
assert isinstance(currency, str)
|
||||
areas = [area.upper() for area in areas]
|
||||
currency = currency.upper()
|
||||
|
||||
try:
|
||||
price_data = await client.async_get_delivery_period(
|
||||
datetime.combine(asked_date, dt_util.utcnow().time()),
|
||||
Currency(currency),
|
||||
areas,
|
||||
)
|
||||
except NordPoolAuthenticationError as error:
|
||||
raise ServiceValidationError(
|
||||
translation_domain=DOMAIN,
|
||||
translation_key="authentication_error",
|
||||
) from error
|
||||
except NordPoolEmptyResponseError as error:
|
||||
raise ServiceValidationError(
|
||||
translation_domain=DOMAIN,
|
||||
translation_key="empty_response",
|
||||
) from error
|
||||
except NordPoolError as error:
|
||||
raise ServiceValidationError(
|
||||
translation_domain=DOMAIN,
|
||||
translation_key="connection_error",
|
||||
) from error
|
||||
|
||||
result: dict[str, JsonValueType] = {}
|
||||
for area in areas:
|
||||
result[area] = [
|
||||
{
|
||||
"start": price_entry.start.isoformat(),
|
||||
"end": price_entry.end.isoformat(),
|
||||
"price": price_entry.entry[area],
|
||||
}
|
||||
for price_entry in price_data.entries
|
||||
]
|
||||
return result
|
||||
|
||||
hass.services.async_register(
|
||||
DOMAIN,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
get_prices_for_date,
|
||||
schema=SERVICE_GET_PRICES_SCHEMA,
|
||||
supports_response=SupportsResponse.ONLY,
|
||||
)
|
26
homeassistant/components/nordpool/services.yaml
Normal file
26
homeassistant/components/nordpool/services.yaml
Normal file
|
@ -0,0 +1,26 @@
|
|||
get_prices_for_date:
|
||||
fields:
|
||||
config_entry:
|
||||
required: true
|
||||
selector:
|
||||
config_entry:
|
||||
integration: nordpool
|
||||
date:
|
||||
required: true
|
||||
selector:
|
||||
date:
|
||||
areas:
|
||||
selector:
|
||||
text:
|
||||
multiple: true
|
||||
currency:
|
||||
selector:
|
||||
select:
|
||||
options:
|
||||
- "DKK"
|
||||
- "EUR"
|
||||
- "NOK"
|
||||
- "PLN"
|
||||
- "SEK"
|
||||
mode: dropdown
|
||||
translation_key: "currency"
|
|
@ -61,5 +61,57 @@
|
|||
"name": "Daily average"
|
||||
}
|
||||
}
|
||||
},
|
||||
"services": {
|
||||
"get_prices_for_date": {
|
||||
"name": "Get prices for date",
|
||||
"description": "Retrieve the prices for a specific date.",
|
||||
"fields": {
|
||||
"config_entry": {
|
||||
"name": "Select Nord Pool configuration entry",
|
||||
"description": "Choose the configuration entry."
|
||||
},
|
||||
"date": {
|
||||
"name": "Date",
|
||||
"description": "Only dates two months in the past and one day in the future is allowed."
|
||||
},
|
||||
"areas": {
|
||||
"name": "Areas",
|
||||
"description": "One or multiple areas to get prices for. If left empty it will use the areas already configured."
|
||||
},
|
||||
"currency": {
|
||||
"name": "Currency",
|
||||
"description": "Currency to get prices in. If left empty it will use the currency already configured."
|
||||
}
|
||||
}
|
||||
}
|
||||
},
|
||||
"selector": {
|
||||
"currency": {
|
||||
"options": {
|
||||
"dkk": "DKK",
|
||||
"eur": "EUR",
|
||||
"nok": "NOK",
|
||||
"pln": "PLN",
|
||||
"sek": "SEK"
|
||||
}
|
||||
}
|
||||
},
|
||||
"exceptions": {
|
||||
"entry_not_found": {
|
||||
"message": "The Nord Pool integration is not configured in Home Assistant."
|
||||
},
|
||||
"entry_not_loaded": {
|
||||
"message": "The Nord Pool integration is currently not loaded or disabled in Home Assistant."
|
||||
},
|
||||
"authentication_error": {
|
||||
"message": "There was an authentication error as you tried to retrieve data too far in the past."
|
||||
},
|
||||
"empty_response": {
|
||||
"message": "Nord Pool has not posted market prices for the provided date."
|
||||
},
|
||||
"connection_error": {
|
||||
"message": "There was a connection error connecting to the API. Try again later."
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
249
tests/components/nordpool/snapshots/test_services.ambr
Normal file
249
tests/components/nordpool/snapshots/test_services.ambr
Normal file
|
@ -0,0 +1,249 @@
|
|||
# serializer version: 1
|
||||
# name: test_service_call
|
||||
dict({
|
||||
'SE3': list([
|
||||
dict({
|
||||
'end': '2024-11-05T00:00:00+00:00',
|
||||
'price': 250.73,
|
||||
'start': '2024-11-04T23:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T01:00:00+00:00',
|
||||
'price': 76.36,
|
||||
'start': '2024-11-05T00:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T02:00:00+00:00',
|
||||
'price': 73.92,
|
||||
'start': '2024-11-05T01:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T03:00:00+00:00',
|
||||
'price': 61.69,
|
||||
'start': '2024-11-05T02:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T04:00:00+00:00',
|
||||
'price': 64.6,
|
||||
'start': '2024-11-05T03:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T05:00:00+00:00',
|
||||
'price': 453.27,
|
||||
'start': '2024-11-05T04:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T06:00:00+00:00',
|
||||
'price': 996.28,
|
||||
'start': '2024-11-05T05:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T07:00:00+00:00',
|
||||
'price': 1406.14,
|
||||
'start': '2024-11-05T06:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T08:00:00+00:00',
|
||||
'price': 1346.54,
|
||||
'start': '2024-11-05T07:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T09:00:00+00:00',
|
||||
'price': 1150.28,
|
||||
'start': '2024-11-05T08:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T10:00:00+00:00',
|
||||
'price': 1031.32,
|
||||
'start': '2024-11-05T09:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T11:00:00+00:00',
|
||||
'price': 927.37,
|
||||
'start': '2024-11-05T10:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T12:00:00+00:00',
|
||||
'price': 925.05,
|
||||
'start': '2024-11-05T11:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T13:00:00+00:00',
|
||||
'price': 949.49,
|
||||
'start': '2024-11-05T12:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T14:00:00+00:00',
|
||||
'price': 1042.03,
|
||||
'start': '2024-11-05T13:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T15:00:00+00:00',
|
||||
'price': 1258.89,
|
||||
'start': '2024-11-05T14:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T16:00:00+00:00',
|
||||
'price': 1816.45,
|
||||
'start': '2024-11-05T15:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T17:00:00+00:00',
|
||||
'price': 2512.65,
|
||||
'start': '2024-11-05T16:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T18:00:00+00:00',
|
||||
'price': 1819.83,
|
||||
'start': '2024-11-05T17:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T19:00:00+00:00',
|
||||
'price': 1011.77,
|
||||
'start': '2024-11-05T18:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T20:00:00+00:00',
|
||||
'price': 835.53,
|
||||
'start': '2024-11-05T19:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T21:00:00+00:00',
|
||||
'price': 796.19,
|
||||
'start': '2024-11-05T20:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T22:00:00+00:00',
|
||||
'price': 522.3,
|
||||
'start': '2024-11-05T21:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T23:00:00+00:00',
|
||||
'price': 289.14,
|
||||
'start': '2024-11-05T22:00:00+00:00',
|
||||
}),
|
||||
]),
|
||||
'SE4': list([
|
||||
dict({
|
||||
'end': '2024-11-05T00:00:00+00:00',
|
||||
'price': 283.79,
|
||||
'start': '2024-11-04T23:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T01:00:00+00:00',
|
||||
'price': 81.36,
|
||||
'start': '2024-11-05T00:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T02:00:00+00:00',
|
||||
'price': 79.15,
|
||||
'start': '2024-11-05T01:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T03:00:00+00:00',
|
||||
'price': 65.19,
|
||||
'start': '2024-11-05T02:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T04:00:00+00:00',
|
||||
'price': 68.44,
|
||||
'start': '2024-11-05T03:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T05:00:00+00:00',
|
||||
'price': 516.71,
|
||||
'start': '2024-11-05T04:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T06:00:00+00:00',
|
||||
'price': 1240.85,
|
||||
'start': '2024-11-05T05:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T07:00:00+00:00',
|
||||
'price': 1648.25,
|
||||
'start': '2024-11-05T06:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T08:00:00+00:00',
|
||||
'price': 1570.5,
|
||||
'start': '2024-11-05T07:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T09:00:00+00:00',
|
||||
'price': 1345.37,
|
||||
'start': '2024-11-05T08:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T10:00:00+00:00',
|
||||
'price': 1206.51,
|
||||
'start': '2024-11-05T09:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T11:00:00+00:00',
|
||||
'price': 1085.8,
|
||||
'start': '2024-11-05T10:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T12:00:00+00:00',
|
||||
'price': 1081.72,
|
||||
'start': '2024-11-05T11:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T13:00:00+00:00',
|
||||
'price': 1130.38,
|
||||
'start': '2024-11-05T12:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T14:00:00+00:00',
|
||||
'price': 1256.91,
|
||||
'start': '2024-11-05T13:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T15:00:00+00:00',
|
||||
'price': 1765.82,
|
||||
'start': '2024-11-05T14:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T16:00:00+00:00',
|
||||
'price': 2522.55,
|
||||
'start': '2024-11-05T15:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T17:00:00+00:00',
|
||||
'price': 3533.03,
|
||||
'start': '2024-11-05T16:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T18:00:00+00:00',
|
||||
'price': 2524.06,
|
||||
'start': '2024-11-05T17:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T19:00:00+00:00',
|
||||
'price': 1804.46,
|
||||
'start': '2024-11-05T18:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T20:00:00+00:00',
|
||||
'price': 1112.57,
|
||||
'start': '2024-11-05T19:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T21:00:00+00:00',
|
||||
'price': 1051.69,
|
||||
'start': '2024-11-05T20:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T22:00:00+00:00',
|
||||
'price': 662.44,
|
||||
'start': '2024-11-05T21:00:00+00:00',
|
||||
}),
|
||||
dict({
|
||||
'end': '2024-11-05T23:00:00+00:00',
|
||||
'price': 349.21,
|
||||
'start': '2024-11-05T22:00:00+00:00',
|
||||
}),
|
||||
]),
|
||||
})
|
||||
# ---
|
167
tests/components/nordpool/test_services.py
Normal file
167
tests/components/nordpool/test_services.py
Normal file
|
@ -0,0 +1,167 @@
|
|||
"""Test services in Nord Pool."""
|
||||
|
||||
from unittest.mock import patch
|
||||
|
||||
from pynordpool import (
|
||||
DeliveryPeriodData,
|
||||
NordPoolAuthenticationError,
|
||||
NordPoolEmptyResponseError,
|
||||
NordPoolError,
|
||||
)
|
||||
import pytest
|
||||
from syrupy.assertion import SnapshotAssertion
|
||||
|
||||
from homeassistant.components.nordpool.const import DOMAIN
|
||||
from homeassistant.components.nordpool.services import (
|
||||
ATTR_AREAS,
|
||||
ATTR_CONFIG_ENTRY,
|
||||
ATTR_CURRENCY,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
)
|
||||
from homeassistant.const import ATTR_DATE
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.exceptions import ServiceValidationError
|
||||
|
||||
from tests.common import MockConfigEntry
|
||||
|
||||
TEST_SERVICE_DATA = {
|
||||
ATTR_CONFIG_ENTRY: "to_replace",
|
||||
ATTR_DATE: "2024-11-05",
|
||||
ATTR_AREAS: ["SE3", "SE4"],
|
||||
ATTR_CURRENCY: "SEK",
|
||||
}
|
||||
TEST_SERVICE_DATA_USE_DEFAULTS = {
|
||||
ATTR_CONFIG_ENTRY: "to_replace",
|
||||
ATTR_DATE: "2024-11-05",
|
||||
}
|
||||
|
||||
|
||||
@pytest.mark.freeze_time("2024-11-05T18:00:00+00:00")
|
||||
async def test_service_call(
|
||||
hass: HomeAssistant,
|
||||
load_int: MockConfigEntry,
|
||||
get_data: DeliveryPeriodData,
|
||||
snapshot: SnapshotAssertion,
|
||||
) -> None:
|
||||
"""Test get_prices_for_date service call."""
|
||||
|
||||
with (
|
||||
patch(
|
||||
"homeassistant.components.nordpool.coordinator.NordPoolClient.async_get_delivery_period",
|
||||
return_value=get_data,
|
||||
),
|
||||
):
|
||||
service_data = TEST_SERVICE_DATA.copy()
|
||||
service_data[ATTR_CONFIG_ENTRY] = load_int.entry_id
|
||||
response = await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
service_data,
|
||||
blocking=True,
|
||||
return_response=True,
|
||||
)
|
||||
|
||||
assert response == snapshot
|
||||
price_value = response["SE3"][0]["price"]
|
||||
|
||||
with (
|
||||
patch(
|
||||
"homeassistant.components.nordpool.coordinator.NordPoolClient.async_get_delivery_period",
|
||||
return_value=get_data,
|
||||
),
|
||||
):
|
||||
service_data = TEST_SERVICE_DATA_USE_DEFAULTS.copy()
|
||||
service_data[ATTR_CONFIG_ENTRY] = load_int.entry_id
|
||||
response = await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
service_data,
|
||||
blocking=True,
|
||||
return_response=True,
|
||||
)
|
||||
|
||||
assert "SE3" in response
|
||||
assert "SE4" in response
|
||||
assert response["SE3"][0]["price"] == price_value
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
("error", "key"),
|
||||
[
|
||||
(NordPoolAuthenticationError, "authentication_error"),
|
||||
(NordPoolEmptyResponseError, "empty_response"),
|
||||
(NordPoolError, "connection_error"),
|
||||
],
|
||||
)
|
||||
@pytest.mark.freeze_time("2024-11-05T18:00:00+00:00")
|
||||
async def test_service_call_failures(
|
||||
hass: HomeAssistant,
|
||||
load_int: MockConfigEntry,
|
||||
error: Exception,
|
||||
key: str,
|
||||
) -> None:
|
||||
"""Test get_prices_for_date service call when it fails."""
|
||||
service_data = TEST_SERVICE_DATA.copy()
|
||||
service_data[ATTR_CONFIG_ENTRY] = load_int.entry_id
|
||||
|
||||
with (
|
||||
patch(
|
||||
"homeassistant.components.nordpool.coordinator.NordPoolClient.async_get_delivery_period",
|
||||
side_effect=error,
|
||||
),
|
||||
pytest.raises(ServiceValidationError) as err,
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
service_data,
|
||||
blocking=True,
|
||||
return_response=True,
|
||||
)
|
||||
assert err.value.translation_key == key
|
||||
|
||||
|
||||
@pytest.mark.freeze_time("2024-11-05T18:00:00+00:00")
|
||||
async def test_service_call_config_entry_bad_state(
|
||||
hass: HomeAssistant,
|
||||
load_int: MockConfigEntry,
|
||||
get_data: DeliveryPeriodData,
|
||||
) -> None:
|
||||
"""Test get_prices_for_date service call when config entry bad state."""
|
||||
|
||||
with (
|
||||
patch(
|
||||
"homeassistant.components.nordpool.coordinator.NordPoolClient.async_get_delivery_period",
|
||||
return_value=get_data,
|
||||
),
|
||||
pytest.raises(ServiceValidationError) as err,
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
TEST_SERVICE_DATA,
|
||||
blocking=True,
|
||||
return_response=True,
|
||||
)
|
||||
assert err.value.translation_key == "entry_not_found"
|
||||
|
||||
service_data = TEST_SERVICE_DATA.copy()
|
||||
service_data[ATTR_CONFIG_ENTRY] = load_int.entry_id
|
||||
await hass.config_entries.async_unload(load_int.entry_id)
|
||||
await hass.async_block_till_done()
|
||||
|
||||
with (
|
||||
patch(
|
||||
"homeassistant.components.nordpool.coordinator.NordPoolClient.async_get_delivery_period",
|
||||
return_value=get_data,
|
||||
),
|
||||
pytest.raises(ServiceValidationError) as err,
|
||||
):
|
||||
await hass.services.async_call(
|
||||
DOMAIN,
|
||||
SERVICE_GET_PRICES_FOR_DATE,
|
||||
service_data,
|
||||
blocking=True,
|
||||
return_response=True,
|
||||
)
|
||||
assert err.value.translation_key == "entry_not_loaded"
|
Loading…
Add table
Add a link
Reference in a new issue