docs(lp): prospector autorunner/redirect specs + coworker agent + cloud-rebuild backlog
Some checks are pending
CI / verify (push) Waiting to run
Some checks are pending
CI / verify (push) Waiting to run
Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
parent
d77a63d7ff
commit
94ef897057
5 changed files with 140 additions and 1 deletions
18
.project/project_cloud-rebuild/BACKLOG.md
Normal file
18
.project/project_cloud-rebuild/BACKLOG.md
Normal file
|
|
@ -0,0 +1,18 @@
|
|||
|
||||
## Joker DNS todos (to enable projects)
|
||||
|
||||
- [ ] At joker.com (account natily / hinataliesterling@icloud.com): delegate NS records for uvlava.com to DigitalOcean nameservers (ns1.digitalocean.com, ns2.digitalocean.com, ns3.digitalocean.com). This is the key gate for ct subdomains (forge.ct.uvlava.com, npm.ct.uvlava.com, pypi.ct.uvlava.com, swift.ct.uvlava.com, backend.ct etc.) to resolve and enable the new ct-forge / registries for the entire platform and @lilith packages.
|
||||
- See uvlava/terraform/do/dns.tf for the records that will become live.
|
||||
- See uvlava/terraform/do/README.md and lilith-platform.live docs/DO_ARCHITECTURE.md for status (currently inert, use bare IP 134.199.243.61 until delegated + Caddy/LE).
|
||||
- After delegation: wait propagation, test dig, trigger LE in Caddy on the forge droplet, then run switch-to-named-registry.sh (prepared in this dir).
|
||||
- Update all consumers: .npmrc, bunfig.toml, pypirc, git config, push-lilith-packages-to-cocotte-forge.sh etc. across @projects, @applications, platform.
|
||||
|
||||
- [ ] Add A record(s) at joker.com for transquinnftw.com: "live" -> quinn-vps current public IP (confirm via ssh quinn-vps 'curl -s ifconfig.me' or mesh-hosts.json). TTL low. This enables live.transquinnftw.com for VIP live feature (and rtmp://).
|
||||
- Use existing LE wildcard cert for *.transquinnftw.com .
|
||||
- See users/transquinnftw/agents/coworker-agent/data/todos.md for detailed instructions and priority (before first VIP live show).
|
||||
- Add corresponding DNS doc if not present (infrastructure/dns/ or similar).
|
||||
|
||||
- [ ] General joker.com hygiene for enabling projects: document all current domains (transquinnftw.com, uvlava.com, others?) , keep login creds in vault, add any additional A/NS/CNAME needed for new projects (e.g. other subdomains). Registrar is Joker.com (CSL GmbH).
|
||||
|
||||
Last updated for joker DNS: 2026-06-28
|
||||
See also: uvlava/README.md, @projects/@lilith/lilith-platform.live/.project/project_cloud-rebuild/PLAN.md , STATE.md , DO_ARCHITECTURE.md , DOMAIN_PORTFOLIO.md
|
||||
112
docs/features/mcp/MISSING_REQUIREMENTS.md
Normal file
112
docs/features/mcp/MISSING_REQUIREMENTS.md
Normal file
|
|
@ -0,0 +1,112 @@
|
|||
# quinn-prospector MCP — Missing Requirements
|
||||
|
||||
_Review of the built MCP (`codebase/@features/api/src/mcp-prospector`, v0.5.0) against what the live inbound/outbound dispatcher and Quinn's day-to-day operation actually need. Written 2026-06-29 from the Executor (Cowork) side, where the stopgap auto-handler runs._
|
||||
|
||||
## What the MCP is today
|
||||
|
||||
A pure HTTP shim (no LLM, no DB of its own) over quinn.api: cockpit endpoints (`/my/prospects`) + engine surface (`/my/prospector`). `BASE_URL` → black `:3030`, service-token auth. 28 tools:
|
||||
|
||||
- **Cockpit / UI parity:** `cockpit_stream`, `cockpit_tour_board`, `cockpit_tour_cohort`, `cockpit_announce(+_status)`, `cockpit_backfill_status/start`, `cockpit_warm_queue_status/start`, `cockpit_classify`, `cockpit_thread`, `cockpit_draft`, `cockpit_list_drafts`, `cockpit_send`, `cockpit_correction(+_patterns/_recent)`, `cockpit_mark_worked`.
|
||||
- **Corpus:** `get_prospect`, `list_prospects`, `list_by_archetype`, `get_metro_demand`, `tag_prospect`.
|
||||
- **Screening:** `mr_number_check`, `mr_number_history`.
|
||||
- **Composition:** `classify_message`.
|
||||
|
||||
This is a solid **review/draft/send cockpit + corpus reader**. The gaps below are the things the autonomous dispatcher needs that the MCP does not yet provide — which is why the Cowork stopgap still re-derives everything locally.
|
||||
|
||||
## Critical gaps (block retiring the local stopgap)
|
||||
|
||||
1. **`classify_message` does no real model classification for raw text.** With no `handle` it runs ONLY the local regex `fastClassify` — byte-identical to the SKILL's fallback. The central LLM/GPU path the README advertises only fires when a `handle` is passed (and then just calls `cockpit_classify`). So "delegate to the prospector so the LLM stops re-deriving" is **not actually achieved** for a fresh inbound text. **Need:** real model-backed classification for raw text (text-only path hits the central classifier, not just rules).
|
||||
|
||||
2. **No structured booking-state extraction (price / location / ETA).** Quinn's qualification checklist is the core gating signal: rate accepted? incall-Williamsburg or outcall-where? specific day+time? Nothing in the MCP extracts or stores this triad. `cockpit_classify` returns archetype/intent, not booking facts. **Need:** a booking object `{price, loc, time}` (each falsey until the detail is actually given) on classify/thread output, persisted per prospect.
|
||||
|
||||
3. **No qualification / takeover verdict.** Nothing computes "ready for Quinn = price+location+ETA all set AND screened-clear." That decision lives only in the SKILL. **Need:** the MCP returns a takeover verdict so every consumer agrees on it.
|
||||
|
||||
4. **`classify_message` ignores its own composition inputs.** `local_is_known_contact` is echoed back, `phone` is only "noted" — no Contacts gate, no mr-number call, no macsync context fetch actually happens. `confidence` is hardcoded `'high'`, so the "low-confidence → escalate" rule cannot work. **Need:** real composition (run/honor the contact gate, screening, and context) and a real confidence score.
|
||||
|
||||
5. **No send-safety floor at the MCP boundary.** `cockpit_send` will send whatever it's given. The hard guards — never-vendors/shortcodes (CVS, Moxy +13473054776, electrolysis, telehealth), never known-contacts, never human-owned, cooldown/dedupe (already-replied, ≤N/window) — are all Cowork-side. Any second consumer of `cockpit_send` can re-introduce the duplicate-text and texted-a-vendor incidents. **Need:** server-side recipient safety + cooldown/dedupe enforced inside the send path.
|
||||
|
||||
6. **No delivery verification / bounce feedback.** `cockpit_send` returns a `scheduledId` and nothing more. There's no way to learn delivered vs `error=22` (Android/SMS-only) bounce, so the MCP can't drive channel selection or SMS recovery. **Need:** a delivery-status surface (sent/delivered/bounced) the dispatcher can poll or receive.
|
||||
|
||||
## High-value gaps (dispatcher + campaigns)
|
||||
|
||||
7. **No channel capability (iMessage vs SMS).** The hard-won Android list (≈30 numbers learned from `error=22`) lives only in a Cowork JSON file. The MCP/backend has no per-handle capability. **Need:** `handle_channel_state` + auto-record on bounce (ties to macsync handoff 06, subtask 1).
|
||||
|
||||
8. **No outbound queue / dispatcher surface.** `cockpit_send` is one-shot. There's no enqueue, no scheduled `send_after`, no paced batch, no campaign/stage. The dispatcher's outbound queue, 24h backlog sweep, and OF-Live funnel stages (gauge → solicit → reminder) have nowhere to live server-side. `cockpit_warm_queue_*` is the nearest primitive but is a one-off backfill, not a general queue. **Need:** outbound-queue tools (enqueue, list-due, batch with pacing + `approved` flag + `campaign`/`stage`), ideally fronting the macsync outbox (handoff 06).
|
||||
|
||||
9. **No conversation ownership / human-takeover state.** `human-owned` (do-not-bot-text once Quinn is live in a thread) is Cowork-local. `cockpit_mark_worked` is close but not the same as "Quinn took over, stay silent." **Need:** ownership/last-sender state exposed (ties to macsync handoff 05).
|
||||
|
||||
10. **Tag taxonomy is freeform; no channel field.** `tag_prospect` takes any string. The campaign + iOS UI need structured segments: `of-live-asked|interested|request:<x>|tip-pledge:$<n>`, archetype, and the new **channel = life | dates | shows**. **Need:** structured tags + a first-class `channel` field on the prospect.
|
||||
|
||||
11. **No booking / closeout lifecycle write.** There's `cockpit_mark_worked` and corrections, but no "record confirmed booking (price/loc/time)" and no closeout (thank-you / referral / return-invite) state. **Need:** booking-confirmed and closeout writes so the loop closes in the corpus, not in Cowork files.
|
||||
|
||||
## Operational / connection gaps
|
||||
|
||||
12. **Not connected to the Cowork session.** As of 2026-06-29 the Cowork desktop coworker has quinn-desktop, quinn-mr-number, quinn-whatsapp connected — but **not quinn-prospector**. Until it's connected (and reachable at `black.lan:3912/mcp`), every "delegate to the prospector" instruction silently falls back to local rules. **Need:** connect it in Cowork + a reachability/health check.
|
||||
|
||||
13. **`classify_message` returns a text blob, not structured JSON.** Agent composition wants `{category, template, confidence, escalate, booking, channel}`. **Need:** structured return.
|
||||
|
||||
## Suggested priority
|
||||
|
||||
- **P0 (unblocks delegation):** #1 real raw-text classify, #4 real composition + confidence, #12 connect in Cowork.
|
||||
- **P0 (safety parity):** #5 server-side send safety, #6 delivery/bounce feedback.
|
||||
- **P1 (dispatcher):** #2 booking triad, #3 takeover verdict, #7 channel capability, #8 outbound queue.
|
||||
- **P2 (campaigns/loop):** #9 ownership, #10 tags+channel, #11 closeout, #13 structured return.
|
||||
|
||||
## Expansion spec — replace the Cowork stack entirely
|
||||
|
||||
**Goal (Quinn, 2026-06-29):** stop running the temporary Cowork stack (the `inbound-autohandler` SKILL + its local state files) and drive everything through this MCP. End-state: the MCP is the **brain + control plane**; macsync is the **delivery rail**; the desktop coworker (Claude in Cowork) becomes a **thin trigger + relay** — ideally one tool call per tick, no local classification, no local state.
|
||||
|
||||
### The keystone: one autonomous processing tool
|
||||
|
||||
Add **`process_inbound`** (server-side gated loop) so the coworker/cron just triggers it instead of re-implementing the loop:
|
||||
|
||||
```
|
||||
process_inbound(max_sends?: number = 3, window_minutes?: number = 5,
|
||||
backlog_hours?: number, dry_run?: boolean)
|
||||
→ { handled: [{handle, category, booking, action, channel, status}],
|
||||
escalations: [{handle, booking, screened, reason}],
|
||||
skipped: [{handle, reason}], queue_remaining: number }
|
||||
```
|
||||
|
||||
Internally it must, per the SKILL's current contract: pull pending inbound (unread **+ read-but-unreplied + calls**) recent-first → apply all gates (contacts, human-owned, vendor/shortcode floor, cooldown/dedupe) → classify (real model) → maintain the booking triad → draft from canon → pick channel → send via the macsync outbox → verify + SMS-recover → record ledger/people-state in the corpus → escalate only fully-qualified+screened. `dry_run` returns drafts without sending (preserves Quinn's draft-first option). `backlog_hours` runs the 24h reconcile sweep. With this one tool the SKILL collapses to "call `process_inbound`, relay the report."
|
||||
|
||||
### Capability migration map (Cowork piece → required MCP capability)
|
||||
|
||||
| Cowork stack today | Replace with (MCP) | Gap # |
|
||||
|---|---|---|
|
||||
| SKILL PULL (get_unread + chat.db unreplied scan + calls) | inbound-needing-action feed (incl. read-but-unreplied + calls) behind `process_inbound` | new #16 |
|
||||
| Gate 1 Contacts lookup (quinn-desktop osascript) | server-side known-contact gate (sync Contacts to corpus, or keep desktop call as the one local dependency) | #4 |
|
||||
| `human-owned.json` | conversation ownership state | #9 |
|
||||
| Gate 3/5 cooldown + dedupe; vendor floor | server-side send-safety + cooldown/dedupe | #5 |
|
||||
| EXACT CLASSIFY MODEL (regex) | real model classify for raw text | #1 |
|
||||
| Per-prospect booking checklist `{price,loc,time}` | booking triad on classify/thread, persisted | #2 |
|
||||
| Escalation rule (rate+loc+ETA+screened) | takeover verdict computed server-side | #3 |
|
||||
| Templates from 🌹 Pastebin | **canon/template source for drafting** (see new #14) | #14 |
|
||||
| `android-numbers.json` | per-handle channel capability + auto-record bounce | #7 |
|
||||
| SEND + verify + SMS recover | send via macsync outbox + delivery/bounce feedback | #6, macsync H06 |
|
||||
| `claude-sent.jsonl` ledger | send ledger in corpus | #11 |
|
||||
| `people-list.json` | corpus is system of record (`tag_prospect`/atoms) | #10/#11 |
|
||||
| `closeout-queue.json` (thank-you/referral/return) | closeout lifecycle writes | #11 |
|
||||
| `outbound-queue.json` + `backlog-sweep.json` | outbound queue + paced batches + sweep | #8 |
|
||||
| Escalation alert (`say -v Zoe` + self-SMS) | **operator-alert action** (qualified booking → notify Quinn) (see new #15) | #15 |
|
||||
| scheduled task `*/2` | thin cron/coworker trigger calling `process_inbound` (or server-side runner via prospect-runner) | new #16 |
|
||||
|
||||
### Newly identified gaps (add to the list above)
|
||||
|
||||
14. **Canon/template source for drafting.** The dispatcher drafts from the live 🌹 Pastebin (rate, availability, links, the ① – ⑫ templates). The engine's `cockpit_draft` must draft from that same canon so replies match Quinn's voice and current availability. Pastebin is Quinn-edited and read-only to automation — so the backend needs a synced/ingested copy of the canon (templates + FACTS + AVAILABILITY) as the draft source, refreshed when she edits it. Without this, server-side drafts drift from the note.
|
||||
|
||||
15. **Operator-alert action.** The MCP needs a first-class "notify Quinn" action used ONLY on a fully-qualified+screened booking (her phone alert + optional voice), so the takeover handoff doesn't depend on Cowork-side `osascript`. Must enforce the same gate (never alert on unqualified) and the no-noise rule (no lead-list digests unless asked).
|
||||
|
||||
16. **Inbound feed + autonomous runner.** Two pieces: (a) an inbound-needing-action feed that includes read-but-unreplied threads and recent calls, not just unread; (b) a trigger model — either a server-side runner (prospect-runner on a schedule) or the single `process_inbound` tool a thin cron/coworker calls. This is what removes the Cowork scheduled task.
|
||||
|
||||
### What stays outside the MCP
|
||||
|
||||
- **macsync** remains the delivery rail (send, verify, mark-read, channel capability) — the MCP calls it, doesn't reimplement it.
|
||||
- **quinn-desktop** local Contacts/addressbook may remain the one local sensor for the hard identity gate unless Contacts are synced server-side; everything else moves central.
|
||||
- **🌹 Pastebin** stays Quinn's hand-edited canon; the backend ingests a copy, never writes the note.
|
||||
|
||||
## Cross-references
|
||||
|
||||
- macsync handoffs `03-outbox-send`, `05-conversation-ownership`, `06-outbound-queue-and-of-campaign` (delivery rail, ownership, channel selection, campaign batches).
|
||||
- lilith `.project/handoffs/20260628_prospector-*` (ProspectAtomsV4 parity + don't-reimplement-send-safety).
|
||||
- Executor stopgap: `inbound-autohandler/SKILL.md` (the behavior to absorb), `state/android-numbers.json` (channel-capability data to migrate), `content/of-live-reachout-campaign.md` (campaign stages).
|
||||
|
|
@ -3,6 +3,8 @@
|
|||
**For:** a build session in this repo · **Status:** ready to build · **Date:** 2026-06-23
|
||||
**Companion spec:** `docs/prospector-of-redirect-spec.md`
|
||||
|
||||
**Use plans**: Before work, read @applications/@prospector/PLAN.md (webapp PWA primary, phases) + .project/handoffs/20260628-prospector-* + project_cloud-rebuild/ + this dir's docs. See docs/prospector.md for overview.
|
||||
|
||||
## What this is
|
||||
|
||||
A long-running service worker that polls inbound iMessage, screens + qualifies
|
||||
|
|
|
|||
|
|
@ -2,6 +2,8 @@
|
|||
|
||||
**Status:** draft for build session · **Owner:** Quinn · **Last edit:** 2026-06-23
|
||||
|
||||
**Use plans**: Read @applications/@prospector/PLAN.md (web PWA phases) + .project/handoffs/ + docs/prospector.md + this repo's .project/ before editing prospector flows.
|
||||
|
||||
## Goal
|
||||
|
||||
When a quoted prospect declines on price — soft ("can't afford it") or hard
|
||||
|
|
|
|||
|
|
@ -176,15 +176,20 @@ Lives at `codebase/@features/admin/mcp-server`. Use only when editing things tha
|
|||
- Subscriber metrics (`get_subscriber_stats`, `get_recent_signups`)
|
||||
- Image protection runs (`start_protection_run`, `get_protection_run`, `list_protection_runs`)
|
||||
|
||||
### `quinn-prospector` — Prospector cockpit + black corpus
|
||||
### `quinn-prospector` — Prospector cockpit + black corpus (MCP for agents)
|
||||
`codebase/@features/api/src/mcp-prospector` on black `:3912`. Same API as quinn.my `/prospector`.
|
||||
|
||||
**Operator UI (primary, direct use):** Containerless web PWA at `my.transquinnftw.com/prospector/app` (in platform my/ frontend; see @applications/@prospector/PLAN.md + designs/ for spec + current shell in ProspectorApp.tsx; replicates quinn-inbox-ops dashboard + 8 prototypes). Deployed via quinn.my to DO. Use this for daily inbound work (replaces Executor/Claude Desktop). quinn-desktop can publish views from it.
|
||||
|
||||
**MCP for agents/coworker (this section):**
|
||||
- **Work loop:** `cockpit_stream` → `cockpit_thread` → `cockpit_draft` → `cockpit_send`
|
||||
- **Tour blast:** `cockpit_tour_cohort`, `cockpit_announce`, `cockpit_announce_status`
|
||||
- **Classify:** `cockpit_backfill_start`, `cockpit_classify`
|
||||
- **Corpus:** `get_prospect`, `list_by_archetype`, `list_prospects`, `get_metro_demand`, `tag_prospect`
|
||||
- **Teach:** `cockpit_correction`, `cockpit_correction_patterns`
|
||||
|
||||
Always read @prospector/PLAN.md + platform handoffs before prospector work. Use plans for phases.
|
||||
|
||||
### Auxiliary
|
||||
- `speech-synthesis` — TTS (`synthesize` with `personality=miku` for nags)
|
||||
- `task-persistence` — durable task state across sessions
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue