fix: Yaris 2013 OBD compatibility hardening
- _decode_odometer: catch all exceptions and return None instead of raising. PID 0xA6 (odometer) is not guaranteed on 2013 Toyota Yaris — a garbage response or unsupported PID previously raised ValueError through python-obd's decoder, which app_obd._query() caught and treated as a lost connection, killing the entire OBD session. Now it gracefully returns None. - connect_obd: reset all sensor globals (rpm, coolant_temp, fuel_level, throttle_position, mil_on, dtc_codes, odometer, timestamps) on each new connection so the UI doesn't display stale readings from the previous ignition cycle while fresh polls are completing. - yaris-obd.service: add commented OBD_PROTOCOL=6 hint for post-confirmation pinning (eliminates 3-5s auto-probe delay after first confirmed connection). Co-authored-by: Copilot <[email protected]>
This commit is contained in:
@@ -12,6 +12,11 @@ WorkingDirectory=/home/yaris/app/yaris-obd
|
|||||||
# the log file promptly instead of sitting in Python's stdout buffer indefinitely
|
# the log file promptly instead of sitting in Python's stdout buffer indefinitely
|
||||||
# when it's redirected to a file instead of a TTY.
|
# when it's redirected to a file instead of a TTY.
|
||||||
Environment=PYTHONUNBUFFERED=1
|
Environment=PYTHONUNBUFFERED=1
|
||||||
|
# Once OBD is confirmed working on this car, pin the protocol to skip the
|
||||||
|
# 3-5s auto-detect probe on every ignition-on: e.g. OBD_PROTOCOL=6 for
|
||||||
|
# ISO 15765-4 CAN 11-bit 500kbps (correct for 2013 Toyota Yaris).
|
||||||
|
# Leave unset during initial setup so auto-detect can find the right value.
|
||||||
|
#Environment=OBD_PROTOCOL=6
|
||||||
ExecStart=/home/yaris/app/yaris-obd/venv/bin/python app.py
|
ExecStart=/home/yaris/app/yaris-obd/venv/bin/python app.py
|
||||||
Restart=on-failure
|
Restart=on-failure
|
||||||
RestartSec=5
|
RestartSec=5
|
||||||
|
|||||||
+19
-1
@@ -52,10 +52,13 @@ connection = None
|
|||||||
|
|
||||||
|
|
||||||
def _decode_odometer(messages):
|
def _decode_odometer(messages):
|
||||||
|
try:
|
||||||
data = messages[0].data[2:]
|
data = messages[0].data[2:]
|
||||||
if len(data) != 4:
|
if len(data) != 4:
|
||||||
raise ValueError(f"expected 4 odometer bytes, received {len(data)}")
|
return None
|
||||||
return int.from_bytes(bytes(data), byteorder="big") / 10
|
return int.from_bytes(bytes(data), byteorder="big") / 10
|
||||||
|
except Exception:
|
||||||
|
return None
|
||||||
|
|
||||||
|
|
||||||
ODOMETER_COMMAND = obd.OBDCommand(
|
ODOMETER_COMMAND = obd.OBDCommand(
|
||||||
@@ -225,6 +228,21 @@ def connect_obd():
|
|||||||
_emit_disconnected()
|
_emit_disconnected()
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
# Reset stale sensor values from the previous ignition cycle so the
|
||||||
|
# UI doesn't briefly display outdated readings before the first polls.
|
||||||
|
global rpm, coolant_temp, fuel_level, throttle_position, mil_on, dtc_codes, odometer
|
||||||
|
global mil_updated_at, dtc_updated_at, speed_updated_at
|
||||||
|
rpm = None
|
||||||
|
coolant_temp = None
|
||||||
|
fuel_level = None
|
||||||
|
throttle_position = None
|
||||||
|
mil_on = None
|
||||||
|
dtc_codes = []
|
||||||
|
odometer = None
|
||||||
|
mil_updated_at = None
|
||||||
|
dtc_updated_at = None
|
||||||
|
speed_updated_at = None
|
||||||
|
|
||||||
_log_connection_diagnostics(candidate)
|
_log_connection_diagnostics(candidate)
|
||||||
app_events.socketio.emit("obd_status", obd_status[1])
|
app_events.socketio.emit("obd_status", obd_status[1])
|
||||||
_start_polling_threads()
|
_start_polling_threads()
|
||||||
|
|||||||
Reference in New Issue
Block a user