Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 47 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,53 @@

## [Unreleased]

### home_assistant_vehicle 0.1.0

A new read-only driver for a car whose level Home Assistant already reads. A
Home Assistant automation publishes one JSON message over MQTT; the driver
subscribes, emits every 5 seconds and holds no Home Assistant token. It
reads the level, charge limit and charging state, and, when the automation
maps them, the charge cable (`plugged`) and the car's place (`at_site` from
a tracker in zone home). The automation may add `plugged_since` from
`last_changed`, but only when the integration reads the cable at least
every 30 seconds: `last_changed` is when Home Assistant read the change.
The header carries the automation for the Tesla Custom Integration.
Messages from a Model Y on that integration, recorded on 15 October 2026,
are the test fixtures.

### tesla_cloud 0.2.0

Report the charge cable (`plugged`, from `conn_charge_cable`, else the
charging state). No cable time: the driver reads the car minutes apart. With
a site position from FTW and the optional `vehicle_location` scope, the same
`vehicle_data` read asks for `location_data`, and the driver emits the car's
distance from the site (`site_distance_m`), never its coordinates. A token
without the scope gets HTTP 403 for that read; the driver then reads
`charge_state` alone and asks again a day later. No request is added and no
car is woken. A level of 1 % goes as 0.01.

### teslamate_vehicle 0.2.0

Report the charge cable from TeslaMate's `plugged_in`. A change is dated
(`plugged_since_ms`, by the box's clock) only when a live update carries it:
a `healthy` message within 10 seconds. A retained value, at subscribe or
redelivered after the broker reconnects, has no known time. With `geofence`
set to this site's TeslaMate geofence, the geofence topic gives `at_site`;
otherwise `latitude` and `longitude` give the distance from the site. The
coordinates are not emitted. A level of 1 % goes as 0.01.

### vag_vehicle 0.3.0

Report the charge cable from the Data Act dataset's plug state. No cable
time: the portal writes every 15 minutes. A plug state other than connected
or disconnected is unknown, not unplugged. The datasets carry no position.
A level of 1 % goes as 0.01.

### tesla_vehicle 0.2.6

A level of 1 % goes as 0.01. FTW reads a vehicle `soc` of 1 as 100 %, so a
car at 1 % looked full.

### pixii_pv 0.3.3

Report zero PV generation when the measured phase sum is negative. Negating
Expand Down
18 changes: 10 additions & 8 deletions SUPPORT_STATUS.md
Original file line number Diff line number Diff line change
Expand Up @@ -80,6 +80,8 @@ Catalog source is not proof that a target can install or run a driver.
| heishamon | 0.8.0 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| hello | 1.1.2 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| hello | 1.1.2 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| home_assistant_vehicle | 0.1.0 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| home_assistant_vehicle | 0.1.0 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| huawei | 2.1.3 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| huawei | 2.1.3 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| janitza | 1.0.5 | ftw-core | not_assessed | — | not_recorded | not_assessed |
Expand Down Expand Up @@ -158,18 +160,18 @@ Catalog source is not proof that a target can install or run a driver.
| sonnen | 2.0.3 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| sungrow | 1.6.0 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| sungrow | 1.6.0 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| tesla_cloud | 0.1.1 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| tesla_cloud | 0.1.1 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| tesla_vehicle | 0.2.5 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| tesla_vehicle | 0.2.5 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| tesla_cloud | 0.2.0 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| tesla_cloud | 0.2.0 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| tesla_vehicle | 0.2.6 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| tesla_vehicle | 0.2.6 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| tesla_wall_connector | 0.1.1 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| tesla_wall_connector | 0.1.1 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| teslamate_vehicle | 0.1.1 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| teslamate_vehicle | 0.1.1 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| teslamate_vehicle | 0.2.0 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| teslamate_vehicle | 0.2.0 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| tibber | 1.1.2 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| tibber | 1.1.2 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| vag_vehicle | 0.2.1 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| vag_vehicle | 0.2.1 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| vag_vehicle | 0.3.0 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| vag_vehicle | 0.3.0 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| varta | 1.1.1 | ftw-core | not_assessed | — | not_recorded | not_assessed |
| varta | 1.1.1 | blixt-l1 | not_assessed | — | not_recorded | not_assessed |
| victron | 2.1.2 | ftw-core | not_assessed | — | not_recorded | not_assessed |
Expand Down
25 changes: 19 additions & 6 deletions devices.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -606,6 +606,19 @@ manufacturers:
control: false
firmware_versions: ""
notes: "Community driver, untested"
- name: "Home Assistant"
model_families:
- name: "Vehicle (Home Assistant MQTT)"
variants: [Model Y]
regions: []
protocols:
- protocol: mqtt
driver: "home_assistant_vehicle"
version: "0.1.0"
ders: [vehicle]
control: false
firmware_versions: ""
notes: "Read-only vehicle level, charge limit, charging state, charge cable and place from a JSON message a Home Assistant automation publishes. Tested with recorded messages from a Model Y on the Tesla Custom Integration; the cable and place fields have not run on a car. Does not wake or command the car."
- name: "Hoymiles"
model_families:
- name: "HM Series"
Expand Down Expand Up @@ -1806,7 +1819,7 @@ manufacturers:
protocols:
- protocol: http
driver: "tesla_vehicle"
version: "0.2.5"
version: "0.2.6"
ders: [vehicle]
control: true
firmware_versions: ""
Expand All @@ -1817,22 +1830,22 @@ manufacturers:
protocols:
- protocol: http
driver: "tesla_cloud"
version: "0.1.1"
version: "0.2.0"
ders: [vehicle]
control: false
firmware_versions: ""
notes: "Read-only vehicle SoC, charge limit and charging state via the official Tesla Fleet API. Optional next to tesla_vehicle (BLE proxy). Does not wake or command the car. Not yet run against a car."
notes: "Read-only vehicle SoC, charge limit, charging state and charge cable via the official Tesla Fleet API. Grant the optional vehicle_location scope to report the car's distance from the site; the coordinates stay in the driver. Optional next to tesla_vehicle (BLE proxy). Does not wake or command the car. Not yet run against a car."
- name: "Tesla Vehicle (TeslaMate)"
variants: [Model 3, Model Y]
regions: []
protocols:
- protocol: mqtt
driver: "teslamate_vehicle"
version: "0.1.1"
version: "0.2.0"
ders: [vehicle]
control: false
firmware_versions: ""
notes: "Read-only vehicle SoC, charge limit and charging state via TeslaMate MQTT. Optional next to tesla_vehicle (BLE proxy). Does not wake or command the car. Not yet run against a car."
notes: "Read-only vehicle SoC, charge limit, charging state, charge cable and place via TeslaMate MQTT. Set geofence to this site's TeslaMate geofence for the place. Optional next to tesla_vehicle (BLE proxy). Does not wake or command the car. Not yet run against a car."
- name: "Tesla Wall Connector"
variants: [Wall Connector Gen 3]
regions: []
Expand Down Expand Up @@ -2064,7 +2077,7 @@ manufacturers:
protocols:
- protocol: http
driver: "vag_vehicle"
version: "0.2.1"
version: "0.3.0"
ders: [vehicle]
control: false
firmware_versions: ""
Expand Down
26 changes: 26 additions & 0 deletions docs/WRITING-A-DRIVER.md
Original file line number Diff line number Diff line change
Expand Up @@ -346,6 +346,32 @@ make check
`make check` regenerates `index.yaml`, `devices.yaml`, `support-status.json`
and the manifest hashes. Commit what it produces — it fails if those are stale.

## A car says where it is plugged in

A vehicle driver can help FTW tell which car is on a charger. Emit
`plugged`, and when the source knows them, `plugged_since_ms` and `at_site`
or `site_distance_m`. The fields are in
[`spec/host-api.md`](../spec/host-api.md#vehicle-ftw).

- **Date only what you saw happen.** Send `plugged_since_ms` only when the
source reads the cable at least every 30 seconds. A car read every few
minutes shows a plug-in minutes late, and FTW would match it to the wrong
charger or to none. A value the driver saw at its first reading, or one a
broker redelivers after a reconnect, has no known time: leave it out.
- **Prefer the source's own idea of home.** A Home Assistant zone or a
TeslaMate geofence gives `at_site`. Measuring against
`host.site_location()` is the fallback: that position is a weather pin.
- **Keep the coordinates in the driver.** Emit only `site_distance_m`,
rounded to the metre.
- **Unknown is not false.** A cable state or a place the source does not
know is `nil`. A wrong `false` tells FTW the car is somewhere else.
- **No extra reads.** The cable and the place come with the reads the level
already needs. Never wake a car, or add a billed request, to learn them.
- **A level of 1 % goes as 0.01.** FTW reads a vehicle `soc` of 1 as 100 %.

`home_assistant_vehicle`, `tesla_cloud`, `teslamate_vehicle` and
`vag_vehicle` show the patterns.

## Testing

The harness is at `drivers/tests/lua_harness/`. `host_mock.lua` lets you set
Expand Down
Loading
Loading