mirror of
https://github.com/home-assistant/core.git
synced 2025-07-25 14:17:45 +00:00
Support units and filters in async_get_travel_times_service for waze_travel_time (#130776)
This commit is contained in:
parent
da85c497bf
commit
98d5020690
@ -3,12 +3,13 @@
|
|||||||
import asyncio
|
import asyncio
|
||||||
from collections.abc import Collection
|
from collections.abc import Collection
|
||||||
import logging
|
import logging
|
||||||
|
from typing import Literal
|
||||||
|
|
||||||
from pywaze.route_calculator import CalcRoutesResponse, WazeRouteCalculator, WRCError
|
from pywaze.route_calculator import CalcRoutesResponse, WazeRouteCalculator, WRCError
|
||||||
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_REGION, Platform
|
from homeassistant.const import CONF_REGION, Platform, UnitOfLength
|
||||||
from homeassistant.core import (
|
from homeassistant.core import (
|
||||||
HomeAssistant,
|
HomeAssistant,
|
||||||
ServiceCall,
|
ServiceCall,
|
||||||
@ -22,7 +23,10 @@ from homeassistant.helpers.selector import (
|
|||||||
SelectSelectorConfig,
|
SelectSelectorConfig,
|
||||||
SelectSelectorMode,
|
SelectSelectorMode,
|
||||||
TextSelector,
|
TextSelector,
|
||||||
|
TextSelectorConfig,
|
||||||
|
TextSelectorType,
|
||||||
)
|
)
|
||||||
|
from homeassistant.util.unit_conversion import DistanceConverter
|
||||||
|
|
||||||
from .const import (
|
from .const import (
|
||||||
CONF_AVOID_FERRIES,
|
CONF_AVOID_FERRIES,
|
||||||
@ -38,6 +42,7 @@ from .const import (
|
|||||||
DEFAULT_FILTER,
|
DEFAULT_FILTER,
|
||||||
DEFAULT_VEHICLE_TYPE,
|
DEFAULT_VEHICLE_TYPE,
|
||||||
DOMAIN,
|
DOMAIN,
|
||||||
|
IMPERIAL_UNITS,
|
||||||
METRIC_UNITS,
|
METRIC_UNITS,
|
||||||
REGIONS,
|
REGIONS,
|
||||||
SEMAPHORE,
|
SEMAPHORE,
|
||||||
@ -80,6 +85,18 @@ SERVICE_GET_TRAVEL_TIMES_SCHEMA = vol.Schema(
|
|||||||
vol.Optional(CONF_AVOID_TOLL_ROADS, default=False): BooleanSelector(),
|
vol.Optional(CONF_AVOID_TOLL_ROADS, default=False): BooleanSelector(),
|
||||||
vol.Optional(CONF_AVOID_SUBSCRIPTION_ROADS, default=False): BooleanSelector(),
|
vol.Optional(CONF_AVOID_SUBSCRIPTION_ROADS, default=False): BooleanSelector(),
|
||||||
vol.Optional(CONF_AVOID_FERRIES, default=False): BooleanSelector(),
|
vol.Optional(CONF_AVOID_FERRIES, default=False): BooleanSelector(),
|
||||||
|
vol.Optional(CONF_INCL_FILTER): TextSelector(
|
||||||
|
TextSelectorConfig(
|
||||||
|
type=TextSelectorType.TEXT,
|
||||||
|
multiple=True,
|
||||||
|
),
|
||||||
|
),
|
||||||
|
vol.Optional(CONF_EXCL_FILTER): TextSelector(
|
||||||
|
TextSelectorConfig(
|
||||||
|
type=TextSelectorType.TEXT,
|
||||||
|
multiple=True,
|
||||||
|
),
|
||||||
|
),
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -107,6 +124,9 @@ async def async_setup_entry(hass: HomeAssistant, config_entry: ConfigEntry) -> b
|
|||||||
avoid_subscription_roads=service.data[CONF_AVOID_SUBSCRIPTION_ROADS],
|
avoid_subscription_roads=service.data[CONF_AVOID_SUBSCRIPTION_ROADS],
|
||||||
avoid_ferries=service.data[CONF_AVOID_FERRIES],
|
avoid_ferries=service.data[CONF_AVOID_FERRIES],
|
||||||
realtime=service.data[CONF_REALTIME],
|
realtime=service.data[CONF_REALTIME],
|
||||||
|
units=service.data[CONF_UNITS],
|
||||||
|
incl_filters=service.data.get(CONF_INCL_FILTER, DEFAULT_FILTER),
|
||||||
|
excl_filters=service.data.get(CONF_EXCL_FILTER, DEFAULT_FILTER),
|
||||||
)
|
)
|
||||||
return {"routes": [vars(route) for route in response]} if response else None
|
return {"routes": [vars(route) for route in response]} if response else None
|
||||||
|
|
||||||
@ -129,6 +149,7 @@ async def async_get_travel_times(
|
|||||||
avoid_subscription_roads: bool,
|
avoid_subscription_roads: bool,
|
||||||
avoid_ferries: bool,
|
avoid_ferries: bool,
|
||||||
realtime: bool,
|
realtime: bool,
|
||||||
|
units: Literal["metric", "imperial"] = "metric",
|
||||||
incl_filters: Collection[str] | None = None,
|
incl_filters: Collection[str] | None = None,
|
||||||
excl_filters: Collection[str] | None = None,
|
excl_filters: Collection[str] | None = None,
|
||||||
) -> list[CalcRoutesResponse] | None:
|
) -> list[CalcRoutesResponse] | None:
|
||||||
@ -194,6 +215,20 @@ async def async_get_travel_times(
|
|||||||
route for route in incl_routes if not should_exclude_route(route)
|
route for route in incl_routes if not should_exclude_route(route)
|
||||||
]
|
]
|
||||||
|
|
||||||
|
if units == IMPERIAL_UNITS:
|
||||||
|
filtered_routes = [
|
||||||
|
CalcRoutesResponse(
|
||||||
|
name=route.name,
|
||||||
|
distance=DistanceConverter.convert(
|
||||||
|
route.distance, UnitOfLength.KILOMETERS, UnitOfLength.MILES
|
||||||
|
),
|
||||||
|
duration=route.duration,
|
||||||
|
street_names=route.street_names,
|
||||||
|
)
|
||||||
|
for route in filtered_routes
|
||||||
|
if route.distance is not None
|
||||||
|
]
|
||||||
|
|
||||||
if len(filtered_routes) < 1:
|
if len(filtered_routes) < 1:
|
||||||
_LOGGER.warning("No routes found")
|
_LOGGER.warning("No routes found")
|
||||||
return None
|
return None
|
||||||
|
@ -20,7 +20,6 @@ from homeassistant.const import (
|
|||||||
CONF_NAME,
|
CONF_NAME,
|
||||||
CONF_REGION,
|
CONF_REGION,
|
||||||
EVENT_HOMEASSISTANT_STARTED,
|
EVENT_HOMEASSISTANT_STARTED,
|
||||||
UnitOfLength,
|
|
||||||
UnitOfTime,
|
UnitOfTime,
|
||||||
)
|
)
|
||||||
from homeassistant.core import CoreState, HomeAssistant
|
from homeassistant.core import CoreState, HomeAssistant
|
||||||
@ -28,7 +27,6 @@ from homeassistant.helpers.device_registry import DeviceEntryType, DeviceInfo
|
|||||||
from homeassistant.helpers.entity_platform import AddEntitiesCallback
|
from homeassistant.helpers.entity_platform import AddEntitiesCallback
|
||||||
from homeassistant.helpers.httpx_client import get_async_client
|
from homeassistant.helpers.httpx_client import get_async_client
|
||||||
from homeassistant.helpers.location import find_coordinates
|
from homeassistant.helpers.location import find_coordinates
|
||||||
from homeassistant.util.unit_conversion import DistanceConverter
|
|
||||||
|
|
||||||
from . import async_get_travel_times
|
from . import async_get_travel_times
|
||||||
from .const import (
|
from .const import (
|
||||||
@ -44,7 +42,6 @@ from .const import (
|
|||||||
CONF_VEHICLE_TYPE,
|
CONF_VEHICLE_TYPE,
|
||||||
DEFAULT_NAME,
|
DEFAULT_NAME,
|
||||||
DOMAIN,
|
DOMAIN,
|
||||||
IMPERIAL_UNITS,
|
|
||||||
SEMAPHORE,
|
SEMAPHORE,
|
||||||
)
|
)
|
||||||
|
|
||||||
@ -201,6 +198,7 @@ class WazeTravelTimeData:
|
|||||||
avoid_subscription_roads,
|
avoid_subscription_roads,
|
||||||
avoid_ferries,
|
avoid_ferries,
|
||||||
realtime,
|
realtime,
|
||||||
|
self.config_entry.options[CONF_UNITS],
|
||||||
incl_filter,
|
incl_filter,
|
||||||
excl_filter,
|
excl_filter,
|
||||||
)
|
)
|
||||||
@ -211,14 +209,5 @@ class WazeTravelTimeData:
|
|||||||
return
|
return
|
||||||
|
|
||||||
self.duration = route.duration
|
self.duration = route.duration
|
||||||
distance = route.distance
|
self.distance = route.distance
|
||||||
|
|
||||||
if self.config_entry.options[CONF_UNITS] == IMPERIAL_UNITS:
|
|
||||||
# Convert to miles.
|
|
||||||
self.distance = DistanceConverter.convert(
|
|
||||||
distance, UnitOfLength.KILOMETERS, UnitOfLength.MILES
|
|
||||||
)
|
|
||||||
else:
|
|
||||||
self.distance = distance
|
|
||||||
|
|
||||||
self.route = route.name
|
self.route = route.name
|
||||||
|
@ -55,3 +55,13 @@ get_travel_times:
|
|||||||
required: false
|
required: false
|
||||||
selector:
|
selector:
|
||||||
boolean:
|
boolean:
|
||||||
|
incl_filter:
|
||||||
|
required: false
|
||||||
|
selector:
|
||||||
|
text:
|
||||||
|
multiple: true
|
||||||
|
excl_filter:
|
||||||
|
required: false
|
||||||
|
selector:
|
||||||
|
text:
|
||||||
|
multiple: true
|
||||||
|
@ -101,6 +101,14 @@
|
|||||||
"avoid_subscription_roads": {
|
"avoid_subscription_roads": {
|
||||||
"name": "[%key:component::waze_travel_time::options::step::init::data::avoid_subscription_roads%]",
|
"name": "[%key:component::waze_travel_time::options::step::init::data::avoid_subscription_roads%]",
|
||||||
"description": "Whether to avoid subscription roads."
|
"description": "Whether to avoid subscription roads."
|
||||||
|
},
|
||||||
|
"incl_filter": {
|
||||||
|
"name": "[%key:component::waze_travel_time::options::step::init::data::incl_filter%]",
|
||||||
|
"description": "Exact streetname which must be part of the selected route."
|
||||||
|
},
|
||||||
|
"excl_filter": {
|
||||||
|
"name": "[%key:component::waze_travel_time::options::step::init::data::excl_filter%]",
|
||||||
|
"description": "Exact streetname which must NOT be part of the selected route."
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -44,6 +44,8 @@ async def test_service_get_travel_times(hass: HomeAssistant) -> None:
|
|||||||
"destination": "location2",
|
"destination": "location2",
|
||||||
"vehicle_type": "car",
|
"vehicle_type": "car",
|
||||||
"region": "us",
|
"region": "us",
|
||||||
|
"units": "imperial",
|
||||||
|
"incl_filter": ["IncludeThis"],
|
||||||
},
|
},
|
||||||
blocking=True,
|
blocking=True,
|
||||||
return_response=True,
|
return_response=True,
|
||||||
@ -51,17 +53,11 @@ async def test_service_get_travel_times(hass: HomeAssistant) -> None:
|
|||||||
assert response_data == {
|
assert response_data == {
|
||||||
"routes": [
|
"routes": [
|
||||||
{
|
{
|
||||||
"distance": 300,
|
"distance": pytest.approx(186.4113),
|
||||||
"duration": 150,
|
"duration": 150,
|
||||||
"name": "E1337 - Teststreet",
|
"name": "E1337 - Teststreet",
|
||||||
"street_names": ["E1337", "IncludeThis", "Teststreet"],
|
"street_names": ["E1337", "IncludeThis", "Teststreet"],
|
||||||
},
|
},
|
||||||
{
|
|
||||||
"distance": 500,
|
|
||||||
"duration": 600,
|
|
||||||
"name": "E0815 - Otherstreet",
|
|
||||||
"street_names": ["E0815", "ExcludeThis", "Otherstreet"],
|
|
||||||
},
|
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user