UNPKG

@phren/cli

Version:

Knowledge layer for AI agents - CLI, MCP server, and data layer

59 lines (58 loc) • 2.91 kB
import { type Json } from "./protocol.js"; import type { WorkspacesReader } from "./server-routes.js"; /** * The `/v1/overview` WebSocket: the same overview `GET /v1/workspaces` * answers, pushed to the phone when it changes, so a phone keeps one socket * per computer open instead of polling. Each tick reads the shared Herdr * snapshot at most one tick old: the activity timer takes one every five * seconds (and open chats every 2.5), so a connected phone adds no Herdr * snapshots of its own, and a status change reaches it within one tick. The * overview is rebuilt when that snapshot changed or `OVERVIEW_REFRESH_MS` has * passed (branches, models and steps live outside the snapshot), and sent * only when it differs from the last one sent. With nothing to send, a heartbeat every * `OVERVIEW_HEARTBEAT_MS` carries the Hook's info and tells the phone the * overview it holds is still current. * * Frames: `{ type: "overview", ...workspaces, phren }` and * `{ type: "heartbeat", phren }`. A phone that asks with `resources=1` also * gets `{ type: "resources", resources }` after the first overview, then at * `OVERVIEW_RESOURCES_MS` intervals (an older phone never asks, so never meets it). * One that asks with `sudo=1` gets `{ type: "sudo", requests }` after the first * overview and whenever the pending sudo requests change. */ export declare const OVERVIEW_TICK_MS: number; export declare const OVERVIEW_REFRESH_MS: number; export declare const OVERVIEW_HEARTBEAT_MS: number; export declare const OVERVIEW_RESOURCES_MS: number; export interface OverviewStreamOptions { read: WorkspacesReader; /** The Hook's info, as `/v1/health` reports it. */ info: () => Json; /** Renews the approval watch lease `watchApprovals=1` asks for. */ renew: (server: string) => void; /** Pending sudo requests (`GET /v1/sudo`), for phones that ask with `sudo=1`. */ sudo?: { list(): unknown[]; subscribe(listener: (requests: unknown[]) => void): () => void; }; /** This computer's resources (`GET /v1/resources`), for phones that ask. */ resources?: () => Promise<unknown>; snapshot?: (server: string, maxAgeMs: number) => Promise<Json>; now?: () => number; tickMs?: number; refreshMs?: number; heartbeatMs?: number; resourcesMs?: number; } /** A socket-like peer: the `ws` client, or a test double. */ export interface OverviewClient { readonly readyState: number; readonly bufferedAmount: number; send(data: string): void; close(code?: number, reason?: string): void; once(event: "close" | "error", listener: () => void): unknown; } export declare function overviewStream(options: OverviewStreamOptions): (client: OverviewClient, server: string, watchApprovals: boolean, withResources?: boolean, typedMux?: boolean, withSudo?: boolean) => { tick: () => Promise<void>; stop: () => void; };