replica-omnisciente/firmware/telemetry/WIRE_FORMAT.md
Raphael Cautus (Maestro) 39fb44fe0e feat(infra): proxmox IaC, firmware, savearth realm, lab-gateway ESP, CI
- infrastructure/proxmox/: CT provisioning configs
- infrastructure/fabric/gitops/: GitOps layer
- fleet.yaml: GPU inventory (Dell GTX 1050 vfio-pci passthrough)
- firmware/: ESP32 firmware tree (67 files, 6.9MB)
- realms/savearth/: Savearth team realm with heteronyms
- lab-gateway: ESP client + manager
- CI: Forgejo + GitHub Actions workflows

Co-authored-by: Álvaro de Campos <campos@portugalfuturista.org>
2026-07-31 14:57:41 +01:00

4 KiB

Réplica Omnisciente — Bare-Metal Telemetry Wire Format

Version: 1.0 Schema version: 1 (matches scripts/data_sharing/ Python collector)

Purpose

Bare-metal agents (ESP32, STM32, RP2040, RISC-V SoCs, etc.) emit telemetry to the Portugal Futurista ingest endpoint using this JSON wire format. It matches exactly what the Python data_sharing/collector.py produces, so the server-side ingest is identical regardless of source.

Endpoint

POST <endpoint>/api/ingest
Content-Type: application/json
X-Aurelio-Source: <device_id>
X-Aurelio-Transport: bare-metal
Authorization: Bearer <token>     (optional)

JSON Envelope

All bare-metal payloads use this envelope:

{
  "schema_version": 1,
  "collected_at": "2026-07-30T16:00:00Z",
  "device_id": "esp32-shower-001",
  "platform": "esp32",
  "consent": {
    "categories": ["tool_calls", "environment", "session_meta"],
    "retention_days": 90,
    "redact_secrets": true
  },
  "environment": { ... },
  "session_meta": [ ... ],
  "tool_calls": [ ... ],
  "agent_metadata": { ... },
  "error_traces": [ ... ],
  "_summary": { ... }
}

Field Reference

Top-level

Field Type Required Description
schema_version int yes Always 1
collected_at string yes ISO-8601 UTC timestamp
device_id string yes Unique device identifier (MAC, serial, etc.)
platform string yes Platform string: esp32, stm32, rp2040, riscv, etc.
consent object yes Consent declaration
environment object if consented Device telemetry
session_meta array if consented Session metadata
tool_calls array if consented Tool/action records
agent_metadata object if consented Agent model/heteronym info
error_traces array if consented Error/crash traces
_summary object yes Per-category item counts
{
  "categories": ["tool_calls", "environment"],
  "retention_days": 90,
  "redact_secrets": true
}

Categories are the same 8 from the Python consent model: tool_calls, thinking, chat_messages, session_meta, agent_metadata, error_traces, file_changes, environment.

environment

{
  "os": "FreeRTOS",
  "os_version": "V11.1.0",
  "firmware_version": "v2.8.0",
  "chip": "ESP32-S3",
  "cpu_mhz": 240,
  "flash_kb": 8192,
  "ram_kb": 512,
  "heap_free_bytes": 234560,
  "uptime_seconds": 3600,
  "wifi_rssi": -55,
  "battery_mv": 3700,
  "collected_at": "2026-07-30T16:00:00Z"
}

session_meta

[
  {
    "session_id": "esp32-shower-001-1234567890",
    "source": "bare-metal",
    "started_at": "2026-07-30T15:00:00Z",
    "message_count": 42
  }
]

tool_calls

On bare-metal, "tool calls" are sensor reads, actuator writes, or firmware actions:

[
  {
    "session_id": "esp32-shower-001-1234567890",
    "tool_name": "read_sensor",
    "arguments": "{\"sensor\":\"flow_rate\",\"channel\":0}",
    "result": "{\"value\":4.2,\"unit\":\"L/min\"}",
    "timestamp": "2026-07-30T16:00:01Z"
  }
]

agent_metadata

{
  "total_sessions": 1,
  "models_used": {"edge-tflite": 1},
  "heteronyms_used": {"device-agent": 1}
}

error_traces

[
  {
    "session_id": "esp32-shower-001-1234567890",
    "log_file": "crash",
    "content": "Guru Meditation Error: Core 0 panic'ed (LoadProhibited). ..."
  }
]

Memory Budget

Targets for 32-bit CPUs with MMU/MPU:

Resource Budget
Payload buffer (static, MPU-aligned) 4 KiB max
Stack for telemetry task 2 KiB
Heap allocations Zero (all static)
JSON serialization Stack/comptime only

Transport

HTTP POST over WiFi (ESP32) or Ethernet (STM32). For devices without IP: buffer to flash/spiffs and flush when connectivity is available.

Secret Redaction

If redact_secrets is true, the device must strip known secret patterns from tool_calls.arguments and error_traces.content before serialization. On bare-metal this is typically a simple substring mask (no regex).