开始之前
三件事,多数 TeslaMate 安装已经具备前两项。
- 带 MQTT broker 的 TeslaMate。Mosquitto 就在 TeslaMate 默认的 Compose 文件里。
- 与 TeslaMate 同一台机器上的 Docker,或任何能连到 broker 的主机。
- 出站网络访问。无需入站端口,你的 TeslaMate 也不必公开。
安装 Notifier
TeslaMate 无法自己联系到你的手机,iOS 通知也只能经由 Apple 送达。Notifier 就是那个监听 MQTT 并把事件转交出去的小容器。它运行在 TeslaMate 旁边,不开放任何端口。
-
在 App 里获取令牌
打开 HedgieMate,进入设置再进入推送通知并开启。App 会显示以 hm_ 开头的关联令牌,以及你当前连接的 TeslaMate 服务器 ID。两者都复制下来。
令牌把 App 和容器关联起来。请当作密码对待。
-
把容器加进 Compose 文件
打开你启动 TeslaMate 用的 docker-compose.yml,加入下面的服务。放在同一个文件里就能和 broker 共享网络,MQTT_HOST 直接写 broker 的服务名即可。
docker-compose.yml# add under services: in the docker-compose.yml you run TeslaMate from hedgiemate-notifier: image: hedgiemate/notifier:latest restart: unless-stopped depends_on: - mosquitto environment: HEDGIEMATE_USER_TOKEN: "hm_your_token_here" SERVER_ID: "your-server-uuid" MQTT_HOST: "mosquitto" MQTT_PORT: "1883" CAR_IDS: "1" LOG_LEVEL: "info" volumes: - hedgiemate-notifier-data:/data # and under the top-level volumes: key, adding it if the file has none hedgiemate-notifier-data:卷是可选的。它让车辆名称在重启后保留;不挂卷时中继也会补上名称。请用具名卷而不是绑定挂载:容器以非 root 用户运行,无法写入 Docker 以 root 身份创建的主机目录。
-
启动它
把新服务拉起来。技术栈里的其他服务不需要重启。
终端docker compose up -d hedgiemate-notifier
然后看日志。正常启动会打印 broker 连接情况和正在监听的车辆 ID。
终端docker compose logs -f hedgiemate-notifier
-
在 App 中确认
App 会在几秒内把该服务器标记为已连接。之后就能按车辆逐项开关事件。
在车辆真正发生状态变化之前不会有任何通知。插上充电线是看到第一个事件最快的方法。
不用 Compose
如果 TeslaMate 不是用 Compose 管理的,docker run 同样可行。把 MQTT_HOST 指向容器能访问到的主机。
docker run -d \ --name hedgiemate-notifier \ --restart unless-stopped \ -e HEDGIEMATE_USER_TOKEN="hm_your_token_here" \ -e SERVER_ID="your-server-uuid" \ -e MQTT_HOST="your-mqtt-host" \ -e CAR_IDS="1" \ hedgiemate/notifier:latest
多个 TeslaMate
每台服务器旁边跑一个 Notifier。同一个关联令牌在所有服务器上都有效,App 里区分它们靠的是服务器 ID。
配置
全部通过环境变量设置。三个必填,其余都有可用的默认值。
| 变量 | 默认值 | 说明 |
|---|---|---|
HEDGIEMATE_USER_TOKEN 必填 | 无 | App 提供的关联令牌,以 hm_ 开头。 |
MQTT_HOST 必填 | 无 | MQTT broker 的主机名。在 Compose 内就是服务名,通常是 mosquitto。 |
SERVER_ID 必填 | 无 | App 给出的服务器 UUID。不填容器也能启动,但 App 中按服务器和按车辆的设置会被忽略。 |
MQTT_PORT | 1883 | broker 端口。 |
MQTT_USERNAME | 无 | broker 用户名,如果你的 broker 需要认证。 |
MQTT_PASSWORD | 无 | broker 密码。 |
MQTT_CLIENT_ID | hedgiemate-notifier | 在 broker 上使用的 client ID。若已有别的客户端用同一个,请改掉。 |
MQTT_TLS | false | broker 使用 TLS 时设为 true,默认端口随之变为 8883。 |
MQTT_NAMESPACE | 无 | 若你在 TeslaMate 设置了 MQTT_NAMESPACE,这里要填相同的值。主题会变成 teslamate<namespace>/cars/#。 |
CAR_IDS | 1 | 要监听的车辆 ID,用逗号分隔,例如 1,2。每辆车有各自的状态机。 |
LOG_LEVEL | info | debug、info、warn 或 error。 |
RELAY_URL | https://push.hedgiemate.com | 中继地址。没有理由改动。 |
全部事件
每一行在 App 中都是按车辆独立的开关。实时活动的更新不属于通知,因此不在列表里。
| 通知 | 触发条件 |
|---|---|
| 行驶 | |
| 行程开始 | state → driving |
| 行程结束 | state leaves driving |
| 充电 | |
| 开始充电 | charging_state → Charging |
| 充电完成 | charging_state → Complete |
| 充电中断 | charging_state leaves Charging without Complete |
| 充电枪已插入 | plugged_in → true |
| 充电枪已拔出 | plugged_in → false |
| 电量 | |
| 电量不足 | battery_level ≤ BATTERY_LOW_THRESHOLD |
| 已达到目标电量 | battery_level ≥ BATTERY_HIGH_THRESHOLD |
| 位置 | |
| 进入地理围栏 | geofence set |
| 离开地理围栏 | geofence cleared or changed |
| 安全 | |
| 哨兵模式录制 | center_display_state = 7 |
| 车辆 | |
| 软件更新 | update_available → true |
| 正在进入休眠 | state → asleep pending |
| 已休眠 | state → asleep |
| 车辆已唤醒 | state leaves asleep |
什么都收不到
按顺序排查。多数情况都在前三条里。
App 仍显示服务器未连接
先用 docker compose ps 确认容器确实在运行,再看它的日志。最常见的原因是 MQTT_HOST 写错:在 Compose 内应当是 broker 的服务名 mosquitto,而不是 localhost。
容器在跑,但从来没有事件
CAR_IDS 必须与 TeslaMate 使用的车辆 ID 一致。TeslaMate 从 1 开始编号,多辆车时逐个列出:CAR_IDS=1,2。
MQTT 连上了,日志却很安静
如果你在 TeslaMate 里设置了 MQTT_NAMESPACE,Notifier 也要设成相同的值。否则主题名对不上,容器无从读起。
有些事件能收到,有些从来收不到
每个事件在 App 中都是按车辆的开关。在设置中打开该服务器,检查这辆车的事件列表。
电量相关通知从来不触发
BATTERY_LOW_THRESHOLD 和 BATTERY_HIGH_THRESHOLD 默认是 20 和 90。它们每次充电只触发一次,所以自开始充电起没有越过阈值的车辆不会发出通知。
过几天通知就停了
确认服务带有 restart: unless-stopped,这样它会随主机一起恢复。然后检查 iOS:专注模式或 App 的通知设置可能把它们拦下了。
实时活动不出现
需要在 iOS 设置中允许 HedgieMate 使用实时活动,并且要有正在进行的会话。灵动岛需要 iPhone 14 Pro 或更新机型。
broker 需要账号或 TLS
设置 MQTT_USERNAME 和 MQTT_PASSWORD。使用 TLS 时把 MQTT_TLS 设为 true,默认端口会变成 8883。
你需要看清它在做什么
把 LOG_LEVEL 设为 debug,复现一次,然后改回去。debug 会记录每一条 MQTT 消息以及由此做出的每个判断。
问题
为什么需要 Notifier?
TeslaMate 跑在你自己的服务器上,无法主动联系你的手机,而 iOS 通知只有 Apple 能送达。Notifier 补上的就是这一段:它监听你的 MQTT 主题,捕捉状态变化,再把事件发送出去等待送达。
我的 TeslaMate 必须能从公网访问吗?
不用。Notifier 只发起出站连接,所以通知功能不需要暴露任何服务,也不需要做端口转发。
究竟有哪些数据离开我的服务器?
事件类型、电量、充电状态,以及你使用地理围栏时的围栏名称。坐标和行驶路线留在你的 TeslaMate,服务器地址从不发送。事件数据在几小时后删除。
可以跑在 TeslaMate 之外的机器上吗?
可以,只要它能连到你的 MQTT broker。把 MQTT_HOST 指向那台主机,并确认从那里能访问 broker 端口。
支持多辆车吗?
支持。在 CAR_IDS 里列出 ID,每辆车都有独立的状态跟踪和 App 内独立的开关。
中继不可达时会怎样?
容器会按递增的间隔重试几次,然后丢弃该事件。它会继续运行,并正常处理下一次状态变化。
它会存储什么吗?
只有车辆名称缓存,而且仅在你挂载了可选卷时才会存。其余内容只在容器运行期间保存在内存中。
怎么更新?
重新拉取镜像并重建服务。发布说明在 GitHub 的 releases 页面。
怎么关掉通知?
在 App 里关闭,或者停止容器。任一方式单独生效,TeslaMate 技术栈里没有其他部分依赖它。
源代码
Notifier 是 MIT 许可的 Go 代码。可以直接读代码,遇到问题也可以提 issue。