From b4e7c582a6c01a3c1fd3dfbb0088f100a6408c27 Mon Sep 17 00:00:00 2001 From: Magnus Hedemark Date: Sun, 9 Aug 2026 13:39:39 -0400 Subject: [PATCH] docs(meshcore-packet-capture): refresh skill for upstream v2.2.0 Bring SKILL.md and references up to date with agessaman/meshcore-packet-capture v2.2.0 (26 commits past the v2.0.0 source index): - CLI boundary: document --neighbors-now / --neighbors-exit - Config: payload decoding (decode_payloads, include_decoded, hashtag channels, channel keys), neighbors publishing (interval, discover window, scope timeouts, max), log rotation, ble_pin, per-broker owner/email - MQTT: neighbors and decoded topics, per-broker include_decoded/neighbors - Deployment: --user-service install/uninstall flow, meshcore ==2.3.8 pin - Source index: refresh commit/version, cover payload_decode.py and neighbors.py Closes #304 Co-authored-by: Magnus Hedemark --- meshcore-packet-capture/SKILL.md | 17 +++++-- .../references/configuration.md | 50 ++++++++++++++++--- .../deployment-and-troubleshooting.md | 26 ++++++++-- .../references/source-index.md | 22 ++++---- 4 files changed, 92 insertions(+), 23 deletions(-) diff --git a/meshcore-packet-capture/SKILL.md b/meshcore-packet-capture/SKILL.md index 323c6bc..5d78af9 100644 --- a/meshcore-packet-capture/SKILL.md +++ b/meshcore-packet-capture/SKILL.md @@ -25,7 +25,7 @@ This project captures from MeshCore **Companion radios only**. Do not route repe meshcore-packet-capture --debug ``` For a checkout, use `python3 -m meshcore_packet_capture` or `python3 packet_capture.py`. - **Verified CLI boundary:** the current parser exposes `--output`, `--verbose`, `--debug`, `--no-mqtt`, and repeatable `--config`. It does not expose `--show-config` or a dry-run flag. Run the exact installed binary with `--help` before documenting or using any other flag; do not invent a configuration-preview command. + **Verified CLI boundary (v2.2.0):** the parser exposes `--output`, `--verbose`, `--debug`, `--no-mqtt`, repeatable `--config`, and the neighbors on-demand pair `--neighbors-now` / `--neighbors-exit` (run one zero-hop neighbor discovery + scopes cycle immediately; with `--neighbors-exit`, quit when the cycle finishes). It does not expose `--show-config` or a dry-run flag. Run the exact installed binary with `--help` before documenting or using any other flag; do not invent a configuration-preview command. 3. Configure one IATA code and at least one MQTT broker before expecting network uploads. `LOC` is a placeholder, not a useful deployment identity. 4. Start with `--no-mqtt` when isolating radio connectivity. Add MQTT only after the device captures packets locally. 5. Verify the actual boundary after every change: device connection logs, packet output, broker connection, and service/container status. Do not treat a successful install as proof of a working capture. @@ -50,6 +50,7 @@ iata = "SEA" [capture] connection_type = "serial" +# ble_pin = "123456" # optional six-digit PIN for BLE connections [serial] ports = ["/dev/ttyUSB0"] @@ -60,6 +61,8 @@ enabled = true server = "mqtt.example.com" port = 1883 transport = "tcp" +# include_decoded = true # publish the nested "decoded" object to this broker +# neighbors = true # publish the neighbors snapshot to this broker [broker.auth] method = "password" @@ -69,6 +72,12 @@ password = "secret" Read `references/configuration.md` for the complete option map, broker authentication, topic templates, packet filters, and precedence edge cases. +### Optional feature blocks (v2.1.0+) + +- **Payload decoding** (`decode_payloads`, `include_decoded`, `decode_hashtag_channels`, `decode_channel_keys`, `decode_include_public`): adds a nested `decoded` object with plain-text / structured fields. GRP_TXT channel messages are decrypted (sender, text), ADVERTs are parsed (name, role, lat/lon), and human-readable type/route labels plus path are included. Raw fields are unchanged. Direct messages (TXT_MSG) cannot be decrypted by a passive observer. Off by default; opt in per broker with `include_decoded = true` in its `[[broker]]` block. +- **Neighbors publishing** (`neighbors` per broker plus `neighbors_interval_hours`, `neighbors_discover_window`, `neighbors_command_timeout`, `neighbors_scope_timeout`, `neighbors_scope_min_timeout`, `neighbors_scope_gap`, `neighbors_cycle_timeout`, `neighbors_max`, `neighbors_self_scopes`): publishes a periodic zero-hop neighbor table plus each neighbor's region scopes to the `neighbors` topic. Off by default; the cycle only runs when at least one enabled broker sets `neighbors = true`. Requires an IATA (or an explicit `[broker.topics] neighbors`). The interval is clamped to 12–336 hours to match the observer firmware. `--neighbors-now` / `--neighbors-exit` trigger a cycle on demand. +- **Log rotation** (`log_rotation` = off|size|time, `log_max_bytes`, `log_rotation_when`, `log_backup_count`): only applies when an output file is given with `--output`. + ## MQTT and authentication - Brokers are sequential and have no fixed upper limit. A missing `MQTT_ENABLED` terminates discovery, so do not leave a numbering gap. @@ -76,7 +85,8 @@ Read `references/configuration.md` for the complete option map, broker authentic - Password auth uses `username` and `password`. - Token auth uses Ed25519 JWT-style tokens. On-device signing is preferred when a connected radio supports it; Python signing is the fallback when a valid 64-byte private key is available. - Never put private keys in a public skill, command transcript, committed `.env`, or shared Docker Compose file. Prefer a protected key file or secret injection. -- Topic placeholders are `{IATA}`, `{IATA_lower}`, `{PUBLIC_KEY}`, and `{TOKEN}`. Per-broker topics override global topics. `RAW` is not published unless explicitly configured. +- Topic placeholders are `{IATA}`, `{IATA_lower}`, `{PUBLIC_KEY}`, and `{TOKEN}`. Per-broker topics override global topics. `RAW` is not published unless explicitly configured. Topics per broker: `status`, `packets`, `decoded`, `debug`, `raw`, `neighbors`. The `decoded` topic carries the nested decoded object when `include_decoded` is enabled; the `neighbors` topic carries the periodic neighbor snapshot when `neighbors` is enabled. +- Per-broker `owner` and `email` override the global `capture.owner_public_key` / `capture.owner_email` for token-auth brokers. - LetsMesh Analyzer brokers require a configured IATA. Do not silently accept the default `LOC` for a LetsMesh deployment. ## Deployment defaults @@ -85,6 +95,7 @@ Legacy hybrid installs are possible: a systemd or launchd unit may wrap a checko - **Manual/PyPI:** `pipx install meshcore-packet-capture` gives the CLI and does not install a background service. - **Managed Linux/macOS:** the root bootstrap installer creates `/opt/meshcore-packet-capture`, `/etc/meshcore-packet-capture`, a virtual environment, and a system service. It installs the latest published release by default; use `--tag` or `--branch` to pin. +- **User service (v2.1.0+):** for a local checkout on Linux, `./install.sh --user-service` creates a per-user systemd service that runs from the checkout's `.venv` (pass `--repo-dir PATH` if the checkout is not the script's directory). Config files live in the repo itself (`.env`, `.env.local`, `config.toml`, `config.d/`). Remove with `./uninstall.sh --user-service` from the same checkout; add `--remove-venv` to also delete the local `.venv`. Manage with `systemctl --user status|restart meshcore-packet-capture` and `journalctl --user -u meshcore-packet-capture -f`. - **macOS BLE:** use the per-user LaunchAgent because Bluetooth permission belongs to the login user. Serial/TCP can use a LaunchDaemon. - **Docker:** use the published image or `docker compose up -d`; serial needs a device mapping, while BLE generally needs `privileged: true` and may need host networking. Linux is the most reliable container host for hardware access. - **NixOS:** use `services.meshcore-packet-capture` and rebuild with `sudo nixos-rebuild switch`. @@ -93,7 +104,7 @@ Read `references/deployment-and-troubleshooting.md` for service commands, Docker ## Output and verification -Normal mode prints minimal packet information. `--verbose` adds JSON packet data; `--debug` adds connection, retry, packet parsing, and MQTT diagnostics. `--output PATH` writes packet data to a file. Captured records include device identity, timestamp, packet type, route, payload length, raw hex, SNR, RSSI, and a hash. +Normal mode prints minimal packet information. `--verbose` adds JSON packet data; `--debug` adds connection, retry, packet parsing, and MQTT diagnostics. `--output PATH` writes packet data to a file. Captured records include device identity, timestamp, packet type, route, payload length, raw hex, SNR, RSSI, and a hash. When `decode_payloads` is enabled, records also carry a nested `decoded` object with human-readable fields (channel message sender/text, ADVERT name/role/coordinates, type/route labels). When troubleshooting, collect evidence in this order: diff --git a/meshcore-packet-capture/references/configuration.md b/meshcore-packet-capture/references/configuration.md index f5fd332..f885613 100644 --- a/meshcore-packet-capture/references/configuration.md +++ b/meshcore-packet-capture/references/configuration.md @@ -1,6 +1,6 @@ # Configuration reference -Source basis: `agessaman/meshcore-packet-capture` commit `1d69230fbd2959412f77788a430c91e1b11cd765`, release `v2.0.0`, inspected 2026-07-11. Re-check upstream before relying on version-sensitive details. +Source basis: `agessaman/meshcore-packet-capture` commit `c011f4e` (v2.2.0), inspected 2026-08-09. Re-check upstream before relying on version-sensitive details. ## TOML layout @@ -15,6 +15,7 @@ log_level = "INFO" status = "meshcore/{IATA}/{PUBLIC_KEY}/status" packets = "meshcore/{IATA}/{PUBLIC_KEY}/packets" # raw = "meshcore/{IATA}/{PUBLIC_KEY}/raw" +# neighbors = "meshcore/{IATA}/{PUBLIC_KEY}/neighbors" [capture] connection_type = "ble" # ble, serial, tcp @@ -25,6 +26,34 @@ connection_retry_delay = 5 health_check_interval = 30 advert_interval_hours = 47 # 0 disables periodic adverts +# Payload decoding (v2.1.0+): adds a nested "decoded" object with +# plain-text / structured fields. GRP_TXT channel messages are decrypted +# (sender, text), ADVERTs parsed (name, role, lat/lon), plus type/route labels. +# decode_payloads = false +# include_decoded = false # global default; opt in per broker below +# decode_hashtag_channels = ["bot", "weather"] +# decode_channel_keys = "name=hexOrBase64,other=..." +# decode_include_public = true + +# Neighbors publishing (v2.1.0+): periodic zero-hop neighbor table + each +# neighbor's region scopes. Off by default; enabled per broker with +# neighbors = true. Interval clamped to 12-336 hours. +# neighbors_interval_hours = 24 +# neighbors_discover_window = 60 +# neighbors_command_timeout = 20 +# neighbors_scope_timeout = 0 # 0 = use device's own estimate +# neighbors_scope_min_timeout = 8 +# neighbors_scope_gap = 2.0 +# neighbors_cycle_timeout = 600 +# neighbors_max = 32 +# neighbors_self_scopes = "" + +# Log rotation (v2.1.0+): only when --output is used +# log_rotation = "off" # off | size | time +# log_max_bytes = "50MB" +# log_rotation_when = "midnight" +# log_backup_count = 5 + [serial] ports = ["/dev/ttyUSB0"] baud_rate = 115200 @@ -39,6 +68,8 @@ transport = "tcp" keepalive = 60 qos = 0 retain = false +# include_decoded = true # publish the "decoded" object to this broker +# neighbors = false # publish the neighbors snapshot to this broker [broker.auth] method = "password" # password, token, or none @@ -53,7 +84,7 @@ verify = true packets = "custom/{IATA}/{PUBLIC_KEY}/packets" ``` -`[capture]` also accepts `tcp_host`, `tcp_port`, `ble_address`, `ble_device_name`, `origin`, `private_key`, `private_key_file`, retry/backoff controls, stats controls, `drain_messages`, TCP keepalive controls, `upload_packet_types`, `exit_on_reconnect_fail`, and binary-interface controls. `config.toml.example` in the upstream repository is the authoritative complete list. +`[capture]` also accepts `tcp_host`, `tcp_port`, `ble_address`, `ble_device_name`, `ble_pin` (v2.1.0+, optional six-digit PIN for BLE connections; Linux may still require BlueZ pairing during first-time setup), `origin`, `private_key`, `private_key_file`, retry/backoff controls, stats controls, `drain_messages`, TCP keepalive controls, `upload_packet_types`, `exit_on_reconnect_fail`, and binary-interface controls. `config.toml.example` in the upstream repository is the authoritative complete list. ## Precedence and merging @@ -71,16 +102,19 @@ TOML dictionaries deep-merge. Broker arrays merge by non-empty `name`; a same-na Every flat runtime setting uses the `PACKETCAPTURE_` prefix: -- Connection: `PACKETCAPTURE_CONNECTION_TYPE`, `PACKETCAPTURE_BLE_ADDRESS`, `PACKETCAPTURE_BLE_DEVICE_NAME`, `PACKETCAPTURE_SERIAL_PORTS`, `PACKETCAPTURE_TCP_HOST`, `PACKETCAPTURE_TCP_PORT`. +- Connection: `PACKETCAPTURE_CONNECTION_TYPE`, `PACKETCAPTURE_BLE_ADDRESS`, `PACKETCAPTURE_BLE_DEVICE_NAME`, `PACKETCAPTURE_BLE_PIN`, `PACKETCAPTURE_SERIAL_PORTS`, `PACKETCAPTURE_TCP_HOST`, `PACKETCAPTURE_TCP_PORT`. - Runtime: `PACKETCAPTURE_TIMEOUT`, `PACKETCAPTURE_MAX_CONNECTION_RETRIES`, `PACKETCAPTURE_CONNECTION_RETRY_DELAY`, `PACKETCAPTURE_HEALTH_CHECK_INTERVAL`, `PACKETCAPTURE_DRAIN_MESSAGES`, `PACKETCAPTURE_STATS_IN_STATUS_ENABLED`, `PACKETCAPTURE_STATS_REFRESH_INTERVAL`. -- Identity/topics: `PACKETCAPTURE_IATA`, `PACKETCAPTURE_ORIGIN`, `PACKETCAPTURE_TOPIC_STATUS`, `PACKETCAPTURE_TOPIC_PACKETS`, `PACKETCAPTURE_TOPIC_DECODED`, `PACKETCAPTURE_TOPIC_DEBUG`, `PACKETCAPTURE_TOPIC_RAW`. +- Identity/topics: `PACKETCAPTURE_IATA`, `PACKETCAPTURE_ORIGIN`, `PACKETCAPTURE_TOPIC_STATUS`, `PACKETCAPTURE_TOPIC_PACKETS`, `PACKETCAPTURE_TOPIC_DECODED`, `PACKETCAPTURE_TOPIC_DEBUG`, `PACKETCAPTURE_TOPIC_RAW`, `PACKETCAPTURE_TOPIC_NEIGHBORS`. +- Decoding (v2.1.0+): `PACKETCAPTURE_DECODE_PAYLOADS`, `PACKETCAPTURE_INCLUDE_DECODED`, `PACKETCAPTURE_DECODE_HASHTAG_CHANNELS`, `PACKETCAPTURE_DECODE_CHANNEL_KEYS`, `PACKETCAPTURE_DECODE_INCLUDE_PUBLIC`. +- Neighbors (v2.1.0+): `PACKETCAPTURE_NEIGHBORS_INTERVAL_HOURS`, `PACKETCAPTURE_NEIGHBORS_DISCOVER_WINDOW`, `PACKETCAPTURE_NEIGHBORS_COMMAND_TIMEOUT`, `PACKETCAPTURE_NEIGHBORS_SCOPE_TIMEOUT`, `PACKETCAPTURE_NEIGHBORS_SCOPE_MIN_TIMEOUT`, `PACKETCAPTURE_NEIGHBORS_SCOPE_GAP`, `PACKETCAPTURE_NEIGHBORS_CYCLE_TIMEOUT`, `PACKETCAPTURE_NEIGHBORS_MAX`, `PACKETCAPTURE_NEIGHBORS_SELF_SCOPES`. +- Log rotation (v2.1.0+): `PACKETCAPTURE_LOG_ROTATION`, `PACKETCAPTURE_LOG_MAX_BYTES`, `PACKETCAPTURE_LOG_ROTATION_WHEN`, `PACKETCAPTURE_LOG_BACKUP_COUNT`. - Keys: `PACKETCAPTURE_PRIVATE_KEY` or `PACKETCAPTURE_PRIVATE_KEY_FILE`. Use the TOML names when writing configuration. Use the environment names when injecting Docker or service settings. ## MQTT broker slots -For broker `n`, the environment form is `PACKETCAPTURE_MQTT_*`. Common fields are `ENABLED`, `NAME`, `SERVER`, `PORT`, `TRANSPORT`, `USE_TLS`, `TLS_VERIFY`, `USERNAME`, `PASSWORD`, `USE_AUTH_TOKEN`, `TOKEN_AUDIENCE`, `TOKEN_TTL`, `TOKEN_OWNER`, `TOKEN_EMAIL`, `TOPIC_TOKEN`, `CLIENT_ID_PREFIX`, `QOS`, `RETAIN`, and `KEEPALIVE`. +For broker `n`, the environment form is `PACKETCAPTURE_MQTT_*`. Common fields are `ENABLED`, `NAME`, `SERVER`, `PORT`, `TRANSPORT`, `USE_TLS`, `TLS_VERIFY`, `USERNAME`, `PASSWORD`, `USE_AUTH_TOKEN`, `TOKEN_AUDIENCE`, `TOKEN_TTL`, `TOKEN_OWNER`, `TOKEN_EMAIL`, `TOPIC_TOKEN`, `CLIENT_ID_PREFIX`, `QOS`, `RETAIN`, `KEEPALIVE`, plus v2.1.0+ `INCLUDE_DECODED` and `NEIGHBORS` per-broker feature flags. Supported topic placeholders: @@ -89,7 +123,7 @@ Supported topic placeholders: - `{PUBLIC_KEY}`: connected radio public key - `{TOKEN}`: broker-specific or global topic token -A broker-specific topic wins over the global topic. `RAW` has no implicit default and is skipped unless configured. If no topic is configured, an IATA-aware default is used when a non-`LOC` IATA exists; custom brokers without IATA use classic topics; LetsMesh brokers without IATA do not receive default topics. +A broker-specific topic wins over the global topic. `RAW` has no implicit default and is skipped unless configured. Per-broker topic keys: `status`, `packets`, `decoded`, `debug`, `raw`, `neighbors`. If no topic is configured, an IATA-aware default is used when a non-`LOC` IATA exists; custom brokers without IATA use classic topics; LetsMesh brokers without IATA do not receive default topics. ## Authentication @@ -113,10 +147,12 @@ token_ttl = 3600 # email = "owner@example.com" ``` +Per-broker `owner` and `email` (v2.1.0+) override the global `capture.owner_public_key` / `capture.owner_email` for that broker's token. + Token generation prefers on-device signing through the connected MeshCore instance. If that fails, it can use a 64-byte MeshCore private key (128 hex characters) from configuration/environment/file, subject to device and firmware support. `AUTH_TOKEN_METHOD=python` forces Python signing; `AUTH_TOKEN_METHOD=meshcore-decoder` selects the external decoder path. Never log or paste the key. ## Packet filtering and output `PACKETCAPTURE_UPLOAD_PACKET_TYPES` accepts comma-separated numeric packet types. Known values are `0` REQ, `1` RESPONSE, `2` TXT_MSG, `3` ACK, `4` ADVERT, `5` GRP_TXT, `6` GRP_DATA, `7` ANON_REQ, `8` PATH, `9` TRACE, `10` MULTIPART, `11` CONTROL, `15` RAW_CUSTOM. Empty/unset means all packet types are uploaded; filtering affects MQTT upload, not local capture. -`--output PATH` writes packet output. `--verbose` adds JSON to normal output. `--debug` enables detailed diagnostics. `--no-mqtt` disables publishing while leaving capture active. +`--output PATH` writes packet output. `--verbose` adds JSON to normal output. `--debug` enables detailed diagnostics. `--no-mqtt` disables publishing while leaving capture active. `--neighbors-now` runs one neighbors discovery + scopes cycle immediately (v2.1.0+); add `--neighbors-exit` to quit when the cycle finishes. With `decode_payloads` enabled, each record gains a nested `decoded` object (GRP_TXT sender/text, ADVERT name/role/lat/lon, type/route labels); direct TXT_MSG payloads remain opaque to a passive observer. Log rotation (`log_rotation`, `log_max_bytes`, `log_rotation_when`, `log_backup_count`) applies when `--output` names a file. diff --git a/meshcore-packet-capture/references/deployment-and-troubleshooting.md b/meshcore-packet-capture/references/deployment-and-troubleshooting.md index 327908e..2e4033c 100644 --- a/meshcore-packet-capture/references/deployment-and-troubleshooting.md +++ b/meshcore-packet-capture/references/deployment-and-troubleshooting.md @@ -1,6 +1,6 @@ # Deployment and troubleshooting -Source basis: `agessaman/meshcore-packet-capture` commit `1d69230fbd2959412f77788a430c91e1b11cd765`, release `v2.0.0`, inspected 2026-07-11. These commands are operational guidance, not proof that a target host has the required hardware or credentials. +Source basis: `agessaman/meshcore-packet-capture` commit `c011f4e` (v2.2.0), inspected 2026-08-09. These commands are operational guidance, not proof that a target host has the required hardware or credentials. ## Manual install @@ -12,7 +12,7 @@ meshcore-packet-capture --help meshcore-packet-capture --debug --no-mqtt ``` -The package requires Python 3.11+ and installs `meshcore>=2.2.31`, `paho-mqtt`, BLE, serial, telemetry, and signing dependencies. A pipx install does not create a service or write `/etc` configuration. +The package requires Python 3.11+ and installs `meshcore==2.3.8` (pinned as of v2.2.0), `paho-mqtt`, BLE, serial, telemetry, and signing dependencies. A pipx install does not create a service or write `/etc` configuration. ## Managed installer @@ -41,6 +41,25 @@ sudo journalctl -u meshcore-packet-capture -f sudo systemctl restart meshcore-packet-capture ``` +## User service (v2.1.0+) + +For a local checkout on Linux, install a per-user systemd service that runs from the checkout's `.venv`: + +```bash +./install.sh --user-service # from the checkout root +./install.sh --user-service --repo-dir /path/to/checkout +``` + +Config files live in the repo itself: `.env`, `.env.local`, `config.toml`, and `config.d/*.toml` (loaded in sorted order). Manage it with user-level systemd: + +```bash +systemctl --user status meshcore-packet-capture +systemctl --user restart meshcore-packet-capture +journalctl --user -u meshcore-packet-capture -f +``` + +Remove with `./uninstall.sh --user-service` from the same checkout; add `--remove-venv` to also delete the local `.venv`. The user-service path is distinct from the root managed install: no `/opt`, `/etc`, or root service is created. + On macOS, BLE uses a per-user LaunchAgent because Bluetooth permissions are granted to the login user. Serial/TCP can use the system LaunchDaemon: ```bash @@ -80,7 +99,7 @@ The module's documentation shows LetsMesh WebSocket/TLS examples and custom pass 1. Run `meshcore-packet-capture --debug --no-mqtt` outside the service/container. 2. Confirm `PACKETCAPTURE_CONNECTION_TYPE` is one of `ble`, `serial`, or `tcp`. -3. For BLE, check Bluetooth permission, adapter visibility, address/name, and container privileges. +3. For BLE, check Bluetooth permission, adapter visibility, address/name, `ble_pin` match, and container privileges. On Linux, BlueZ may require a first-time pairing even when a PIN is configured. 4. For serial, verify the host device exists and the service user/container sees the mapped path. 5. For TCP, verify host/port reachability and inspect SDK reconnect messages. @@ -94,6 +113,7 @@ Do not jump to MQTT diagnosis until local device connection succeeds. 4. For token auth, verify audience, token TTL, device signing capability, and private-key fallback availability. 5. Inspect resolved topic templates and IATA without exposing credentials. 6. If packet filtering is configured, confirm the numeric packet type is included. +7. If expecting a `decoded` object, verify `decode_payloads` is enabled and the target broker sets `include_decoded = true`. If expecting a neighbors snapshot, verify the broker sets `neighbors = true` and an IATA (or explicit `[broker.topics] neighbors`) exists; the cycle only runs when at least one enabled broker opts in. The process tolerates transient disconnects, retries commands, and uses MQTT grace periods. A single reconnect warning is not proof of a permanent failure; look for the later connected/failed state. diff --git a/meshcore-packet-capture/references/source-index.md b/meshcore-packet-capture/references/source-index.md index ed25900..0f60cd8 100644 --- a/meshcore-packet-capture/references/source-index.md +++ b/meshcore-packet-capture/references/source-index.md @@ -1,32 +1,34 @@ # Source index -This skill was built from the public repository [agessaman/meshcore-packet-capture](https://github.com/agessaman/meshcore-packet-capture), inspected at commit `1d69230fbd2959412f77788a430c91e1b11cd765` on 2026-07-11. The checkout reported release `v2.0.0`, published 2026-06-22. Upstream is the source of truth when this skill conflicts with a newer release. +This skill was built from the public repository [agessaman/meshcore-packet-capture](https://github.com/agessaman/meshcore-packet-capture), inspected at commit `c011f4e` on 2026-08-09. The checkout reported release `v2.2.0`, published 2026-07-30. Upstream is the source of truth when this skill conflicts with a newer release. ## Coverage inventory - [x] `README.md`: scope, install modes, configuration precedence, CLI, Docker, output, topics, troubleshooting -- [x] `pyproject.toml`, `requirements.txt`: Python/runtime dependency floor and CLI entry point +- [x] `pyproject.toml`, `requirements.txt`: Python/runtime dependency floor (meshcore pinned `==2.3.8` as of v2.2.0) and CLI entry point - [x] `src/meshcore_packet_capture/__main__.py`: installed command dispatch -- [x] `src/meshcore_packet_capture/packet_capture.py`: transports, retries, health checks, MQTT, topics, stats, filters, output, shutdown -- [x] `src/meshcore_packet_capture/config_loader.py`: TOML loading, deep merge, named broker merge, environment flattening +- [x] `src/meshcore_packet_capture/packet_capture.py`: transports, retries, health checks, MQTT, topics, stats, filters, output, shutdown, neighbors CLI flags (`--neighbors-now`, `--neighbors-exit`) +- [x] `src/meshcore_packet_capture/config_loader.py`: TOML loading, deep merge, named broker merge, environment flattening, decoding/neighbors/log-rotation keys - [x] `src/meshcore_packet_capture/auth_token.py`: device/Python/decoder signing and key format - [x] `src/meshcore_packet_capture/enums.py`: packet and route type vocabulary -- [x] `config.toml.example`, `.env`: configuration surface and legacy aliases +- [x] `src/meshcore_packet_capture/payload_decode.py`: GRP_TXT decryption, ADVERT parsing, structured decode fields (v2.1.0+) +- [x] `src/meshcore_packet_capture/neighbors.py`: zero-hop neighbor discovery + region-scope collection for the neighbors topic (v2.1.0+) +- [x] `config.toml.example`, `.env`: configuration surface and legacy aliases (decode/neighbors/log-rotation blocks, `ble_pin`, per-broker `include_decoded`/`neighbors`/`owner`/`email`) - [x] `presets/*.toml`: broker preset shape and sequential broker behavior - [x] `DOCKER.md`, `docker-compose.yml`, `Dockerfile`: container deployment and hardware access - [x] `NIXOS.md`, `nix/`: NixOS package/module deployment -- [x] `install.sh`, `installer/`: bootstrap, release resolution, interactive install, update, migrate +- [x] `install.sh`, `installer/`: bootstrap, release resolution, interactive install, update, migrate, `--user-service` flow - [x] `packaging/systemd/`, `packaging/launchd/`: service supervision and platform permissions -- [x] `uninstall.sh`: backup and destructive cleanup boundaries +- [x] `uninstall.sh`: backup, `--user-service` removal, and destructive cleanup boundaries - [x] `devtools/`: BLE/network diagnostic helpers, treated as optional development tools - [x] `tests/`: configuration, installer, CLI, packet parsing, JWT, presets, and lifecycle behavior - [x] `.github/workflows/`: Docker, Nix, pytest, and release automation ## Reconciliation notes -- The README says the recommended meshcore dependency is `>=2.2.31`; `pyproject.toml` confirms that floor. +- The README says the recommended meshcore dependency is `>=2.2.31`; `pyproject.toml` at v2.2.0 pins `==2.3.8` and the contact-injection shim was removed. The skill follows the pin. - TOML is described as primary, but the actual precedence depends on whether a value came from the real process environment or a dotenv file. The skill documents the implementation's snapshot behavior. -- The README says the installer installs the latest release by default; `installer/__main__.py` and `install.sh` confirm explicit `--tag`/`--branch` overrides. +- The README says the installer installs the latest release by default; `installer/__main__.py` and `install.sh` confirm explicit `--tag`/`--branch` overrides, plus the v2.1.0+ `--user-service` local-checkout flow. - Older README examples mention `docker-compose`; current `DOCKER.md` uses `docker compose`. Prefer the Compose v2 form. - `NIXOS.md` documents a bounded broker example; `config_loader.py` and tests show the Python runtime supports more than four enabled brokers. The skill follows the runtime for the general rule and treats Nix option count as module-specific. - Upstream contains compatibility/development helpers and a large implementation file. This skill distills operation and diagnosis rather than copying source code. @@ -34,6 +36,6 @@ This skill was built from the public repository [agessaman/meshcore-packet-captu ## Refresh procedure 1. Fetch the current default branch and latest release with `gh`. -2. Re-read `README.md`, `pyproject.toml`, `config.toml.example`, `DOCKER.md`, `NIXOS.md`, service templates, installer entry points, config loader, and CLI parser. +2. Re-read `README.md`, `pyproject.toml`, `config.toml.example`, `DOCKER.md`, `NIXOS.md`, service templates, installer entry points, config loader, CLI parser, `payload_decode.py`, and `neighbors.py`. 3. Run the upstream tests if dependencies and hardware-independent fixtures are available. 4. Update this index's commit/date and reconcile every changed command, default, version, and environment variable before changing executable guidance.