/** * Channel registry — the read/write helpers over the per-space channels KV bucket. * * The bucket holds one {@link ChannelConfig} per channel (key = the concrete channel token) * plus the space-wide defaults under {@link CHANNEL_DEFAULTS_KEY}. Writes are **privileged** * (manager / `cotal up` / `cotal channels`); agents read it (the live cache lives on the * endpoint). Because description/instructions reach the model, both text fields are bounded * here and oversize is **rejected at the write path** — never silently truncated. */ import { type KV } from "@nats-io/kv"; import { type NatsConnection } from "@nats-io/transport-node"; import type { ChannelConfig, ChannelDefaults, DeliveryClass } from "./types.js"; /** The declarative channel-config file read at `cotal up` to seed the registry. */ export interface ChannelRegistryFile { defaults?: ChannelDefaults; /** Map of channel token → its config. */ channels?: Record; } /** Length caps on the model-facing registry text — unbounded text would stuff every agent's * context and bloat the KV, so a write past these throws rather than clamps. */ export declare const MAX_CHANNEL_DESCRIPTION = 200; export declare const MAX_CHANNEL_INSTRUCTIONS = 2000; /** Throw if a config is invalid: oversize text (rejected, never clamped — a write past the cap * is a caller bug) or an unparseable `replayWindow`. */ export declare function validateChannelConfig(cfg: ChannelConfig): void; /** Validate a defaults patch the same way per-channel config is — the space default feeds * {@link effectiveDeliveryClass} as a co-equal input, so a bad value must fail loud here, not * silently become the space-wide effective class. */ export declare function validateChannelDefaults(d: ChannelDefaults): void; /** Parse a duration like `"24h"`, `"30m"`, `"7d"`, `"90s"` into milliseconds. Throws on a bad * format — a typo'd window must fail loud, not silently mean "no window". */ export declare function parseDuration(s: string): number; /** Effective replay-on-join policy for a channel: per-channel override ?? space default ?? * `true`. Default-true preserves Cotal's original always-replay behavior. */ export declare function effectiveReplay(cfg: ChannelConfig | undefined, defaults: ChannelDefaults | undefined): boolean; /** Effective backfill window in ms (per-channel ?? space default), or undefined for "the full * retained window". Only meaningful when {@link effectiveReplay} is true. */ export declare function effectiveReplayWindowMs(cfg: ChannelConfig | undefined, defaults: ChannelDefaults | undefined): number | undefined; /** Effective delivery class for a channel (SPEC §4): per-channel override ?? space default ?? * `"durable"`. Default-durable keeps persistence on when a space declares no default — the safe * fallback; a space sets `defaults.deliveryClass` at creation per deployment profile. The SAME * resolution MUST drive live join, durable fan-out, history read, and membership surfacing, so * every path agrees on a channel's class. */ export declare function effectiveDeliveryClass(cfg: ChannelConfig | undefined, defaults: ChannelDefaults | undefined): DeliveryClass; /** Open the channels registry bucket. Auth mode (creds present) OPENs the bucket pre-created * at `cotal up`; open dev mode lazily CREATEs it. Mirrors the presence-bucket open/create * split (and, like presence, agents are denied KV stream-create so they must OPEN). */ export declare function openChannelRegistry(nc: NatsConnection, space: string, opts?: { create?: boolean; }): Promise; /** Read one channel's config (or undefined if unset/deleted). */ export declare function readChannelConfig(kv: KV, channel: string): Promise; /** Read the space-wide defaults (or undefined if unset). */ export declare function readChannelDefaults(kv: KV): Promise; /** Privileged write of a channel's config. **Merges** over any existing entry so a partial * set (e.g. `--desc` only) doesn't wipe `replay`. Validated before the put. */ export declare function writeChannelConfig(kv: KV, channel: string, patch: ChannelConfig): Promise; /** Privileged write of the space-wide defaults (merged over any existing). Validated before the * put — a bad default would otherwise feed {@link effectiveDeliveryClass} silently. */ export declare function writeChannelDefaults(kv: KV, patch: ChannelDefaults): Promise; /** Connect (with the given privileged creds, or open if none), seed the registry from a * declarative {@link ChannelRegistryFile} (defaults + per-channel config, merged), disconnect. * Used by `cotal up` to seed once at setup, and by `cotal channels` for runtime writes. * Each field in the file overwrites that field in the registry; unspecified fields are kept. */ export declare function seedChannelRegistry(opts: { servers: string; space: string; creds?: string; /** User mode: a `channel-writer`-view bearer + the space's sentinel creds (instead of a creds file). */ bearer?: string; sentinelCreds?: string; file: ChannelRegistryFile; }): Promise; /** Write the space-wide default delivery class at space creation IF it is not already set (SPEC §4: * `defaults.deliveryClass` MUST be on the wire so the effective default is discoverable, never * inferred from the `?? "durable"` resolution fallback). Clobber-safe and idempotent: an explicit * value already in the registry (e.g. seeded from a `channels.json` default) wins, so a re-up never * overrides an operator's choice. Returns true if it wrote. Called by `cotal up` with the profile * class — local/self-hosted (auth, daemon present) ⇒ `durable`, open/dev (no daemon) ⇒ `live`. */ export declare function ensureDefaultDeliveryClass(opts: { servers: string; space: string; creds?: string; deliveryClass: DeliveryClass; }): Promise; /** Connect (privileged/open), delete the given channel-registry keys, disconnect. Used by * `cotal down -f` to remove ONLY the cards a `spawn -f` run created (ownership-scoped); the caller is * responsible for the members-present safety check. The bucket must already exist (no create on a * delete path); a key that's already absent is a no-op. The space-wide defaults key is never a * channel name, so it can't be removed here. */ export declare function deleteChannels(opts: { servers: string; space: string; creds?: string; /** User mode: a `channel-writer`-view bearer + the space's sentinel creds (instead of a creds file). */ bearer?: string; sentinelCreds?: string; channels: string[]; }): Promise; /** Connect, read the whole registry (defaults + every channel entry) into a * {@link ChannelRegistryFile}, disconnect. The read side of {@link seedChannelRegistry}, * used by `cotal channels list`. */ export declare function readChannelRegistry(opts: { servers: string; space: string; creds?: string; /** User mode: the caller's OWN agent-view bearer + the space's sentinel creds — the registry is * world-readable in-space, so no elevated view is needed for the read side. */ bearer?: string; sentinelCreds?: string; }): Promise; //# sourceMappingURL=channels.d.ts.map