import type { Enablement } from "./enablement.js"; import type { JournalEntry } from "./journal.js"; import type { WireReport } from "./send.js"; export interface DxDeps { entries: () => JournalEntry[]; print: (line: string) => void; now: () => number; enabled: () => boolean; path: () => string; /** * Durable unattended-send state. Optional so the many callers that only read * the journal need not resolve it; absent reads as not enabled. */ enablement?: () => Enablement; } export interface DxOptions { /** Only consider runs from the last N days. */ days: number; json: boolean; /** Send the findings to the Vincentt team. Never implied by anything else. */ send: boolean; /** Skip the confirmation prompt. Only meaningful with --send. */ yes: boolean; /** The creator's own words about the friction, carried with the report. */ note?: string; /** `vincentt dx enable` — a positional subcommand, not a flag. */ enable: boolean; /** `vincentt dx disable` — a positional subcommand, not a flag. */ disable: boolean; } export declare function parseDxOptions(args: string[]): DxOptions; export declare function dxCommand(deps: DxDeps, options: DxOptions): number; /** Wire the command to the real journal. */ export declare function runDx(args: string[], print: (line: string) => void, enablement?: () => Enablement): number; export interface DxEnableDeps { print: (line: string) => void; now: () => number; /** stdin.isTTY && stdout.isTTY. Evidence of an interactive session, not proof of a human. */ interactive: () => boolean; /** Ask once. Returns false to abort. */ confirm: (question: string) => Promise; /** * Persist the grant, or clear it when given undefined. NEVER called on a * refusal path — `enable` that refuses must not touch the file at all. */ save: (next: { at: string; } | undefined) => Promise; } /** * `vincentt dx enable` — grant this machine durable permission to send DX reports * without asking first. * * The TTY requirement is a SPEED BUMP, NOT A BOUNDARY, and is written down as * such so a later reader does not build on a guarantee that is not there. It * stops the reflex — an agent that meets a prompt, infers there must be a way * past it, and tries the obvious thing. It does not stop a caller that allocates * a PTY or writes config.json directly. * * The refusal path writes NOTHING. Not "writes the same bytes back" — nothing at * all: this file holds the PAT, and a refusal that round-trips the config through * a write can lose the credential if it dies mid-write. */ export declare function dxEnableCommand(deps: DxEnableDeps, sunset: number): Promise; /** * `vincentt dx disable` — the obvious opposite command. * * Clears BOTH keys. Leaving the timestamp behind would make a later re-enable * report its age from the first grant, which is the kind of thing that ships * wrong and is never noticed. Needs no terminal and no confirmation: turning a * capability OFF is always safe to do, and requiring a TTY here would strand a * creator who wanted to revoke from a script. */ export declare function dxDisableCommand(deps: DxEnableDeps): Promise; export interface DxSendDeps extends DxDeps { /** Resolved API host + PAT. Absent when the creator is not signed in. */ auth: () => Promise<{ apiUrl: string; pat: string; } | undefined>; post: (apiUrl: string, pat: string, report: WireReport) => Promise<{ ref: string; findings: number; expiresAt: string; }>; /** Ask before sending. Returns false to abort. */ confirm: (question: string) => Promise; cliVersion: () => string; /** * stdin.isTTY && stdout.isTTY. Evidence of an INTERACTIVE SESSION, not proof of * a human: an agent harness that allocates a PTY passes this with nobody * present. The enabled path below is the honest one; this arm gates * convenience, not authorization. */ interactive: () => boolean; /** Durable unattended-send state, read strictly. Absent reads as not enabled. */ enablement?: () => Enablement; } /** * `vincentt dx --send`. * * The order is the consent model and is not an implementation detail: find the * friction, BUILD the payload, SHOW it in full, ask, and only then send. A * creator who cannot see what leaves their machine before it leaves has not * agreed to anything. */ export declare function dxSendCommand(deps: DxSendDeps, options: DxOptions): Promise;