zz_

app/cli/lib/watchedRepos.ts

zzmq.dev@gmail.com/zz / app / cli / lib / watchedRepos.ts @ 5e5720fb Download
Ladder Summary
  • file This module implements a tiny external store that tracks the set of repositories a running **`zz work`** session is watching. It exports the **`RepoWatchStore`** interface (exposing `get()`, `add(repo)` and `subscribe(listener)`) and a factory function **`createRepoWatchStore(initial)`** that creates such a store, managing an internal array of `ResolvedRepo`s and a set of listeners that are notified whenever a new repo is added. The store can be used both by non‑React code (e.g., the main loop) and by React components via `useSyncExternalStore`.
// A small external store over the set of repos a running `zz work`
// session is watching -- lets a shard discovered mid-session (see
// agent/scriptedWork.ts's runContributorWorkAsk) reach both the TUI
// (via React's useSyncExternalStore) and mainLoop's own polling
// without restarting the process. Deliberately not React-specific
// itself: mainLoop (a plain async function, not a component) reads
// it directly via get(), the TUI subscribes via subscribe()/get().
import type { ResolvedRepo } from "./repo.js";

export interface RepoWatchStore {
  get(): ResolvedRepo[];
  /** No-op if a repo with this slug is already watched -- this is also what makes a shard only ever added once per session, regardless of how many asks reference it. */
  add(repo: ResolvedRepo): void;
  subscribe(listener: () => void): () => void;
}

export function createRepoWatchStore(initial: ResolvedRepo[]): RepoWatchStore {
  let repos = initial;
  const listeners = new Set<() => void>();
  return {
    get: () => repos,
    add(repo) {
      if (repos.some((r) => r.slug === repo.slug)) return;
      repos = [...repos, repo];
      for (const listener of listeners) listener();
    },
    subscribe(listener) {
      listeners.add(listener);
      return () => listeners.delete(listener);
    },
  };
}