> For the complete documentation index, see [llms.txt](https://adatrack.gitbook.io/docs/llms.txt). Markdown versions of documentation pages are available by appending `.md` to page URLs; this page is available as [Markdown](https://adatrack.gitbook.io/docs/changelog/2026-06.md).

# June 2026

## v1.7.0

### Device Categories (v1.7.0)

Device types in AdaTrack are now **user-managed categories** — a first-class entity with a name, curated icon, and colour that users attach to their devices. The previous hardcoded five-string `type` field (`tracker`, `sensor`, `actuator`, `gateway`, `unknown`) has been fully replaced.

* **Custom categories:** Create, rename, and delete your own categories. Each category pairs an icon (from a curated catalogue) with a hex colour, both reflected on the live map markers and device list badges.
* **Built-in system categories:** Six seeded system categories (`Unknown`, `GPS Tracker`, `Environmental Sensor`, `Actuator`, `Gateway`, `Truck / Vehicle`) are available to all users and cannot be deleted.
* **Quota-gated:** The number of custom categories a user can create is governed by their subscription tier. System categories do not count toward the quota.
* **Device form integration:** The device creation and edit forms now show a category picker with a colour-coded icon preview. Existing devices were migrated automatically — their former `type` string was matched to the closest built-in category during the migration.
* **Map and list rendering:** Live map markers and device list badges now use the category's icon and colour directly. Filtering, legend, and future cross-feature integrations (alerts, geofences, workflows, reporting) use `category_id` as a stable reference.
* **Localization:** All UI strings are available in English and Slovak.

### Teltonika Codec8 TCP Ingestion (v1.7.0)

AdaTrack now natively ingests telemetry from **Teltonika GPS trackers** (FMB920, FMT100, FMB140, and others) via the new **Codec8 plugin** — no custom firmware or third-party bridge required.

* **TCP listener on a configurable port** (default `6868`) handles the full Codec8 handshake: IMEI identification, data framing, CRC-16/IBM validation, and per-packet ACK.
* **Codec8 and Codec8E support:** Both 1-byte IO ID (Codec8) and 2-byte IO ID (Codec8E) frames are parsed natively in Go. GPS element and all IO elements are decoded per AVL record.
* **IMEI → device UUID mapping:** Users enter their Teltonika device's IMEI directly in the standard device creation or edit form. The plugin resolves it to an AdaTrack device UUID automatically via an in-process LRU cache (TTL 5 min, PostgreSQL fallback). No manual mapping step is required.
* **Decoder auto-setup:** Selecting **Codec8 TCP** as the transport type in the device form automatically finds or creates a passthrough decoder profile and pre-selects it — no profile management needed.
* **Ordered ingestion for offline-buffered data:** Teltonika devices buffer AVL records while offline and flush them as multiple TCP packets on reconnect. The plugin now accumulates all records for a session and sorts them by timestamp before dispatching to the pipeline, preventing out-of-order records from corrupting TripDetector FSM state. ACKs are sent per-packet so the device clears its buffer immediately; the flush happens on session end (idle timeout or disconnect). Configurable via `session_idle_timeout_sec` (default 30 s) and `max_session_records` (default 10,000).
* **Full platform pipeline:** Every AVL record triggers the complete downstream pipeline — geofencing, alert rules, workflow nodes, WebSocket broadcast — identically to a UDP or MQTT packet.
* **Plugin admin page** at `/plugins/codec8/` shows live server health (active connections, packets received, CRC errors, uptime) and a table of all IMEI mappings across users.
* **License gate:** Requires **Standard** tier or above and the `plugin:codec8` license feature. Not available on Community Edition.
* **Localization:** Admin page and device form strings available in English and Slovak.

### Observability Dashboards (v1.7.0)

Five pre-built Grafana dashboards are now provisioned automatically with the observability stack:

* **IoT Backend** — UDP packet throughput, decoder latency (p50/p95/p99), HMAC failures, DB write rates.
* **MQTT Broker** — Connected clients, messages in/out per minute, session breakdown.
* **Plugin System** — Per-plugin event counts, VM execution latency, error rates.
* **Travel Log** — Trips detected, active detectors, FSM state-transition rates, export counts, out-of-order packet drops (`codec8_session_out_of_order_dropped_total`).
* **Workflows** — Trigger counts, action execution latency, failure rates by workflow.

All dashboards are loaded automatically when the observability stack starts.

### Plugin Widget Framework (v1.7.0)

Plugins can now register **dashboard widgets** and **trip replay telemetry renderers** as first-class extension points — next step toward a fully extensible UI plugin surface.

* **Plugin dashboard widgets:** A compiled or scripted plugin can supply one or more dashboard widgets. Each widget declares a display name and a render function that receives the current device reading and returns a set of named values.
* **Trip replay telemetry renderers:** A plugin can provide a custom telemetry panel rendered alongside the trip replay timeline, updating as the user scrubs through the playback.
* **Widget primitives:** Eight visual primitives are available for widget authors: Speedometer, Odometer, Gauge, Thermometer, Voltage Meter, Signal Bars, Indicator, and Fault Badge. Scripted (JS) plugins can compose these via the plugin host API.
* **Dashboard integration:** The dashboard widget picker now lists installed plugin widgets alongside built-in widget types.
* **Developer sandbox:** A live widget sandbox page lets plugin authors preview widget rendering without setting up a full dashboard.

### Codec8 Telemetry UI Plugin (v1.7.0)

A scripted plugin ships as a seeded built-in, providing Codec8-specific dashboard widgets and a trip replay telemetry panel. It serves as the reference implementation for scripted plugin widget authorship.

* **Five dashboard widgets:** Speed (speedometer), Odometer, Satellite Count (signal bars), Battery Voltage (voltage meter), and Engine Temperature (thermometer). All widgets bind directly to decoded Codec8 IO element fields.
* **Trip replay telemetry panel:** When replaying a trip for a Codec8 device, a live telemetry panel appears alongside the timeline showing decoded IO element values (voltage, temperature, digital I/Os, event IO) at the current playback position, updating as the user scrubs.
* **Available automatically** on all deployments that have the Codec8 TCP plugin enabled.

### Alert Rules — Notification Channel Now Optional (v1.7.0)

Alert rules no longer require a notification channel. Previously, every rule had to be tied to an email, webhook, or other channel — making it impossible to use a rule purely as a workflow trigger without also sending a notification.

* **Channel is optional.** Rules can now be saved without selecting a notification channel. Existing rules are unaffected.
* **Alert events are only recorded when a geo rule matches the device.** Previously an event was recorded even when no rules matched, producing noise in the alert history.
* **Channel notifications are skipped** for rules with no channel configured. Workflow triggers and plugin event hooks still fire normally.

### Workflows — Geofence Rule Trigger Node (v1.7.0)

A new **Trigger: Geofence Rule** node is available in the Workflow Editor. When a geofence alert rule fires on a matching device, any enabled workflow containing this trigger node is executed automatically with the full alert event payload (device name, geofence name, transition direction, coordinates, severity, message). An optional filter restricts triggering to specific rules; leaving it empty matches all rules.

### Bug Fixes (v1.7.0)

#### Travel Log

* **Incorrect stop detection fixed.** The trip detector was incorrectly recording stop events in certain sequences where a brief speed dip was followed immediately by re-acceleration. The detection logic was tightened with extensive new test coverage.
* **Travel log accuracy improvements.** Several inter-related accuracy issues were addressed: distance calculations were corrected to be consistent across the pipeline; a minimum stop duration threshold (default 30 s) was introduced so brief traffic-light pauses no longer split a trip into separate legs.
* **Batch trip deletion.** Users can now select multiple trips in the Travel Log list and delete them in one action.
* **Speed chart — max speed per bucket.** The trip speed chart now plots the maximum speed recorded within each time bucket rather than the average, giving a more accurate picture of peak speed during each segment of the journey.
* **Scroll regression fixed.** A layout regression caused the page to lose scroll position when navigating between the trip list and detail views.

#### Geofencing & Alerting

* **Telemetry alert rule builder fixes.** The operator dropdown now resets correctly when the field type changes, and numeric threshold validation no longer blocks saving when the value is zero.
* **Geofencing page UI fix.** Rule-level changes (name, trigger type) are now reflected immediately after an inline edit without requiring a full page reload.
* **Dashboard live map layout fix.** Map widget sizing corrected after a layout regression introduced during the plugin widget work.

#### Map

* **GeoHeatmap — Android crash fixed.** A WebGL shader compilation error caused the geographic heatmap to crash on Android Chrome and WebView. The heatmap now detects the failure at runtime and falls back to a CPU-side rendering path, working correctly on all mobile browsers.
* **Category pin icons improved.** Device category map pins now use a sharper anchor shape with better contrast at small sizes.

***

## v1.6.2

### Chat Bot — Travel Log Integration (v1.6.2)

* **Three new Travel Log commands.** Linked users can now query their trip data directly from Telegram or Slack:
  * `/trips` — List the 10 most recent trips with device name, start time, distance, and duration.
  * `/trip <id>` — Full detail for a single trip: distance, duration, max/avg speed, stop count, start and end addresses.
  * `/tripstats` — 30-day analytics summary: total trips, total distance, total hours driven, average and peak speed. All three require the new `chatbot.travel.read` permission (granted to the `USER` role by default).
* **Trip event notifications.** The Chat Bot now forwards `trip.started` and `trip.completed` events to linked users. Completed trip notifications include the distance (km) and duration (minutes). Notifications respect quiet hours and the new **Notify Trips** preference toggle, which is opt-in (default: off) to avoid noise for high-frequency fleets.
* **`notify_trips` preference column.** A new preference has been added to each linked account's notification profile. Existing accounts default to `false`; users can toggle it from the **Chat Bot > Preferences** tab in the web UI.
* **Chat Bot plugin updated to v1.1.0.** The manifest version reflects the addition of travel log capabilities and the two new event hooks (`trip.started`, `trip.completed`).

### AI Assistant — Travel Log Tools (v1.6.2)

* **Three new LLM tools** allow the AI Assistant to answer natural-language travel questions:

  * `list_trips` — Return recent trips, optionally filtered by device.
  * `get_trip_details` — Return full statistics for a specific trip.
  * `get_trip_analytics` — Return an analytics summary (total trips, distance, hours, avg/max speed) over a user-specified time range.

  Example prompts that now work: *"How far did my fleet drive last week?"*, *"What was the longest trip yesterday?"*, *"Show me the trips for device Truck-04 this month."*

### Plugin SDK (v1.6.2)

* **`TravelLog()` accessor added to `PluginHost`.** Third-party plugins and scripted VMs can now read travel log data via `host.TravelLog()`, which returns a `TravelLogReader` interface with `ListTrips`, `GetTrip`, and `GetAnalyticsSummary` methods. Access is subject to the calling plugin's declared `travel_log:list` and `travel_log:analytics` permissions.

## v1.6.1

### Travel Log — UX Improvements (v1.6.1)

* **Trip detail is now a full page.** Clicking a trip in the Travel Log list navigates to a dedicated page (`/travel-log/<trip-id>`) with breadcrumb navigation back to the list. The previous drawer overlay has been removed.
* **Responsive detail layout.** On desktop, the map (65%) and trip timeline (35%) appear side by side and fill the viewport height, with stats cards and the speed chart below. On mobile, the layout stacks vertically: map → timeline → stats.
* **Speed-gradient segment colouring on the timeline.** Each segment between timeline events is now colour-coded to reflect the average speed of that leg, consistent with the map polyline gradient.
* **Live active-trip stats via WebSocket.** Active trips in the list now receive real-time distance, speed, and stop-count updates pushed from the server, without requiring a page refresh.
* **Per-device detector configuration.** When exactly one device is selected in the filter panel, a **Configure Detection** button appears (Standard & Enterprise tiers, requires `travel_log:configure` permission) and opens the threshold form inline on the Travel Log page.

## v1.6.0

### Features (v1.6.0)

* **Travel Log — Automatic Trip Detection:** AdaTrack now automatically detects, records, and analyses trips for every GPS-equipped device. A stateful per-device detector (IDLE → MOVING → STOPPED\_WAIT state machine) runs alongside the telemetry ingestion pipeline and segments continuous location streams into discrete journeys using configurable speed, distance, and duration thresholds. No user intervention required — trips appear in the new **Travel Log** page as soon as telemetry flows in.
* **Travel Log — Trip History & Map View:** The Travel Log page (`/travel-log`) presents a split-panel layout: a sortable, filterable trip list on the left and a live map preview on the right. Selecting a trip highlights the full route as a speed-gradient polyline (green → yellow → red) with start, end, and stop markers. Active in-progress trips show live distance and duration counters via WebSocket.
* **Travel Log — Trip Detail & Playback:** Each trip has a three-tab detail view (Map, Timeline, Stats). The **Playback** mode animates the device icon along the route at configurable speed multipliers (1× – 32×) with a scrubbable timeline, real-time speed/heading readout, and decoded payload fields at the cursor position.
* **Travel Log — Export:** Trips can be exported individually or in bulk as CSV (stats + stop list), GPX 1.1 (full trace points and stop waypoints), or PDF (map image + stats table via the existing reporting engine). Bulk export supports up to 1,000 trips per request.
* **Travel Log — Manual Editing:** Users can split a trip at any point on the timeline, merge two consecutive same-device trips (within a 60-minute gap), or soft-delete trips. Admins can hard-delete.
* **Travel Log — Dashboard Widgets:** Six new dashboard widgets — Trips Today, Distance Today, Idle Time Today, Last Trip Summary, Device Trip History (sparkline), and Active Trips — are available in the Dashboard builder.
* **Travel Log — Workflow Triggers:** Two new AdaTrack Flow trigger nodes — **Trip Started** and **Trip Completed** — expose full trip metadata (device name, coordinates, distance, duration, stop count, speed) to any downstream workflow action.
* **Travel Log — Report Blocks:** Two new blocks in the Report Designer: **Trip Summary Table** (configurable columns, grouping by device or day) and **Trip Map** (static map of all trip traces, coloured by device or speed gradient).
* **Travel Log — RBAC & Quotas:** Seven granular permission slugs (`travel_log:list`, `travel_log:get`, `travel_log:export`, `travel_log:delete`, `travel_log:edit`, `travel_log:configure`, `travel_log:analytics`) with role-based defaults. Tier-based limits apply to trace point resolution (Community: 500 pts, Standard: 5,000 pts, Enterprise: unlimited) and trip history retention (30 days / 1 year / unlimited). Usage is tracked in the quota panel as `travel_log_trips_stored`. The entire module is gated by the `enable_travel_log` feature flag (default: enabled).
* **Travel Log — Per-Device Detector Configuration (Standard & Enterprise):** Detection thresholds (min start speed, min start duration, min start distance, stop confirm duration) can be tuned per device from the device settings page, enabling support for slow-moving assets such as forklifts or golf carts.

## v1.5.4

### Features & Enhancements (v1.5.4)

* **Chat Bot — `/alerts` command:** The `/alerts [--severity critical|warning|info]` command is now fully implemented. Linked users can list their 10 most recent alert events directly from Telegram or Slack, with severity emoji indicators (🔴 critical / 🟡 warning / 🔵 info) and human-readable relative timestamps. The optional `--severity` flag filters results to a single severity level. Requires the `chatbot.alerts.read` permission.

### Bug Fixes (v1.5.4)

* **AI Assistant — Concurrent token quota bypass (security):** Simultaneous AI requests could collectively exceed the configured daily token budget. Each request read the same "0 tokens used" snapshot before any writes occurred, allowing 5 concurrent requests with a 25,000-token limit to collectively consume up to 5× the budget. Fixed by introducing a `BeginRequest` method that atomically reserves `ai_max_tokens` in an in-flight map under a mutex before the LLM call begins. Subsequent concurrent requests see the combined committed + in-flight total and are rejected if the budget would be exceeded. The reservation is released on all exit paths via `defer`. See `docs/bugs/bug-12-ai-assistant-token-quota-bypass.md` for full analysis.
* **AI Assistant — Chatbot path skipped daily/monthly quota:** Telegram and Slack messages routed to the AI assistant (`onChatbotAIRequest`) only checked the per-minute RPM limit — the daily and monthly token budgets were never consulted, making the chatbot path completely unbounded regardless of configured limits. Fixed by adding a `BeginRequest` call to the chatbot handler, giving it the same quota enforcement as the HTTP chat endpoint.
* **Dashboard — Live map layout:** The live map widget in the device dashboard view is no longer misaligned. The `DeviceDashboardView` and `DashboardLayout` components were updated to correctly size and position the map panel within the dashboard grid.
* **Charts — Rendering fixes:** Multiple fixes to `TimeSeriesChart` and `ChartWidget` following the migration to Chart.js. Chart data, axis configuration, and report PDF rendering now behave correctly across all consumers (statistics page, dashboard widgets, report designer).
* **Chat Bot — Device and telemetry command edge cases:** Several edge cases in the `/device` and `/telemetry` commands were resolved, including handling of devices with no recent readings and formatting of numeric payload fields.

### Infrastructure (v1.5.4)

* **Go 1.26.4:** Backend binaries rebuilt on Go 1.26.4 (security release). All plugin modules (`chatbot`, `mqtt`, `ai_assistant`) and tools (`adatrack-ctl`, `license-gen`) updated to match. CI and deployment workflows updated accordingly.
* **Charts — Migrated to Chart.js:** `TimeSeriesChart` and the dashboard trend chart widget migrated from Recharts to Chart.js 4. Chart.js provides more consistent rendering across browsers and better support for the animation and axis customisation needed by the statistics and dashboard pages.
