Nostr relay event moderation — shadow-queue + Timmy AI auto-review #39

Closed
opened 2026-03-19 18:52:14 +00:00 by replit · 1 comment
Owner

Why

Every post — even from whitelisted accounts — is shadow-queued before publication. Timmy auto-reviews benign events and flags ambiguous ones for manual admin review.

Acceptance criteria

  • relay_event_queue DB table: event_id, pubkey, kind, raw_event (JSON), status (pending/approved/rejected/auto_approved), reviewed_by (timmy_ai/admin/null), review_reason, created_at, decided_at
  • POST /api/relay/policy updated: whitelisted non-elite → insert into queue, return shadowReject; elite → inject via strfry HTTP import, return accept
  • injectEvent(rawEvent) helper calls strfry's POST /import endpoint (internal container network)
  • ModerationService: enqueue(event), autoReview(eventId) (calls Claude haiku with concise moderation prompt → approve/flag), decide(eventId, decision, reason) (updates DB + calls injectEvent on approval)
  • Background poll loop every 30 s, processes up to 10 pending events per cycle
  • Admin endpoints: GET /api/admin/relay/queue?status=pending, POST /api/admin/relay/queue/:id/approve, POST /api/admin/relay/queue/:id/reject
  • GET /api/admin/relay/stats: event counts by status for today + account count

Out of scope

  • Admin UI (separate issue)
  • Spam/rate-limit heuristics

Relevant files

  • artifacts/api-server/src/lib/ (new ModerationService)
  • artifacts/api-server/src/routes/ (relay/policy, admin/relay)
  • lib/db/src/schema/

Delegate

@hermes

## Why Every post — even from whitelisted accounts — is shadow-queued before publication. Timmy auto-reviews benign events and flags ambiguous ones for manual admin review. ## Acceptance criteria - [ ] `relay_event_queue` DB table: event_id, pubkey, kind, raw_event (JSON), status (pending/approved/rejected/auto_approved), reviewed_by (timmy_ai/admin/null), review_reason, created_at, decided_at - [ ] `POST /api/relay/policy` updated: whitelisted non-elite → insert into queue, return `shadowReject`; elite → inject via strfry HTTP import, return `accept` - [ ] `injectEvent(rawEvent)` helper calls strfry's `POST /import` endpoint (internal container network) - [ ] `ModerationService`: `enqueue(event)`, `autoReview(eventId)` (calls Claude haiku with concise moderation prompt → approve/flag), `decide(eventId, decision, reason)` (updates DB + calls injectEvent on approval) - [ ] Background poll loop every 30 s, processes up to 10 pending events per cycle - [ ] Admin endpoints: `GET /api/admin/relay/queue?status=pending`, `POST /api/admin/relay/queue/:id/approve`, `POST /api/admin/relay/queue/:id/reject` - [ ] `GET /api/admin/relay/stats`: event counts by status for today + account count ## Out of scope - Admin UI (separate issue) - Spam/rate-limit heuristics ## Relevant files - `artifacts/api-server/src/lib/` (new ModerationService) - `artifacts/api-server/src/routes/` (relay/policy, admin/relay) - `lib/db/src/schema/` ## Delegate `@hermes`
replit added the apienhancementhermesbackend labels 2026-03-19 18:52:14 +00:00
replit added the timmy label 2026-03-19 19:33:33 +00:00
claude was assigned by Rockachopa 2026-03-22 23:38:13 +00:00
Collaborator

PR #62 created.

All acceptance criteria for the relay event moderation feature were already implemented in the codebase (DB table, relay policy, ModerationService, background poll loop, admin endpoints, admin panel). This PR adds testkit coverage with 10 new tests (T41–T50) covering the relay policy health check, admin stats, queue operations, grant/revoke flow, and input validation guards.

PR #62 created. All acceptance criteria for the relay event moderation feature were already implemented in the codebase (DB table, relay policy, ModerationService, background poll loop, admin endpoints, admin panel). This PR adds testkit coverage with 10 new tests (T41–T50) covering the relay policy health check, admin stats, queue operations, grant/revoke flow, and input validation guards.
This repo is archived. You cannot comment on issues.