---
name: peat-btle
description: Per-repo skill for the Peat BLE mesh transport — multi-platform Rust crate (Linux/macOS/iOS/Android/ESP32) plus an Android AAR via UniFFI.
when_to_use: Editing files under peat-btle/, reviewing peat-btle PRs, debugging BLE advertise/scan/GATT/peripheral issues, working on M5Stack/ESP32 firmware integration, or working on ADR slices that touch the BLE transport.
verifies_with: cargo fmt --check, cargo clippy -- -D warnings, cargo test (host platform), plus per-platform feature builds for any flag whose paths the change touches.
---
# `peat-btle` SKILL
`peat-btle` is the Bluetooth Low Energy transport for the Peat Protocol. It implements a `Transport`-shaped surface plus the wire codec primitives (typed BLE structs, `*_to_*` JSON projections, 0xB6 framing) that other peat-* code can plug into for BLE-based peer connectivity. peat-btle has **zero peat-mesh dep** as of 0.4.0 (ADR-059 Amendment 4 Slice 4.b deleted the back-edge); peat-mesh's `bluetooth` feature wraps these primitives with its own `Translator` trait impl in peat-mesh's tree. The crate is multi-platform: Linux uses `bluer` (BlueZ), macOS/iOS use `objc2-core-bluetooth`, Android uses UniFFI bindings consumed by the ATAK plugin, ESP32 uses NimBLE. The `translator-codec` feature is what consumers (peat-mesh-using hosts and standalone embedded callers like M5Stack Core2 / Bitchat-style sensors) enable to get the wire codec.
## When this skill applies
- Editing any file under `src/` (transport, peer, platform, codec)
- Editing `android/` (Gradle/Kotlin AAR build)
- Editing `uniffi-bindgen/` or anything that affects generated bindings
- Touching the feature-flag matrix in `Cargo.toml`
- Working on M5Stack / ESP32 firmware that pins this crate
- Working on an active slice of any **local ADR** (`docs/adr/`) or any **ecosystem ADR** that lands here. Recent ecosystem slices touching this repo: `ADR-032` (pluggable transport), `ADR-039` (BLE refinements), `ADR-049` (security primitives), `ADR-059` (translator / cross-transport bridging) — these live in `peat/docs/adr/` (sibling repo). Local ADRs cover peat-btle's internal architecture (trust model, provisioning, document registry).
## Scope
**In scope:**
- BLE transport implementations and the platform adapter layer (`src/platform/`)
- Peer state, advertisement, scan, GATT
- BleTranslator wire codec (`translator-codec` feature) — the typed BLE structs, JSON projection helpers, and 0xB6 framing. peat-mesh's `Translator`-trait integration on top of these primitives lives in peat-mesh's tree (Slice 4.a), not here.
- UniFFI surface (`uniffi` feature) and the Android AAR build
- Feature-flag wiring in `Cargo.toml`
**Out of scope (route elsewhere):**
- Mesh routing / topology / discovery / sync → `peat-mesh/SKILL.md`
- ATAK plugin lifecycle / Android UI → `peat-atak-plugin/SKILL.md`
- Top-level shared types/traits — consider whether the change belongs in `peat/peat-protocol` or `peat/peat-transport` (workspace subcrates of the `peat` repo) instead
## Workflow
1. **Orient.** Read `peat/SKILL.md` (ecosystem) if accessible. Read this file. Read `CONTRIBUTING.md` for the per-platform build matrix. `git status`, `git log -10`.
2. **Locate the spec.** Confirm the task has a GitHub issue with Context / Scope / Acceptance / Constraints / Dependencies. If not, stop and ask the user.
3. **Plan.** Produce a 1–5 step plan. Cross-check against ecosystem hard invariants (transport agnosticism, FFI direction, dependency direction) and the scope guards below. If the change is architectural, reference the relevant ecosystem ADR.
4. **Implement.** Branch from `main` per the trunk-based convention. Vertical slices, one concern per commit. Match existing module boundaries — keep platform-specific code under `src/platform/<os>/` and not in shared code paths.
5. **Verify.** Run every command in the verification checklist below. Capture output.
6. **Hand off.** Open PR against `main` referencing the issue. Single concern per PR — squash-merge applies, so the PR title becomes the merge commit subject.
## Verification (exit criteria)
A session in this repo is not done until each of these produces evidence:
- [ ] `cargo fmt --check` exits 0
- [ ] `cargo clippy -- -D warnings` exits 0
- [ ] `cargo test` exits 0 on the host platform
- [ ] For platform-specific changes: `cargo build --features <flag>` for each affected platform feature (`linux`, `macos`, `ios`, `android`, `esp32`, `windows`) — and `cargo test --features <flag>` where the feature gates test code paths
- [ ] For codec/translator changes: `cargo test --features translator-codec`
- [ ] For Android AAR changes: `cd android && ./gradlew assembleRelease` succeeds
- [ ] For UniFFI surface changes: regenerated bindings are committed in the same PR (do not let bindings drift)
- [ ] If the change is functional: a behavioral test or a hardware-test plan covers the new behavior — not just unit-coverage padding
"Seems right" or "the diff looks correct" is never sufficient.
## Anti-rationalization
| Excuse | Rebuttal |
|---|---|
| "This change is too small to need a test." | If it's worth changing, it's worth one assertion. Add the test. |
| "I'll fix the clippy warning later." | The CI gate is `-D warnings`. There is no later. Fix it before commit. |
| "I only changed shared code; the per-platform builds will pass." | BLE platform code interacts non-obviously with feature flags and target dependencies. Build each affected platform locally. |
| "I'll regenerate the UniFFI bindings in a follow-up." | Stale bindings break the ATAK plugin's AAR consumption and the Android CI gate. Regenerate and commit in the same PR. |
| "I'll bump the version to drop the `-rc` suffix to clean up." | peat-btle is in an active RC cycle and downstream M5Stack/ESP32 firmware pins specific RCs (see the peat repo's "M5Stack peat-btle dep gate" CI check). Don't bump versions casually. |
| "Cargo.lock churn is noise." | peat-btle commits `Cargo.lock` because downstream consumers pin against this crate's resolved deps. Lockfile changes ride along with version bumps; don't strip them. |
| "Transport-level retry can live in peat-mesh's adapter — same trait." | peat-btle **is** the transport adapter for BLE. Retry semantics specific to BLE link characteristics (advertise window, GATT timeouts, paired-vs-unpaired) belong here, not in `peat-mesh`. |
| "Re-introduce the `mesh-translator` feature so peat-btle can host the `Translator` impl directly." | Don't. ADR-059 Amendment 4 Slice 4.b deleted that feature precisely to break the `peat-mesh ⇄ peat-btle` cycle. peat-mesh's tree is the home for `Translator` impls now. |
## Scope guards
- Touch only files the issue/user asked you to touch.
- Do not edit other peat-* repos. Cross-repo work goes in a separate PR in that repo, linked through a tracking issue.
- Keep platform-specific code under `src/platform/<os>/`. Shared code must compile on every supported platform feature.
- Do not bleed app-layer logic (mesh sync, document state, broker concerns) into BLE transport — those belong in `peat-mesh` or `peat-protocol`.
- Do not break the Android AAR build silently. If you touch the UniFFI surface, regenerate bindings and run `./gradlew assembleRelease`.
- Do not configure git to bypass GPG signing or use `--no-verify` to skip pre-commit hooks.
## Gotchas
Add an entry each time a session produces output that needed correction. One line per gotcha plus a `Why:` line.
- *(none recorded yet)*
## References (read on demand, not by default)
- Ecosystem invariants: `peat/SKILL.md` (sibling repo)
- Build matrix and feature flags: `CONTRIBUTING.md`
- Quickstart guide: `peat-btle-quickstart-guide.md`
- M5Stack/Samsung integration test plan: `peat-btle-m5stack-samsung-test-plan.md`
- Implementation kickstart: `peat-btle-implementation-kickstart.md`
- Cross-compilation: `Cross.toml`
- **Local ADR index**: `docs/adr/` — covers peat-btle's internal architecture (trust, provisioning, document registry). Numbering is inconsistent across the existing files (`001-`, `03-`, `04-`, `ADR-001-`, etc.) — match the existing convention if adding new ones, or normalize as a separate cleanup PR.
- **Ecosystem ADR index**: `peat/docs/adr/` (sibling repo) — `ADR-032` (pluggable transport), `ADR-039` (BLE refinements), `ADR-049` (security primitives), `ADR-059` (translator / cross-transport bridging) and others; cited in this repo's `Cargo.toml` comments and recent commits
- Repo: https://github.com/defenseunicorns/peat-btle
---
*Last updated: 2026-05-05*
*Maintained by: Kit Plummer, VP Data and Autonomy, Defense Unicorns*