Home Assistant Unofficial Reference 2024.12.1
services.py
Go to the documentation of this file.
1 """Services for Tibber integration."""
2 
3 from __future__ import annotations
4 
5 import datetime as dt
6 from datetime import datetime
7 from functools import partial
8 from typing import Any, Final
9 
10 import voluptuous as vol
11 
12 from homeassistant.core import (
13  HomeAssistant,
14  ServiceCall,
15  ServiceResponse,
16  SupportsResponse,
17  callback,
18 )
19 from homeassistant.exceptions import ServiceValidationError
20 from homeassistant.util import dt as dt_util
21 
22 from .const import DOMAIN
23 
24 PRICE_SERVICE_NAME = "get_prices"
25 ATTR_START: Final = "start"
26 ATTR_END: Final = "end"
27 
28 SERVICE_SCHEMA: Final = vol.Schema(
29  {
30  vol.Optional(ATTR_START): str,
31  vol.Optional(ATTR_END): str,
32  }
33 )
34 
35 
36 async def __get_prices(call: ServiceCall, *, hass: HomeAssistant) -> ServiceResponse:
37  tibber_connection = hass.data[DOMAIN]
38 
39  start = __get_date(call.data.get(ATTR_START), "start")
40  end = __get_date(call.data.get(ATTR_END), "end")
41 
42  if start >= end:
43  end = start + dt.timedelta(days=1)
44 
45  tibber_prices: dict[str, Any] = {}
46 
47  for tibber_home in tibber_connection.get_homes(only_active=True):
48  home_nickname = tibber_home.name
49 
50  price_data = [
51  {
52  "start_time": starts_at,
53  "price": price,
54  "level": tibber_home.price_level.get(starts_at),
55  }
56  for starts_at, price in tibber_home.price_total.items()
57  ]
58 
59  selected_data = [
60  price
61  for price in price_data
62  if start <= dt.datetime.fromisoformat(price["start_time"]) < end
63  ]
64  tibber_prices[home_nickname] = selected_data
65 
66  return {"prices": tibber_prices}
67 
68 
69 def __get_date(date_input: str | None, mode: str | None) -> datetime:
70  """Get date."""
71  if not date_input:
72  if mode == "end":
73  increment = dt.timedelta(days=1)
74  else:
75  increment = dt.timedelta()
76  return dt_util.start_of_local_day() + increment
77 
78  if value := dt_util.parse_datetime(date_input):
79  return dt_util.as_local(value)
80 
82  translation_domain=DOMAIN,
83  translation_key="invalid_date",
84  translation_placeholders={
85  "date": date_input,
86  },
87  )
88 
89 
90 @callback
91 def async_setup_services(hass: HomeAssistant) -> None:
92  """Set up services for Tibber integration."""
93 
94  hass.services.async_register(
95  DOMAIN,
96  PRICE_SERVICE_NAME,
97  partial(__get_prices, hass=hass),
98  schema=SERVICE_SCHEMA,
99  supports_response=SupportsResponse.ONLY,
100  )
None async_setup_services(HomeAssistant hass)
Definition: services.py:91
ServiceResponse __get_prices(ServiceCall call, *HomeAssistant hass)
Definition: services.py:36
datetime __get_date(str|None date_input, str|None mode)
Definition: services.py:69