Update readme and add UDS
This commit is contained in:
@@ -1,111 +1,95 @@
|
||||
# OBD2 Client для Skoda Kodiaq 2021 на RPi5
|
||||
# OBD2 Client
|
||||
|
||||
Python приложение для чтения OBD2 данных через WaveShare 2-CH CAN HAT.
|
||||
Python приложение для мониторинга OBD2 данных Skoda Kodiaq 2021 на Raspberry Pi 5.
|
||||
|
||||
## Возможности
|
||||
|
||||
- **OBD2 Protocol** — чтение стандартных PID (Mode 01)
|
||||
- **Offline-first Storage** — SQLite с автосинхронизацией в PostgreSQL
|
||||
- **Handler Pipeline** — модульная обработка данных
|
||||
- **Flipper Zero UI** — отображение на портативном дисплее
|
||||
- **UPS Monitoring** — мониторинг X120x UPS HAT
|
||||
- **Systemd Services** — автозапуск при загрузке
|
||||
|
||||
## Установка
|
||||
|
||||
```bash
|
||||
# Основные зависимости
|
||||
pip install -r requirements.txt
|
||||
|
||||
# Для PostgreSQL (опционально)
|
||||
pip install psycopg2-binary
|
||||
|
||||
# Для UPS мониторинга (опционально, только RPi)
|
||||
pip install smbus2 gpiozero
|
||||
```
|
||||
|
||||
## Конфигурация RPi5
|
||||
|
||||
### /boot/config.txt
|
||||
```
|
||||
### /boot/firmware/config.txt
|
||||
|
||||
```ini
|
||||
# CAN HAT (MCP2515)
|
||||
dtparam=spi=on
|
||||
dtoverlay=mcp2515-can0,oscillator=16000000,interrupt=23
|
||||
dtoverlay=mcp2515-can0,oscillator=16000000,interrupt=25
|
||||
|
||||
# UART для Flipper Zero
|
||||
enable_uart=1
|
||||
dtoverlay=disable-bt
|
||||
```
|
||||
|
||||
### Инициализация CAN интерфейса
|
||||
### Инициализация CAN
|
||||
|
||||
```bash
|
||||
sudo ip link set can0 up type can bitrate 500000
|
||||
sudo ifconfig can0 txqueuelen 65536
|
||||
sudo ip link set can0 type can bitrate 500000
|
||||
sudo ip link set can0 up
|
||||
```
|
||||
|
||||
## Использование
|
||||
|
||||
### Запуск с реальным авто
|
||||
### Базовый запуск
|
||||
|
||||
```bash
|
||||
python -m src.main --interface can0
|
||||
```
|
||||
|
||||
### Только сканирование PID
|
||||
```bash
|
||||
python -m src.main --interface can0 --scan-only
|
||||
```
|
||||
|
||||
### Тестирование с виртуальным CAN
|
||||
```bash
|
||||
# Создание виртуального интерфейса
|
||||
sudo modprobe vcan
|
||||
sudo ip link add dev vcan0 type vcan
|
||||
sudo ip link set up vcan0
|
||||
|
||||
# Запуск клиента
|
||||
python -m src.main --interface vcan0 --virtual
|
||||
```
|
||||
|
||||
### Параметры командной строки
|
||||
|
||||
| Параметр | Описание |
|
||||
|----------|----------|
|
||||
| `-i, --interface` | CAN интерфейс (can0, vcan0) |
|
||||
| `-c, --config` | Путь к config.json |
|
||||
| `-v, --virtual` | Использовать виртуальный CAN |
|
||||
| `--scan-only` | Только сканировать PID |
|
||||
| `--flipper PORT` | Включить Flipper Zero сервер на указанном порту |
|
||||
| `--debug` | Включить отладочный вывод |
|
||||
|
||||
## Интеграция с Flipper Zero
|
||||
|
||||
### Подключение
|
||||
|
||||
```
|
||||
RPi5 Flipper Zero
|
||||
GPIO14 (TX) --------> RX (pin 14)
|
||||
GPIO15 (RX) <-------- TX (pin 13)
|
||||
GND ---------- GND (pin 18)
|
||||
```
|
||||
|
||||
### Запуск с Flipper
|
||||
### С Flipper Zero
|
||||
|
||||
```bash
|
||||
python -m src.main --interface can0 --flipper /dev/serial0
|
||||
```
|
||||
|
||||
### Страницы на Flipper
|
||||
### Только сканирование PID
|
||||
|
||||
| Страница | Тип | Описание |
|
||||
|----------|-----|----------|
|
||||
| Live Data | Info | RPM, Speed, Coolant, Throttle, Fuel |
|
||||
| Statistics | Info | Queries, Success rate, Uptime |
|
||||
| System Info | Info | IP, CPU temp, Memory, CAN interface |
|
||||
| Actions | Menu | Reconnect, Clear cache, Reboot, Shutdown |
|
||||
```bash
|
||||
python -m src.main --interface can0 --scan-only
|
||||
```
|
||||
|
||||
### Управление
|
||||
### Тестовый режим (виртуальный CAN)
|
||||
|
||||
- **←/→** - переключение страниц
|
||||
- **↑/↓** - выбор пункта меню / прокрутка
|
||||
- **OK** - подтверждение действия
|
||||
- **Back** - отмена / возврат
|
||||
```bash
|
||||
sudo modprobe vcan
|
||||
sudo ip link add dev vcan0 type vcan
|
||||
sudo ip link set up vcan0
|
||||
|
||||
## Поддерживаемые PID
|
||||
python -m src.main --interface vcan0 --virtual
|
||||
```
|
||||
|
||||
| PID | Параметр | Единицы |
|
||||
|-----|----------|---------|
|
||||
| 0x04 | Engine Load | % |
|
||||
| 0x05 | Coolant Temp | °C |
|
||||
| 0x0C | Engine RPM | RPM |
|
||||
| 0x0D | Vehicle Speed | km/h |
|
||||
| 0x0F | Intake Air Temp | °C |
|
||||
| 0x10 | MAF Rate | g/s |
|
||||
| 0x11 | Throttle Position | % |
|
||||
| 0x2F | Fuel Level | % |
|
||||
| 0x5C | Oil Temperature | °C |
|
||||
### Параметры CLI
|
||||
|
||||
| Параметр | Описание |
|
||||
|----------|----------|
|
||||
| `-i, --interface` | CAN интерфейс (can0, vcan0) |
|
||||
| `-c, --config` | Путь к config.json |
|
||||
| `-v, --virtual` | Виртуальный CAN режим |
|
||||
| `--scan-only` | Только сканирование PID |
|
||||
| `--flipper PORT` | Включить Flipper Zero сервер |
|
||||
| `--no-monitor` | Отключить консольный вывод |
|
||||
| `--debug` | Отладочный режим |
|
||||
|
||||
## Конфигурация
|
||||
|
||||
Файл `config.json`:
|
||||
### config.json
|
||||
|
||||
```json
|
||||
{
|
||||
@@ -117,49 +101,335 @@ python -m src.main --interface can0 --flipper /dev/serial0
|
||||
"obd2": {
|
||||
"request_id": "0x7DF",
|
||||
"response_id": "0x7E8",
|
||||
"timeout": 0.1
|
||||
"timeout": 0.2
|
||||
},
|
||||
"polling": {
|
||||
"interval_fast": 0.1,
|
||||
"interval_slow": 1.0,
|
||||
"fast_pids": ["0x0C", "0x0D", "0x11"],
|
||||
"slow_pids": ["0x05", "0x2F", "0x5C"]
|
||||
"fast_pids": ["0x0C", "0x0D", "0x11", "0x04"],
|
||||
"slow_pids": ["0x05", "0x5C", "0x0F", "0x2F"]
|
||||
},
|
||||
"storage": {
|
||||
"enabled": true,
|
||||
"db_path": null,
|
||||
"wal_mode": true,
|
||||
"retention_days": 30,
|
||||
"batch_size": 50,
|
||||
"flush_interval": 1.0
|
||||
},
|
||||
"postgresql": {
|
||||
"enabled": false,
|
||||
"host": "localhost",
|
||||
"port": 5432,
|
||||
"database": "carpibord",
|
||||
"user": "carpibord",
|
||||
"password": "",
|
||||
"sync_interval": 30.0,
|
||||
"batch_size": 500
|
||||
},
|
||||
"flipper": {
|
||||
"enabled": true,
|
||||
"port": "/dev/serial0",
|
||||
"baudrate": 115200,
|
||||
"show_ups": true
|
||||
}
|
||||
}
|
||||
```
|
||||
|
||||
## Переменные окружения
|
||||
### Переменные окружения
|
||||
|
||||
- `OBD2_CONFIG_PATH` - путь к config.json
|
||||
- `OBD2_CAN_INTERFACE` - CAN интерфейс
|
||||
- `OBD2_CAN_BITRATE` - битрейт
|
||||
- `OBD2_CAN_VIRTUAL` - использовать виртуальный CAN (true/false)
|
||||
- `OBD2_TIMEOUT` - таймаут ответа
|
||||
```bash
|
||||
# CAN
|
||||
export OBD2_CAN_INTERFACE=can0
|
||||
export OBD2_CAN_BITRATE=500000
|
||||
|
||||
## Структура проекта
|
||||
# Storage
|
||||
export OBD2_STORAGE_ENABLED=true
|
||||
export OBD2_STORAGE_PATH=/data/obd2.db
|
||||
|
||||
# PostgreSQL
|
||||
export OBD2_PG_ENABLED=true
|
||||
export OBD2_PG_HOST=postgres.example.com
|
||||
export OBD2_PG_DATABASE=carpibord
|
||||
export OBD2_PG_USER=carpibord
|
||||
export OBD2_PG_PASSWORD=secret
|
||||
|
||||
# Flipper
|
||||
export OBD2_FLIPPER_ENABLED=true
|
||||
export OBD2_FLIPPER_PORT=/dev/serial0
|
||||
```
|
||||
|
||||
## Архитектура
|
||||
|
||||
### Handler Pipeline (Offline-First)
|
||||
|
||||
```
|
||||
VehiclePoller ──► HandlerPipeline
|
||||
│
|
||||
├── StorageHandler ──► SQLite (obd2_data.db)
|
||||
│ │ │
|
||||
│ │ [unsynced data]
|
||||
│ │ │
|
||||
│ └─────── background sync ───────┐
|
||||
│ │
|
||||
└── PostgreSQLHandler ◄──────────────────┘
|
||||
│
|
||||
▼
|
||||
PostgreSQL (remote)
|
||||
```
|
||||
|
||||
**Принцип работы:**
|
||||
1. `VehiclePoller` опрашивает PID и вызывает callbacks
|
||||
2. `StorageHandler` батчит данные и пишет в SQLite
|
||||
3. `PostgreSQLHandler` в фоне синхронизирует unsynced записи в PostgreSQL
|
||||
4. При потере связи данные накапливаются локально
|
||||
5. При восстановлении — автоматическая досинхронизация
|
||||
|
||||
### Структура проекта
|
||||
|
||||
```
|
||||
obd2_client/
|
||||
├── src/
|
||||
│ ├── __init__.py
|
||||
│ ├── main.py # Точка входа, CLI
|
||||
│ ├── config.py # Конфигурация
|
||||
│ ├── logger.py # Логирование
|
||||
│ ├── can/
|
||||
│ │ ├── frame.py # CAN фрейм dataclass
|
||||
│ │ └── interface.py # Абстракция CAN шины
|
||||
│ ├── obd2/
|
||||
│ │ ├── pids.py # Определения PID
|
||||
│ │ ├── protocol.py # OBD2 запросы/ответы
|
||||
│ │ └── scanner.py # Автодетект PID
|
||||
│ ├── vehicle/
|
||||
│ │ ├── state.py # Состояние авто
|
||||
│ │ └── poller.py # Циклический опрос
|
||||
│ └── flipper/
|
||||
│ ├── protocol.py # UART протокол
|
||||
│ ├── pages.py # Генераторы страниц
|
||||
│ └── server.py # UART сервер
|
||||
│ ├── main.py # Точка входа, CLI
|
||||
│ ├── config.py # Конфигурация
|
||||
│ ├── logger.py # Логирование
|
||||
│ │
|
||||
│ ├── can/ # CAN абстракция
|
||||
│ │ ├── frame.py # CANFrame dataclass
|
||||
│ │ └── interface.py # CANInterface
|
||||
│ │
|
||||
│ ├── obd2/ # OBD2 протокол
|
||||
│ │ ├── pids.py # Определения PID, декодеры
|
||||
│ │ ├── protocol.py # Request/Response
|
||||
│ │ └── scanner.py # Автодетект PID
|
||||
│ │
|
||||
│ ├── vehicle/ # Состояние автомобиля
|
||||
│ │ ├── state.py # VehicleState (thread-safe)
|
||||
│ │ └── poller.py # VehiclePoller (fast/slow)
|
||||
│ │
|
||||
│ ├── handlers/ # Data Pipeline
|
||||
│ │ ├── base.py # BaseHandler, OBD2Reading
|
||||
│ │ ├── pipeline.py # HandlerPipeline
|
||||
│ │ ├── storage_handler.py # SQLite handler
|
||||
│ │ └── postgresql_handler.py # PostgreSQL sync
|
||||
│ │
|
||||
│ ├── storage/ # Persistence
|
||||
│ │ └── storage.py # SQLite + sessions
|
||||
│ │
|
||||
│ └── flipper/ # Flipper Zero интеграция
|
||||
│ ├── protocol.py # UART протокол
|
||||
│ ├── server.py # FlipperServer
|
||||
│ ├── pages.py # PageManager, страницы
|
||||
│ └── providers/ # Data providers
|
||||
│ ├── base.py # BaseProvider
|
||||
│ └── ups_provider.py # X120x UPS
|
||||
│
|
||||
├── config.json
|
||||
├── config.json.example
|
||||
├── requirements.txt
|
||||
└── README.md
|
||||
```
|
||||
|
||||
## Поддерживаемые PID
|
||||
|
||||
### OBD2 Standard (Mode 0x01)
|
||||
|
||||
| PID | Параметр | Единицы | Интервал |
|
||||
|-----|----------|---------|----------|
|
||||
| 0x04 | Engine Load | % | Fast |
|
||||
| 0x05 | Coolant Temp | °C | Slow |
|
||||
| 0x0C | Engine RPM | RPM | Fast |
|
||||
| 0x0D | Vehicle Speed | km/h | Fast |
|
||||
| 0x0F | Intake Air Temp | °C | Slow |
|
||||
| 0x10 | MAF Rate | g/s | Slow |
|
||||
| 0x11 | Throttle Position | % | Fast |
|
||||
| 0x2F | Fuel Level | % | Slow |
|
||||
| 0x5C | Oil Temperature | °C | Slow |
|
||||
|
||||
### UDS Extended (Mode 0x22) — MQB Platform
|
||||
|
||||
UDS (ISO 14229) позволяет читать расширенные данные напрямую из ECU.
|
||||
**Это read-only протокол, не влияющий на работу автомобиля.**
|
||||
|
||||
#### Engine ECU (0x7E0 → 0x7E8)
|
||||
|
||||
| PID | Параметр | Единицы | Min | Max |
|
||||
|-----|----------|---------|-----|-----|
|
||||
| 0x202A | Boost Pressure Actual | kPa | 0 | 400 |
|
||||
| 0x2029 | Boost Pressure Target | kPa | 0 | 400 |
|
||||
| 0xF423 | Fuel Rail Pressure | kPa | 0 | 25000 |
|
||||
| 0x10C0 | Lambda Actual | λ | 0.5 | 2.0 |
|
||||
| 0x1456 | Lambda Target | λ | 0.5 | 2.0 |
|
||||
| 0x437C | Torque Actual | Nm | 0 | 500 |
|
||||
| 0x39A2 | Wastegate Position | % | 0 | 100 |
|
||||
| 0x39A3 | Wastegate Target | % | 0 | 100 |
|
||||
| 0x2004 | Ignition Timing | ° | -10 | 50 |
|
||||
| 0x200A | Timing Correction Cyl 1 | ° | -15 | 5 |
|
||||
| 0x200B | Timing Correction Cyl 2 | ° | -15 | 5 |
|
||||
| 0x200C | Timing Correction Cyl 3 | ° | -15 | 5 |
|
||||
| 0x200D | Timing Correction Cyl 4 | ° | -15 | 5 |
|
||||
|
||||
#### Instrument Cluster (0x714 → 0x77E)
|
||||
|
||||
| PID | Параметр | Единицы | Min | Max |
|
||||
|-----|----------|---------|-----|-----|
|
||||
| 0x22D1 | RPM (from cluster) | RPM | 0 | 8000 |
|
||||
| 0x224D | Ambient Light Sensor | - | 0 | 255 |
|
||||
|
||||
#### DSG Transmission (0x7E1 → 0x7E9)
|
||||
|
||||
| PID | Параметр | Единицы | Min | Max |
|
||||
|-----|----------|---------|-----|-----|
|
||||
| 0x3816 | Current Gear | gear | -1 | 7 |
|
||||
| 0x3815 | Gear Selector (PRNDM) | mode | 0 | 5 |
|
||||
| 0x1940 | Transmission Temp | °C | -40 | 150 |
|
||||
|
||||
## UDS конфигурация
|
||||
|
||||
```json
|
||||
"uds": {
|
||||
"enabled": true,
|
||||
"interval_fast": 0.2,
|
||||
"interval_slow": 1.0,
|
||||
"fast_pids": ["0x202A", "0x437C", "0x10C0", "0x2004"],
|
||||
"slow_pids": ["0x39A2", "0x200A", "0x3816", "0x3815"]
|
||||
}
|
||||
```
|
||||
|
||||
### Flipper Zero — страница UDS Data
|
||||
|
||||
```
|
||||
┌──────────────────────┐
|
||||
│ UDS Data │
|
||||
├──────────────────────┤
|
||||
│ Boost: 185 kPa │
|
||||
│ Torque: 280 Nm │
|
||||
│ Lambda: 1.000 │
|
||||
│ Timing: 12.5 deg │
|
||||
│ Wastegate: 45% │
|
||||
│ Gear: 4 │
|
||||
└──────────────────────┘
|
||||
```
|
||||
|
||||
## Flipper Zero интеграция
|
||||
|
||||
### Подключение
|
||||
|
||||
```
|
||||
RPi5 GPIO Flipper Zero
|
||||
───────── ────────────
|
||||
GPIO14 (TX) ────── Pin 14 (RX)
|
||||
GPIO15 (RX) ────── Pin 13 (TX)
|
||||
GND ────── Pin 18 (GND)
|
||||
```
|
||||
|
||||
### Страницы
|
||||
|
||||
| # | Страница | Тип | Описание |
|
||||
|---|----------|-----|----------|
|
||||
| 0 | Live Data | Info | RPM, Speed, Temps, Throttle, Fuel |
|
||||
| 1 | Statistics | Info | Queries, Success rate, Uptime |
|
||||
| 2 | System Info | Info | IP, CPU, Memory, CAN interface |
|
||||
| 3 | App Status | Info | Pipeline, Storage, PostgreSQL sync |
|
||||
| 4 | UPS Status | Info | Battery %, Voltage, Power status |
|
||||
| 5 | Actions | Menu | Reconnect, Clear cache, Reboot, Shutdown |
|
||||
|
||||
### Управление
|
||||
|
||||
| Кнопка | Действие |
|
||||
|--------|----------|
|
||||
| ← / → | Переключение страниц |
|
||||
| ↑ / ↓ | Прокрутка / выбор пункта меню |
|
||||
| OK | Подтверждение |
|
||||
| Back | Отмена |
|
||||
|
||||
## Systemd сервисы
|
||||
|
||||
### Установка
|
||||
|
||||
```bash
|
||||
cd ../systemd
|
||||
sudo ./install.sh
|
||||
```
|
||||
|
||||
### Управление
|
||||
|
||||
```bash
|
||||
# Запуск
|
||||
sudo systemctl start carpibord
|
||||
|
||||
# Статус
|
||||
sudo systemctl status carpibord
|
||||
|
||||
# Логи
|
||||
journalctl -u carpibord -f
|
||||
|
||||
# Остановка
|
||||
sudo systemctl stop carpibord
|
||||
```
|
||||
|
||||
### Сервисы
|
||||
|
||||
| Сервис | Описание |
|
||||
|--------|----------|
|
||||
| `can0-link.service` | Поднимает CAN интерфейс на 500 kbps |
|
||||
| `carpibord.service` | Запускает OBD2 Client после CAN и сети |
|
||||
|
||||
## PostgreSQL Setup
|
||||
|
||||
### Создание базы
|
||||
|
||||
```sql
|
||||
CREATE DATABASE carpibord;
|
||||
CREATE USER carpibord WITH PASSWORD 'your-password';
|
||||
GRANT ALL PRIVILEGES ON DATABASE carpibord TO carpibord;
|
||||
```
|
||||
|
||||
### Таблицы (создаются автоматически)
|
||||
|
||||
```sql
|
||||
-- Readings
|
||||
CREATE TABLE obd2_readings (
|
||||
id SERIAL PRIMARY KEY,
|
||||
device_id TEXT DEFAULT 'rpi5',
|
||||
session_id TEXT,
|
||||
pid INTEGER NOT NULL,
|
||||
name TEXT NOT NULL,
|
||||
value REAL NOT NULL,
|
||||
unit TEXT NOT NULL,
|
||||
timestamp TIMESTAMPTZ NOT NULL
|
||||
);
|
||||
|
||||
-- Sessions
|
||||
CREATE TABLE obd2_sessions (
|
||||
id TEXT PRIMARY KEY,
|
||||
device_id TEXT DEFAULT 'rpi5',
|
||||
start_time TIMESTAMPTZ NOT NULL,
|
||||
end_time TIMESTAMPTZ,
|
||||
duration_seconds REAL,
|
||||
reading_count INTEGER,
|
||||
avg_speed REAL,
|
||||
max_speed REAL,
|
||||
avg_rpm REAL,
|
||||
max_rpm REAL
|
||||
);
|
||||
```
|
||||
|
||||
## UPS мониторинг (X120x)
|
||||
|
||||
Поддерживаются UPS HAT на базе MAX17048 fuel gauge:
|
||||
- X1201, X1202 и совместимые
|
||||
- Подключение по I2C (адрес 0x36)
|
||||
- GPIO 6 для детекции потери питания
|
||||
|
||||
### Отображаемые данные
|
||||
|
||||
- Battery % с визуализацией `[==== ]`
|
||||
- Напряжение батареи (V)
|
||||
- Статус: Charging / Full / Battery Mode
|
||||
- Input voltage (V)
|
||||
- Предупреждения при низком заряде
|
||||
|
||||
## Лицензия
|
||||
|
||||
MIT
|
||||
|
||||
Reference in New Issue
Block a user