Skip to content

Commit

Permalink
fix: further fine tune adaptive checking
Browse files Browse the repository at this point in the history
  • Loading branch information
alandtse committed Feb 5, 2020
1 parent 07c69e3 commit 5f1e34d
Show file tree
Hide file tree
Showing 3 changed files with 63 additions and 10 deletions.
8 changes: 8 additions & 0 deletions teslajsonpy/connection.py
Original file line number Diff line number Diff line change
Expand Up @@ -161,6 +161,8 @@ async def websocket_connect(self, vin: int, vehicle_id: int, **kwargs):
vehicle_id (int): vehicle_id from Tesla api
on_message (function): function to call on a valid message. It must
process a json delivered in data
on_disconnect (function): function to call on a disconnect message. It must
process a json delivered in data
"""

Expand All @@ -183,6 +185,12 @@ async def _process_messages() -> None:
raise TeslaException(
"Can't validate token for websocket connection."
)
if (
msg_json["msg_type"] == "data:error"
and msg_json["value"] == "disconnected"
):
if kwargs.get("on_disconnect"):
kwargs.get("on_disconnect")()
if kwargs.get("on_message"):
kwargs.get("on_message")(msg_json)
elif msg.type == aiohttp.WSMsgType.ERROR:
Expand Down
1 change: 1 addition & 0 deletions teslajsonpy/const.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,3 +8,4 @@
IDLE_INTERVAL = 600 # interval after parking to check at regular update_interval
ONLINE_INTERVAL = 60 # interval for checking online state; does not hit individual cars
SLEEP_INTERVAL = 660 # interval required to let vehicle sleep; based on testing
DRIVING_INTERVAL = 60 # interval when driving detected
64 changes: 54 additions & 10 deletions teslajsonpy/controller.py
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,12 @@
from teslajsonpy.charger import ChargerSwitch, ChargingSensor, RangeSwitch
from teslajsonpy.climate import Climate, TempSensor
from teslajsonpy.connection import Connection
from teslajsonpy.const import IDLE_INTERVAL, ONLINE_INTERVAL, SLEEP_INTERVAL
from teslajsonpy.const import (
DRIVING_INTERVAL,
IDLE_INTERVAL,
ONLINE_INTERVAL,
SLEEP_INTERVAL,
)
from teslajsonpy.exceptions import RetryLimitError, TeslaException
from teslajsonpy.gps import GPS, Odometer
from teslajsonpy.lock import ChargerLock, Lock
Expand Down Expand Up @@ -79,6 +84,7 @@ def __init__(
self.__vehicle_id_vin_map = {}
self.__websocket_listeners = []
self.__last_parked_timestamp = {}
self.__update_state = {}

async def connect(self, test_login=False) -> Tuple[Text, Text]:
"""Connect controller to Tesla."""
Expand All @@ -99,6 +105,7 @@ async def connect(self, test_login=False) -> Tuple[Text, Text]:
self._last_update_time[vin] = 0
self._last_wake_up_time[vin] = 0
self.__update[vin] = True
self.__update_state[vin] = "normal"
self.raw_online_state[vin] = car["state"]
self.car_online[vin] = car["state"] == "online"
self.__last_parked_timestamp[vin] = self._last_attempted_update_time
Expand Down Expand Up @@ -463,7 +470,7 @@ async def _wake_up(self, car_id):
return self.car_online[car_vin]

async def update(self, car_id=None, wake_if_asleep=False, force=False):
# pylint: disable=too-many-locals
# pylint: disable=too-many-locals,too-many-statements
"""Update all vehicle attributes in the cache.
This command will connect to the Tesla API and first update the list of
Expand All @@ -488,21 +495,58 @@ async def update(self, car_id=None, wake_if_asleep=False, force=False):
"""

def _calculate_next_interval(vin: int) -> int:
cur_time = time.time()
# _LOGGER.debug(
# "%s: %s > %s; shift_state: %s sentry: %s climate: %s, charging: %s ",
# vin[-5:],
# cur_time - self.__last_parked_timestamp[vin],
# IDLE_INTERVAL,
# self.__driving[vin].get("shift_state"),
# self.__state[vin].get("sentry_mode"),
# self.__climate[vin].get("is_climate_on"),
# self.__charging[vin].get("charging_state") == "Charging",
# )
if self.raw_online_state[vin] == "asleep" or self.__driving[vin].get(
"shift_state"
):
self.__last_parked_timestamp[vin] = cur_time
elif (
cur_time - (self.__last_parked_timestamp[vin])
) > IDLE_INTERVAL and not self.__state[vin].get("sentry_mode"):
_LOGGER.debug(
"%s trying to sleep; will ignore updates for %s seconds",
"%s resetting last_parked_timestamp: shift_state %s",
vin[-5:],
round(
SLEEP_INTERVAL + self._last_update_time[vin] - time.time(), 2
),
self.__driving[vin].get("shift_state"),
)
self.__last_parked_timestamp[vin] = cur_time
if self.__driving[vin].get("shift_state") in ["D", "R"]:
if self.__update_state[vin] != "driving":
self.__update_state[vin] = "driving"
_LOGGER.debug(
"%s driving; increasing scan rate to every %s seconds",
vin[-5:],
DRIVING_INTERVAL,
)
return DRIVING_INTERVAL
if (
cur_time - self.__last_parked_timestamp[vin] > IDLE_INTERVAL
) and not (
self.__state[vin].get("sentry_mode")
or self.__climate[vin].get("is_climate_on")
or self.__charging[vin].get("charging_state") == "Charging"
):
if self.__update_state[vin] != "trying_to_sleep":
self.__update_state[vin] = "trying_to_sleep"
_LOGGER.debug(
"%s trying to sleep; scan throttled to %s seconds and will ignore updates for %s seconds",
vin[-5:],
SLEEP_INTERVAL,
round(SLEEP_INTERVAL + self._last_update_time[vin] - cur_time, 2),
)
return SLEEP_INTERVAL
if self.__update_state[vin] != "normal":
self.__update_state[vin] = "normal"
_LOGGER.debug(
"%s scanning every %s seconds",
vin[-5:],
self.update_interval,
)
return self.update_interval

cur_time = time.time()
Expand Down

0 comments on commit 5f1e34d

Please sign in to comment.