# Agent Deployment Plan

How to use Claude Code agents effectively for building Field Observer. Each agent is a focused unit of work that can run in parallel where dependencies allow.

## Phase 1 Agents (Local Capture + Upload + Feed)

### Agent 1: Scaffold & UI Shell
**Type:** general-purpose
**Task:** Create `index.html`, `css/field-observer.css`, `js/app.js`, and the join screen UI. Mobile-first layout, CSS custom properties from acequia-tokens.css. No framework, vanilla JS + DOM.
**Depends on:** nothing

### Agent 2: Camera Capture + Upload Module
**Type:** general-purpose
**Task:** Build `js/capture.js`, `js/upload.js`, and `js/ui/capture-overlay.js`. Two input paths:
- **Capture:** getUserMedia with front/back switching, photo to canvas, video via MediaRecorder
- **Upload:** `<input type="file" accept="image/*,video/*" multiple>`, EXIF GPS extraction, batch processing
Both paths produce: Blob + thumbnail (400px canvas) + metadata object.
**Depends on:** nothing (standalone module)

### Agent 3: OPFS Store + Feed Renderer
**Type:** general-purpose
**Task:** Build `js/opfs-store.js`, `js/feed.js`, and `js/ui/lightbox.js`.
- OPFS: read/write/delete media blobs in `/field-observer/{groupId}/thumb/` and `/full/` and `/clip/`
- Feed: renders grid of thumbnails from metadata array, lightbox with swipe (touch events)
- IndexedDB: small metadata index only (manifest entries, settings)
- Exports `addMedia()`, `getMedia()`, `renderFeed()`, `opfs.write()`, `opfs.read()`
**Depends on:** nothing (standalone module)

**Phase 1 integration:** One agent wires capture/upload output into OPFS store + feed. Short task after the three above finish.

---

## Phase 2 Agents (Networking)

### Agent 4: Acequia Integration
**Type:** general-purpose (with Explore subagent first)
**Task:** Build `js/share-engine.js`. Bootstrap acequia, join group, register routes. Wire up:
- Event bus: publish `media/new` with thumbnail blob on capture/upload
- Event bus: subscribe `media/new` to call `feed.addMedia()`
- Group shared state: maintain media manifest
**Pre-work:** Explore agent reads acequia.io/documentation to understand exact API surface for Group, Event Bus, and shared state.
**Depends on:** Agent 1 (app shell), Agent 3 (feed module), acequia.js availability

### Agent 5: Join Screen Logic
**Type:** general-purpose
**Task:** Build `js/ui/join-screen.js`. Group creation (generate short code), join by code, QR code generation (using a lightweight QR lib or canvas), recent groups from localStorage, display name persistence.
**Depends on:** Agent 1 (UI shell)

---

## Phase 3 Agents (Persistent Storage)

### Agent 6: WebDAV Persistence
**Type:** general-purpose
**Task:** Extend `share-engine.js` with WebDAV upload. On capture/upload: PUT thumbnail + full-res to `/acq/geo.camera/field-observer/{group}/`. On group join: PROPFIND to load existing media manifest. Offline queue in OPFS (pending-uploads dir), drain on reconnect.
**Depends on:** Agent 4 (share engine exists)

---

## Phase 4 Agents (Multi-Device Backup)

### Agent 7: Mirror / Replication Engine
**Type:** general-purpose
**Task:** Build `js/mirror.js`. Implements:
- Mirror opt-in toggle per device
- Background replication: pull full-res from WebDAV or WebRTC peers into local OPFS
- Mirror registry in shared state (`mirrors` array per media entry)
- WebRTC route `/media/{id}/full` to serve full-res from OPFS to requesting peers
- Fetch routing: local OPFS > WebRTC mirror > WebDAV server
- Bandwidth-aware: only replicate on WiFi (Network Information API)
**Depends on:** Agent 4 (share engine), Agent 3 (OPFS store)

---

## Phase 5 Agents (Geo + Map)

### Agent 8: Geolocation + Map View
**Type:** general-purpose
**Task:** Build `js/map-view.js`. Request geolocation permission, attach coords to media metadata. EXIF GPS extraction for uploaded files. Leaflet map with photo markers, marker clustering, tap-to-view. Toggle between grid and map views.
**Depends on:** Agent 3 (feed data model)

---

## Phase 6 Agents (Long Video + Seeking)

### Agent 9: Video Index Builder
**Type:** general-purpose
**Task:** Build `js/video-index.js`. Parses WebM (Cues/Cluster elements) and MP4 (moov/stss atoms) containers to extract keyframe byte offsets. Produces a `{mediaId}-index.json` with time-to-byte mapping. Stored in OPFS alongside video and uploaded to WebDAV.
**Depends on:** nothing (pure parsing module, can develop standalone with test files)

### Agent 10: Seekable Video Player
**Type:** general-purpose
**Task:** Build `js/ui/video-player.js`. Uses MediaSource API + SourceBuffer. On seek:
- Binary-search the keyframe index for nearest preceding keyframe
- Request byte range from WebDAV (HTTP Range header) or from mirror peer (WebRTC route)
- Append chunk to SourceBuffer
- Keyframe markers on seek bar
- Buffering indicator
**Depends on:** Agent 9 (video index), Agent 7 (mirror routes for WebRTC byte-range)

---

## Cross-Cutting Agents (use throughout)

### Explore Agent
**When:** Before any agent that needs to understand existing code (acequia API, service worker patterns, existing apps).
**Task:** Read specific files, understand API surface, report back with function signatures and usage patterns.
**Example prompts:**
- "Read acequia.io/documentation/ files about Group, Event Bus, and shared state. Report the exact JS API for joining a group, publishing events, and updating shared state."
- "Read geo.camera/apps/camera-calibrator/ to understand how existing apps structure their HTML/JS/CSS."

### Test Agent (worktree isolation)
**When:** After each phase completes.
**Task:** Run in isolated worktree. Verify the app loads, capture works (mock getUserMedia in tests), feed renders, WebRTC events fire.
**Isolation:** `worktree` mode so test scaffolding doesn't pollute the main branch.

---

## Parallelism Map

```
Phase 1:  [Agent 1] ─┐
          [Agent 2] ──┼── integrate ── Phase 1 done
          [Agent 3] ─┘

Phase 2:  [Agent 4] ──┬── Phase 2 done
          [Agent 5] ──┘

Phase 3:  [Agent 6] ──── Phase 3 done

Phase 4:  [Agent 7] ──── Phase 4 done

Phase 5:  [Agent 8] ──── Phase 5 done

Phase 6:  [Agent 9] ─┬── Phase 6 done
          [Agent 10]─┘
```

Phases 1-2 are the critical path. Agents 1, 2, 3 are fully independent and should run in parallel. Agent 9 (video index parser) is also independent and could start anytime.

## Agent Prompting Tips

- Always include the path to `plan.md` and `agents.md` so the agent has full context
- For acequia integration, include the exact file paths to the documentation the agent should read
- Specify "vanilla JS, no framework, ES6 modules" to prevent agents from pulling in React/Vue
- Specify "mobile-first, touch events, no hover states" for UI agents
- Tell agents to use CSS custom properties and the existing acequia-tokens.css design system
- For OPFS work, note that `navigator.storage.getDirectory()` is async, and `createSyncAccessHandle()` is only available in workers
