Feat v0.5.1 chat core (#31)
All checks were successful
All checks were successful
Co-authored-by: Jeffrey Smith <jasafpro@gmail.com> Co-committed-by: Jeffrey Smith <jasafpro@gmail.com>
This commit was merged in pull request #31.
This commit is contained in:
61
ROADMAP.md
61
ROADMAP.md
@@ -1,6 +1,6 @@
|
||||
# Switchboard Core — Roadmap
|
||||
|
||||
## Current: v0.5.0 — Realtime Primitive + Dialog Audit + Permissions UI
|
||||
## Current: v0.5.1 — Chat Core Library
|
||||
|
||||
Fork of chat-switchboard, gutted to a pure extension platform. All AI/chat
|
||||
features removed from the kernel. What remains is the minimum viable
|
||||
@@ -341,18 +341,22 @@ participation is post-MVP.
|
||||
| Native dialog audit | ✅ | 5 bare `confirm()` calls migrated to `sw.confirm()` in tasks, schedules, notes (×2), editor packages. |
|
||||
| Admin permissions UI | ✅ | Permissions drawer in admin Packages page. Grant/revoke per permission, grant-all bulk action. `pending_review`/`suspended` status badges. SDK API client methods added. Closes gap identified in v0.4.7. |
|
||||
|
||||
### v0.5.1 — Chat Core Library (planned)
|
||||
### v0.5.1 — Chat Core Library
|
||||
|
||||
| Step | Status | Description |
|
||||
|------|--------|-------------|
|
||||
| Library package | | `chat-core` library with `permissions: ["db.write"]`. Private ext_data tables, exported Starlark functions, REST endpoints. |
|
||||
| Conversations table | | `conversations` — title, type (direct/group), created_by, updated_at. |
|
||||
| Participants table | | `participants` — conversation_id, participant_id, participant_type (user/bot), display_name, role (member/admin), joined_at. |
|
||||
| Messages table | | `messages` — conversation_id, participant_id, content, content_type (text/system/file), edited_at. |
|
||||
| Read cursors table | | `read_cursors` — conversation_id, participant_id, last_read_message_id. |
|
||||
| Exported Starlark API | | `chat.create()`, `chat.send()`, `chat.history()`, `chat.add_participant()`, `chat.remove_participant()`, `chat.mark_read()`. |
|
||||
| REST endpoints | | Full CRUD for conversations, messages, participants. Paginated message history. Unread counts. |
|
||||
| Realtime integration | | On `chat.send()`: insert message, emit `chat.message.created` event, call `realtime.publish("conversation:{id}", "message", data)`. |
|
||||
| Library package | ✅ | `chat-core` library with `permissions: ["db.write", "realtime.publish"]`. Private ext_data tables, exported Starlark functions, REST endpoints. |
|
||||
| Conversations table | ✅ | `conversations` — title, type (direct/group), created_by, updated_at. |
|
||||
| Participants table | ✅ | `participants` — conversation_id, participant_id, participant_type (user/bot), display_name, role (member/admin), joined_at. |
|
||||
| Messages table | ✅ | `messages` — conversation_id, participant_id, content, content_type (text/system/file), edited_at. |
|
||||
| Read cursors table | ✅ | `read_cursors` — conversation_id, participant_id, last_read_message_id. |
|
||||
| Exported Starlark API | ✅ | `create()`, `send()`, `history()`, `add_participant()`, `remove_participant()`, `mark_read()` — available via `lib.require("chat-core")`. |
|
||||
| REST endpoints | ✅ | 15 routes: full CRUD for conversations, messages, participants. Cursor-based paginated message history. Per-conversation unread counts. |
|
||||
| Realtime integration | ✅ | On `send()`: insert message, publish `realtime.publish("conversation:{id}", "message", data)`. Also emits `participant.added`, `participant.removed`, `message.edited`, `message.deleted` events. |
|
||||
| db.query() range params | ✅ | Kernel enhancement: `before`/`after` kwargs for `db.query()` enabling cursor-based pagination and efficient unread counting. 7 new tests. |
|
||||
| Admin Library filter | ✅ | Added `Library` type filter to admin Packages page alongside Surface/Extension/Full/Workflow. |
|
||||
| Admin filter Dropdown | ✅ | Replaced button group with themed `Dropdown` primitive for type filter. Keyboard nav, consistent theming via CSS vars. |
|
||||
| Unicode security gate | ✅ | `ScanSource()` detects variation selectors, bidi overrides, zero-width chars, tag characters. `Verdict()` blocks GlassWorm payloads and Trojan Source (CVE-2021-42574). Two enforcement points: install (422) + Starlark exec. 23 new tests. |
|
||||
|
||||
### v0.5.2 — Chat Surface (planned)
|
||||
|
||||
@@ -377,6 +381,12 @@ participation is post-MVP.
|
||||
| Multi-user E2E | | Docker compose test: multiple browser sessions, verify real-time message delivery, presence indicators, cross-replica broadcast. |
|
||||
| Workflow integration | | Verify: workflow stage with `audience: team` can create a conversation via `chat.create()`, add assigned members as participants. Conversation scoped to instance. |
|
||||
|
||||
### Backlog — Admin UI Polish
|
||||
|
||||
| Item | Description |
|
||||
|------|-------------|
|
||||
| "Requires Review" filter | Dropdown filter option or dedicated button for `pending_review` packages. Useful when the package list grows long. |
|
||||
|
||||
### v0.5.4 — Package Updates (planned)
|
||||
|
||||
| Step | Status | Description |
|
||||
@@ -403,9 +413,33 @@ participation is post-MVP.
|
||||
Extension, communication, and operations tracks converge. First
|
||||
externally usable release.
|
||||
|
||||
- Health monitoring (extension package wrapping kernel `/health`)
|
||||
- Backup/restore tooling (ext_data export/import, admin surface)
|
||||
- Documentation site (extension authoring guide, API reference, deployment guide)
|
||||
Design docs: `docs/DESIGN-cluster-registry.md` — PG-backed cluster registry and self-assembling mesh.
|
||||
|
||||
### v0.6.0 — Cluster Registry + HA (planned)
|
||||
|
||||
PG is the consensus layer. Zero new infrastructure. `UNLOGGED` table + `LISTEN/NOTIFY` replaces etcd/Consul/Redis for homelab-to-small-team scale.
|
||||
|
||||
| Step | Status | Description |
|
||||
|------|--------|-------------|
|
||||
| `node_registry` table | | `UNLOGGED TABLE` — node_id, endpoint, seq, registered_at, heartbeat, stats JSONB. Folds into existing schema init. |
|
||||
| Node registration | | Self-registration on startup: `INSERT ... ON CONFLICT DO UPDATE`. `node_id` = `hostname-PID` or `CLUSTER_NODE_ID` env override. |
|
||||
| Heartbeat tick | | Every 10s: update own heartbeat + collect runtime stats (goroutines, heap, GC, uptime, ws_clients, extensions). |
|
||||
| Stale sweep | | Every heartbeat tick: `DELETE WHERE heartbeat < now() - 30s`. All nodes run it — idempotent, no ring topology. |
|
||||
| Self-eviction | | If heartbeat UPDATE returns 0 rows: node was swept by peer → log error + `os.Exit(1)`. K8s restarts → re-register. |
|
||||
| LISTEN/NOTIFY routing | | Durable events (messages, state changes) fan-out via `pg_notify`. All replicas receive, push to local WS subscribers, drop if irrelevant. Phase 1: ephemeral events (typing, presence) also via NOTIFY (8KB limit, ~60 bytes each). |
|
||||
| Cluster API | | `GET /api/admin/cluster` — `SELECT node_id, endpoint, registered_at, heartbeat, stats FROM node_registry ORDER BY seq`. Returns `{data: [...]}` envelope. |
|
||||
| Admin cluster dashboard | | Extension renders one card per node: node_id, endpoint, uptime, ws_clients, heap, GC pause. JSONB stats — future keys render automatically, no schema migration. |
|
||||
| Health endpoint | | `GET /health` includes `cluster: {size, peers, heartbeat_age_ms}`. Satisfies MVP health monitoring requirement. |
|
||||
| Config | | `CLUSTER_NODE_ID`, `CLUSTER_HEARTBEAT_INTERVAL` (default 10s), `CLUSTER_STALE_THRESHOLD` (default 30s), `CLUSTER_ENDPOINT` (Phase 2 mesh, auto-detect). |
|
||||
| Single-node regression | | One-node behavior identical to pre-cluster: one registry row, NOTIFY delivers back to same instance. No special-casing. |
|
||||
| Multi-node integration test | | Docker Compose: 3 instances, shared PG. Verify registration, heartbeat, peer discovery, stale sweep on shutdown, WS fan-out. |
|
||||
|
||||
### v0.6.1 — Backup/Restore + Documentation (planned)
|
||||
|
||||
| Step | Status | Description |
|
||||
|------|--------|-------------|
|
||||
| Backup tooling | | ext_data export/import, admin surface for backup management. |
|
||||
| Documentation site | | Extension authoring guide, API reference, deployment guide. |
|
||||
|
||||
## Post-MVP
|
||||
|
||||
@@ -434,5 +468,6 @@ externally usable release.
|
||||
| Notes over Editor | First surface is Obsidian-style notes (rich text, folders, backlinks) instead of a code editor. Notes is a stronger E2E proof — it exercises ext_data, storage, and the SDK more fully than a pure-browser CM6 editor. |
|
||||
| No built-in auto-install | Extensions ship in the repo but are not auto-installed. Distribution model TBD — explicit install only. Keeps the kernel clean and avoids opinionated defaults. |
|
||||
| Chat as extension, not kernel | Human-to-human chat built entirely as library + surface packages. Zero kernel awareness of conversations, messages, or participants. Kernel gains one generic `realtime` module. Proves near-infinite extensibility. LLM participation layers on top via a separate bridge extension — the chat system doesn't know or care whether a participant is human or AI. |
|
||||
| PG as consensus layer | Horizontal scaling uses PG as the sole coordinator (UNLOGGED node_registry + LISTEN/NOTIFY). No etcd, Consul, Redis, or Raft. Rationale: system is already tightly coupled to PG; adding a second consensus layer doubles operational complexity for zero benefit at homelab-to-small-team scale. UNLOGGED table is visible to all connections, survives session disconnect, and cleans up automatically on PG crash — correct behavior since all nodes are dead anyway. Sweep-all for health (every node deletes stale rows) is simpler than ring topology and has no edge cases. |
|
||||
| Two trigger tiers | Event + webhook triggers are extension-declared (manifest contract, full sandbox). Scheduled tasks are user-created ad-hoc (restricted sandbox — no raw HTTP, no DB table creation, connections-only outbound). Separation keeps extension contracts static and user automation safe. |
|
||||
| Scheduled task identity | Tasks run as their creator (RBAC-scoped). Admin-created tasks can opt into system context. Creator deactivation pauses the schedule. Ensures audit trail and permission boundaries. |
|
||||
Reference in New Issue
Block a user