repos_status.ts

Zod schemas for the repos status --json document, the report the Rust repos tool (crates/fuz_repos) prints, and the error document it prints in place of the report on a fatal error.

The schemas mirror the Rust types by hand, each named as its Rust type prefixed Repos (EntryStatus is ReposEntryStatus), with fields as serde writes them: snake_case, a tagged enum as an object whose kind names its variant, an Option as null (never omitted), counts as integers, and times as unix seconds. A flattened enum's kind and payload sit beside its struct's own fields, so those structs are unions here (ReposUnregisteredClone, ReposStatusErrorBody) — or, for an enum with no payloads, an object whose kind is an enum (ReposProbeError). Where a Rust enum holds variants the status document never carries, the mirror leaves them out: ReposFetchFailure has no push rejection, and ReposStatusErrorBody holds only the errors repos status --json can print.

Every object is strict and every union closed, so a field or variant the mirror doesn't know fails the parse. The Rust side bumps version on any change to the document's shape; a consumer checks it first, and on a mismatch reports both versions and how to install the binary this repo builds (cargo install --path crates/fuz_repos --locked) rather than a parse error.

Drift is caught by the golden fixtures: a Rust test writes every status document shape to src/test/fixtures/repos_status/, covering every variant the status report and its error document can hold, and a TS test parses each with these schemas. The field semantics live in the Rust rustdoc and the JSON contract in docs/repos.md. The repos sync --json and repos push --json documents have no TS consumer and aren't mirrored here.

view source

Declarations
#

52 declarations

REPOS_STATUS_FORMAT_VERSION
#

repos_status.ts view source

18 import {REPOS_STATUS_FORMAT_VERSION} from '@fuzdev/fuz_repos/repos_status.js';

The repos status --json document's format version, Rust's STATUS_FORMAT_VERSION: the one these schemas parse.

ReposAtRest
#

repos_status.ts view source

value + type

{ on_branch: boolean | null; clean: boolean; idle: boolean; followed: { kind: "in_sync"; } | { kind: "ahead"; commits: number; } | { kind: "behind"; commits: number; } | { kind: "diverged"; ahead: number; behind: number; } | ... 4 more ... | null; } import {ReposAtRest} from '@fuzdev/fuz_repos/repos_status.js';

Whether an entry's primary checkout sits where the registry puts it.

on_branch

type boolean | null

clean

type boolean

idle

type boolean

followed

type { kind: "in_sync"; } | { kind: "ahead"; commits: number; } | { kind: "behind"; commits: number; } | { kind: "diverged"; ahead: number; behind: number; } | { kind: "shallow"; } | { kind: "gone"; } | { kind: "unmapped"; } | { kind: "untracked"; } | null

ReposBranchHold
#

repos_status.ts view source

value + type

"entry" | "pinned" | "push_url" | "fetch_failed" | "dirty_checkout" | "unprobed_worktree" | "several_checkouts" | "busy" | "busy_unknown"

type "entry" | "pinned" | "push_url" | "fetch_failed" | "dirty_checkout" | "unprobed_worktree" | "several_checkouts" | "busy" | "busy_unknown"

import {ReposBranchHold} from '@fuzdev/fuz_repos/repos_status.js';

What holds a branch's action back.

ReposBranchNeedsHuman
#

repos_status.ts view source

value + type

"diverged" | "unmapped" | "archived_ahead" | "shallow_local_work" | "upstream_not_a_branch"

type "diverged" | "unmapped" | "archived_ahead" | "shallow_local_work" | "upstream_not_a_branch"

import {ReposBranchNeedsHuman} from '@fuzdev/fuz_repos/repos_status.js';

Why a branch is left to a person.

ReposBranchStatus
#

repos_status.ts view source

value + type

{ name: string; upstream: string | null; worktree: string | null; symref: string | null; unique_commits: number; newest_commit_at: number; relation: { kind: "in_sync"; } | { kind: "ahead"; commits: number; } | ... 5 more ... | { ...; }; verdict: { ...; } | ... 4 more ... | { ...; }; } import {ReposBranchStatus} from '@fuzdev/fuz_repos/repos_status.js';

One local branch and its verdict.

name

type string

upstream

type string | null

worktree

type string | null

symref

type string | null

unique_commits

type number

newest_commit_at

type number

relation

type ReposRelation

verdict

type ReposVerdict

ReposCheckout
#

repos_status.ts view source

value + type

{ path: string; primary: boolean; head: { kind: "branch"; name: string; } | { kind: "detached"; commit: string; }; uncommitted: { staged: number; unstaged: number; untracked: number; conflicted: number; }; ... 4 more ...; busy: { ...; }[]; } import {ReposCheckout} from '@fuzdev/fuz_repos/repos_status.js';

One checkout of a repo: its primary, or a linked worktree probed.

path

type string

primary

type boolean

head

type ReposHead

uncommitted

type ReposUncommitted

in_progress

type "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am" | null

locked

type boolean

linked

type boolean

submodules

type boolean | null

busy

type ReposSession[]

ReposCheckoutList
#

repos_status.ts view source

value + type

"requires" | "consults"

type "requires" | "consults"

import {ReposCheckoutList} from '@fuzdev/fuz_repos/repos_status.js';

A repo's list of the sibling checkouts it uses.

ReposCleanupReason
#

repos_status.ts view source

value + type

"merged" | "upstream_gone"

type "merged" | "upstream_gone"

import {ReposCleanupReason} from '@fuzdev/fuz_repos/repos_status.js';

Why a branch reads as cleanup.

ReposCloneHold
#

repos_status.ts view source

value + type

"entry" | "unprobed_worktree" | "busy"

type "entry" | "unprobed_worktree" | "busy"

import {ReposCloneHold} from '@fuzdev/fuz_repos/repos_status.js';

What holds a missing entry's clone back.

ReposCloneRecipe
#

repos_status.ts view source

value + type

{ url: string; branch: string | null; shallow: boolean; sparse: string | null; } import {ReposCloneRecipe} from '@fuzdev/fuz_repos/repos_status.js';

How sync would clone a missing entry.

url

type string

branch

type string | null

shallow

type boolean

sparse

type string | null

ReposCloneVerdict
#

repos_status.ts view source

value + type

{ kind: "act"; recipe: { url: string; branch: string | null; shallow: boolean; sparse: string | null; }; } | { kind: "held"; recipe: { url: string; branch: string | null; shallow: boolean; sparse: string | null; }; by: "entry" | ... 1 more ... | "busy"; }

type { kind: "act"; recipe: { url: string; branch: string | null; shallow: boolean; sparse: string | null; }; } | { kind: "held"; recipe: { url: string; branch: string | null; shallow: boolean; sparse: string | null; }; by: "entry" | "unprobed_worktree" | "busy"; }

import {ReposCloneVerdict} from '@fuzdev/fuz_repos/repos_status.js';

What sync does about a missing entry: clone it, or why not yet.

ReposEntryKind
#

repos_status.ts view source

value + type

"repo" | "reference"

type "repo" | "reference"

import {ReposEntryKind} from '@fuzdev/fuz_repos/repos_status.js';

Which registry table an entry comes from.

ReposEntryName
#

repos_status.ts view source

value + type

{ kind: "repo" | "reference"; key: string; } import {ReposEntryName} from '@fuzdev/fuz_repos/repos_status.js';

An entry by table and key.

kind

type "repo" | "reference"

key

type string

ReposEntryStatus
#

repos_status.ts view source

value + type

{ key: string; kind: "repo" | "reference"; dir: string; url: string; writable: boolean; archived: boolean; visibility: "public" | "private" | null; ci: boolean; branch: string | null; pinned: boolean; ... 13 more ...; visibility_check: { ...; } | ... 2 more ... | null; } import {ReposEntryStatus} from '@fuzdev/fuz_repos/repos_status.js';

One registry entry's state.

key

type string

kind

type "repo" | "reference"

dir

type string

url

type string

writable

type boolean

archived

type boolean

visibility

type "public" | "private" | null

ci

type boolean

branch

type string | null

pinned

type boolean

refresh

type { kind: "act"; } | { kind: "held"; by: "entry" | "pinned" | "origin_not_https"; } | null

presence

type ReposPresence

clone

type { kind: "act"; recipe: { url: string; branch: string | null; shallow: boolean; sparse: string | null; }; } | { kind: "held"; recipe: { url: string; branch: string | null; shallow: boolean; sparse: string | null; }; by: "entry" | "unprobed_worktree" | "busy"; } | null

layout

type ReposLayout | null

checkouts

type ReposCheckout[]

branches

type ReposBranchStatus[]

at_rest

type ReposAtRest | null

stashes

type number

fetched_at

type number | null

needs_human

type ReposNeedsHuman[]

probe_error

type ReposProbeError | null

unprobed_worktrees

type ReposUnprobedWorktreeStatus[]

fetch_error

type { kind: "ref_gone"; refname: string; fix: { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }; } | { kind: "unreachable"; cause: "dns" | "connection" | "host_key" | "auth"; message: string; } | { kind: "repo_not_found"; message: string; } | { kind: "timed_out"; after_secs: number; } | { kind: "failed"; message: string; } | { kind: "refspec_outside_origin"; refspec: string; } | { kind: "origin_refs_shared"; remote: string; refspec: string; } | { kind: "legacy_remotes_unreadable"; path: string; } | null

visibility_check

type { kind: "leak"; } | { kind: "private"; } | { kind: "unknown"; failure: { kind: "ref_gone"; refname: string; fix: { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }; } | { kind: "unreachable"; cause: "dns" | "connection" | "host_key" | "auth"; message: string; } | { kind: "repo_not_found"; message: string; } | { kind: "timed_out"; after_secs: number; } | { kind: "failed"; message: string; } | { kind: "refspec_outside_origin"; refspec: string; } | { kind: "origin_refs_shared"; remote: string; refspec: string; } | { kind: "legacy_remotes_unreadable"; path: string; }; } | null

ReposFetchFailure
#

repos_status.ts view source

value + type

{ kind: "ref_gone"; refname: string; fix: { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }; } | { kind: "unreachable"; cause: "dns" | ... 2 more ... | "auth"; message: string; } | ... 5 more ... | { ...; }

type { kind: "ref_gone"; refname: string; fix: { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }; } | { kind: "unreachable"; cause: "dns" | "connection" | "host_key" | "auth"; message: string; } | { kind: "repo_not_found"; message: string; } | { kind: "timed_out"; after_secs: number; } | { kind: "failed"; message: string; } | { kind: "refspec_outside_origin"; refspec: string; } | { kind: "origin_refs_shared"; remote: string; refspec: string; } | { kind: "legacy_remotes_unreadable"; path: string; }

import {ReposFetchFailure} from '@fuzdev/fuz_repos/repos_status.js';

Why a fetch or the visibility check failed, or why the tool refused to fetch: Rust's RemoteFailure without rejected, which only a push meets.

ReposGitDirHolds
#

repos_status.ts view source

value + type

{ submodules: boolean; worktree_refs: boolean; staged: boolean | null; } import {ReposGitDirHolds} from '@fuzdev/fuz_repos/repos_status.js';

What an unprobed worktree's git dir holds that a prune would lose.

submodules

type boolean

worktree_refs

type boolean

staged

type boolean | null

ReposHead
#

repos_status.ts view source

value + type

{ kind: "branch"; name: string; } | { kind: "detached"; commit: string; }

type { kind: "branch"; name: string; } | { kind: "detached"; commit: string; }

import {ReposHead} from '@fuzdev/fuz_repos/repos_status.js';

A checkout's HEAD: a probed checkout's, an unprobed worktree's, or an unlisted git dir's — the last two null when it can't be read.

ReposInProgressOp
#

repos_status.ts view source

value + type

"rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"

type "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"

import {ReposInProgressOp} from '@fuzdev/fuz_repos/repos_status.js';

A git operation in progress.

ReposLayout
#

repos_status.ts view source

value + type

{ shallow: boolean; sparse: boolean; partial_filter: string | null; } import {ReposLayout} from '@fuzdev/fuz_repos/repos_status.js';

A clone's shape: shallow, sparse, or partial.

shallow

type boolean

sparse

type boolean

partial_filter

type string | null

ReposNeedsHuman
#

repos_status.ts view source

value + type

{ kind: "not_a_repo"; detail: string; } | { kind: "operation_in_progress"; checkout: string; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "origin_mismatch"; origin: { ...; } | ... 1 more ... | { ...; }; expected: string; fix: { ...; } | ... 1 more ... | { ...; }; } |...

type { kind: "not_a_repo"; detail: string; } | { kind: "operation_in_progress"; checkout: string; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "origin_mismatch"; origin: { kind: "url"; url: string; } | { kind: "no_url"; } | { kind: "missing"; }; expected: string; fix: { kind: "add"; } | { kind: "set_url"; } | { kind: "by_hand"; reason: "outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"; }; } | { kind: "origin_not_https"; fetch_url: string; expected: string; fix: { kind: "add"; } | { kind: "set_url"; } | { kind: "by_hand"; reason: "outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"; } | null; } | { kind: "fetch_url_mismatch"; fetch_url: string; expected: string; fix: { kind: "add"; } | { kind: "set_url"; } | { kind: "by_hand"; reason: "outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"; } | null; } | { kind: "worktree_unreadable"; path: string; } | { kind: "default_branch_missing"; branch: string; } | { kind: "default_branch_no_upstream"; branch: string; } | { kind: "default_branch_gone"; branch: string; } | { kind: "unexpected_detached"; checkout: string; } | { kind: "checkout_unresolvable"; checkout: string; path: string; error: string; } | { kind: "unlisted_git_dir"; git_dir: string; head: { kind: "branch"; name: string; } | { kind: "detached"; commit: string; } | null; busy: { pid: number; cwd: string; worktree: string | null; process_cwd: string | null; source: "session_file" | "roster_worker"; }[]; } | { kind: "push_url_mismatch"; push_urls: string[]; expected: string; } | { kind: "clone_shares_repo"; with: string; } | { kind: "cloned_unregistered"; dir: string; }

import {ReposNeedsHuman} from '@fuzdev/fuz_repos/repos_status.js';

Why sync would stop on an entry and leave it to a person.

ReposOriginByHand
#

repos_status.ts view source

value + type

"outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"

type "outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"

import {ReposOriginByHand} from '@fuzdev/fuz_repos/repos_status.js';

Why no git remote command fits an origin's fix.

ReposOriginFix
#

repos_status.ts view source

value + type

{ kind: "add"; } | { kind: "set_url"; } | { kind: "by_hand"; reason: "outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"; }

type { kind: "add"; } | { kind: "set_url"; } | { kind: "by_hand"; reason: "outside_repo_file" | "valueless_url" | "empty_value" | "several_urls"; }

import {ReposOriginFix} from '@fuzdev/fuz_repos/repos_status.js';

How to point origin at the registry's URL.

ReposOriginRemote
#

repos_status.ts view source

value + type

{ kind: "url"; url: string; } | { kind: "no_url"; } | { kind: "missing"; }

type { kind: "url"; url: string; } | { kind: "no_url"; } | { kind: "missing"; }

import {ReposOriginRemote} from '@fuzdev/fuz_repos/repos_status.js';

The origin remote as git sees it, when it isn't the registry's url.

ReposPresence
#

repos_status.ts view source

value + type

{ kind: "present"; } | { kind: "missing"; } | { kind: "not_a_repo"; }

type { kind: "present"; } | { kind: "missing"; } | { kind: "not_a_repo"; }

import {ReposPresence} from '@fuzdev/fuz_repos/repos_status.js';

Whether a repo is at the entry's dir.

ReposProbeError
#

repos_status.ts view source

value + type

{ kind: "path_unreadable" | "non_utf8_path" | "config_unreadable" | "fetch_url_unreadable" | "push_urls_unreadable" | "git_not_run" | "git_timed_out" | "git_failed" | "unexpected_output"; message: string; } import {ReposProbeError} from '@fuzdev/fuz_repos/repos_status.js';

Why an entry's probe failed: its kind, and a message for display.

kind

type "path_unreadable" | "non_utf8_path" | "config_unreadable" | "fetch_url_unreadable" | "push_urls_unreadable" | "git_not_run" | "git_timed_out" | "git_failed" | "unexpected_output"

message

type string

ReposProbeErrorKind
#

repos_status.ts view source

value + type

"path_unreadable" | "non_utf8_path" | "config_unreadable" | "fetch_url_unreadable" | "push_urls_unreadable" | "git_not_run" | "git_timed_out" | "git_failed" | "unexpected_output"

type "path_unreadable" | "non_utf8_path" | "config_unreadable" | "fetch_url_unreadable" | "push_urls_unreadable" | "git_not_run" | "git_timed_out" | "git_failed" | "unexpected_output"

import {ReposProbeErrorKind} from '@fuzdev/fuz_repos/repos_status.js';

What kind of failure stopped an entry's probe.

ReposPrune
#

repos_status.ts view source

value + type

{ kind: "safe"; } | { kind: "loses"; losses: ({ kind: "operation"; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "detached_head"; } | { kind: "unknown_head"; } | ... 5 more ... | { ...; })[]; } | { ...; }

type { kind: "safe"; } | { kind: "loses"; losses: ({ kind: "operation"; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "detached_head"; } | { kind: "unknown_head"; } | { kind: "missing_branch"; name: string; } | { kind: "submodules"; } | { kind: "worktree_refs"; } | { kind: "staged_changes"; } | { kind: "unmatched_git_dir"; } | { kind: "relative_gitdir"; git_dir: string; })[]; } | { kind: "moved"; to: string[]; }

import {ReposPrune} from '@fuzdev/fuz_repos/repos_status.js';

Whether pruning an unprobed worktree is safe.

ReposPruneLoss
#

repos_status.ts view source

value + type

{ kind: "operation"; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "detached_head"; } | { kind: "unknown_head"; } | { kind: "missing_branch"; name: string; } | ... 4 more ... | { ...; }

type { kind: "operation"; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "detached_head"; } | { kind: "unknown_head"; } | { kind: "missing_branch"; name: string; } | { kind: "submodules"; } | { kind: "worktree_refs"; } | { kind: "staged_changes"; } | { kind: "unmatched_git_dir"; } | { kind: "relative_gitdir"; git_dir: string; }

import {ReposPruneLoss} from '@fuzdev/fuz_repos/repos_status.js';

What pruning an unprobed worktree would lose.

ReposRefGoneFix
#

repos_status.ts view source

value + type

{ kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }

type { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }

import {ReposRefGoneFix} from '@fuzdev/fuz_repos/repos_status.js';

How to repair a fetch refspec naming a ref gone from origin.

ReposRefreshHold
#

repos_status.ts view source

value + type

"entry" | "pinned" | "origin_not_https"

type "entry" | "pinned" | "origin_not_https"

import {ReposRefreshHold} from '@fuzdev/fuz_repos/repos_status.js';

What holds a reference's refresh back.

ReposRefreshVerdict
#

repos_status.ts view source

value + type

{ kind: "act"; } | { kind: "held"; by: "entry" | "pinned" | "origin_not_https"; }

type { kind: "act"; } | { kind: "held"; by: "entry" | "pinned" | "origin_not_https"; }

import {ReposRefreshVerdict} from '@fuzdev/fuz_repos/repos_status.js';

What a run does about refreshing a third-party reference or a pin.

ReposRegistryIssue
#

repos_status.ts view source

value + type

{ kind: "repo_not_owned"; key: string; account: string; } | { kind: "fork_not_owned"; key: string; } | { kind: "dir_not_a_name"; entry: { kind: "repo" | "reference"; key: string; }; dir: string; } | ... 5 more ... | { ...; }

type { kind: "repo_not_owned"; key: string; account: string; } | { kind: "fork_not_owned"; key: string; } | { kind: "dir_not_a_name"; entry: { kind: "repo" | "reference"; key: string; }; dir: string; } | { kind: "dir_claimed_twice"; dir: string; first: { kind: "repo" | "reference"; key: string; }; second: { kind: "repo" | "reference"; key: string; }; } | { kind: "key_in_both"; key: string; } | { kind: "key_is_other_dir"; key: string; entry: { kind: "repo" | "reference"; key: string; }; } | { kind: "unknown_checkout_ref"; key: string; field: "requires" | "consults"; target: string; } | { kind: "self_ref"; key: string; field: "requires" | "consults"; } | { kind: "requires_and_consults"; key: string; target: string; }

import {ReposRegistryIssue} from '@fuzdev/fuz_repos/repos_status.js';

A registry integrity rule broken.

ReposRelation
#

repos_status.ts view source

value + type

{ kind: "in_sync"; } | { kind: "ahead"; commits: number; } | { kind: "behind"; commits: number; } | { kind: "diverged"; ahead: number; behind: number; } | { kind: "shallow"; } | { kind: "gone"; } | { kind: "unmapped"; } | { ...; }

type { kind: "in_sync"; } | { kind: "ahead"; commits: number; } | { kind: "behind"; commits: number; } | { kind: "diverged"; ahead: number; behind: number; } | { kind: "shallow"; } | { kind: "gone"; } | { kind: "unmapped"; } | { kind: "untracked"; }

import {ReposRelation} from '@fuzdev/fuz_repos/repos_status.js';

A branch's relation to its upstream.

ReposRepairBlock
#

repos_status.ts view source

value + type

{ kind: "rewrites"; path: string; git_dir: string; } | { kind: "claimed_dir"; git_dir: string; } | { kind: "swapped"; git_dir: string; with: string; } | { kind: "relative_gitdir"; git_dir: string; } | { ...; } | { ...; } | { ...; }

type { kind: "rewrites"; path: string; git_dir: string; } | { kind: "claimed_dir"; git_dir: string; } | { kind: "swapped"; git_dir: string; with: string; } | { kind: "relative_gitdir"; git_dir: string; } | { kind: "unreadable_gitdir"; git_dir: string; } | { kind: "non_utf8_path"; } | { kind: "nul_in_gitdir"; git_dir: string; }

import {ReposRepairBlock} from '@fuzdev/fuz_repos/repos_status.js';

What keeps a moved worktree's repair from being offered.

ReposSession
#

repos_status.ts view source

value + type

{ pid: number; cwd: string; worktree: string | null; process_cwd: string | null; source: "session_file" | "roster_worker"; } import {ReposSession} from '@fuzdev/fuz_repos/repos_status.js';

A live Claude Code session: its process, and where it works.

pid

type number

cwd

type string

worktree

type string | null

process_cwd

type string | null

source

type "session_file" | "roster_worker"

ReposSessions
#

repos_status.ts view source

value + type

{ kind: "available"; unscoped: { pid: number; cwd: string; worktree: string | null; process_cwd: string | null; source: "session_file" | "roster_worker"; }[]; } | { kind: "unavailable"; reason: { ...; } | ... 3 more ... | { ...; }; }

type { kind: "available"; unscoped: { pid: number; cwd: string; worktree: string | null; process_cwd: string | null; source: "session_file" | "roster_worker"; }[]; } | { kind: "unavailable"; reason: { kind: "home_unknown"; } | { kind: "relative_config_dir"; path: string; } | { kind: "unreadable"; path: string; error: string; } | { kind: "unparseable"; path: string; error: string; } | { kind: "foreign_pid_domain"; path: string; pid_domain: string; source: "session_file" | "roster_worker"; }; }

import {ReposSessions} from '@fuzdev/fuz_repos/repos_status.js';

Busy detection as the report carries it.

ReposSessionSource
#

repos_status.ts view source

value + type

"session_file" | "roster_worker"

type "session_file" | "roster_worker"

import {ReposSessionSource} from '@fuzdev/fuz_repos/repos_status.js';

Where a live Claude Code session was recorded.

ReposStatusDocument
#

repos_status.ts view source

value + type

{ version: 18; workspace: string; registry: string; fetched: boolean; sessions: { kind: "available"; unscoped: { pid: number; cwd: string; worktree: string | null; process_cwd: string | null; source: "session_file" | "roster_worker"; }[]; } | { ...; }; entries: { ...; }[]; unregistered: ({ ...; } | ... 4 more ... | ...

type ReposStatusReport | ReposStatusErrorReport

import {ReposStatusDocument} from '@fuzdev/fuz_repos/repos_status.js';

Either document repos status --json prints. No tag is needed: error is the error document's alone, and each side's strictness refuses the other's fields. A consumer wanting a sharper parse error branches on error first and parses with that side's schema.

ReposStatusErrorBody
#

repos_status.ts view source

value + type

{ kind: "references_with_targets"; message: string; hint: string | null; } | { kind: "root_not_found"; message: string; hint: string | null; } | { kind: "registry_not_found"; message: string; hint: string | null; } | ... 7 more ... | { ...; }

type { kind: "references_with_targets"; message: string; hint: string | null; } | { kind: "root_not_found"; message: string; hint: string | null; } | { kind: "registry_not_found"; message: string; hint: string | null; } | { kind: "root_in_entry"; key: string; message: string; hint: string | null; } | { kind: "registry_read"; message: string; hint: string | null; } | { kind: "registry_parse"; message: string; hint: string | null; } | { kind: "registry_invalid"; issues: ({ kind: "repo_not_owned"; key: string; account: string; } | { kind: "fork_not_owned"; key: string; } | { kind: "dir_not_a_name"; entry: { kind: "repo" | "reference"; key: string; }; dir: string; } | { kind: "dir_claimed_twice"; dir: string; first: { kind: "repo" | "reference"; key: string; }; second: { kind: "repo" | "reference"; key: string; }; } | { kind: "key_in_both"; key: string; } | { kind: "key_is_other_dir"; key: string; entry: { kind: "repo" | "reference"; key: string; }; } | { kind: "unknown_checkout_ref"; key: string; field: "requires" | "consults"; target: string; } | { kind: "self_ref"; key: string; field: "requires" | "consults"; } | { kind: "requires_and_consults"; key: string; target: string; })[]; message: string; hint: string | null; } | { kind: "git_not_found"; message: string; hint: string | null; } | { kind: "git_too_old"; found: string; required: string; message: string; hint: string | null; } | { kind: "unknown_entry"; name: string; suggestions: string[]; message: string; hint: string | null; } | { kind: "io"; message: string; hint: string | null; }

import {ReposStatusErrorBody} from '@fuzdev/fuz_repos/repos_status.js';

A fatal error as repos status --json prints it, its kind flattened beside message and hint. Only the kinds status can print: the rest of Rust's ErrorKind are repos push's, or precede knowing --json.

ReposStatusErrorReport
#

repos_status.ts view source

value + type

{ version: 18; error: { kind: "references_with_targets"; message: string; hint: string | null; } | { kind: "root_not_found"; message: string; hint: string | null; } | { kind: "registry_not_found"; message: string; hint: string | null; } | ... 7 more ... | { ...; }; } import {ReposStatusErrorReport} from '@fuzdev/fuz_repos/repos_status.js';

The document repos status --json prints on a fatal error, in place of the report.

version

type 18

error

type ReposStatusErrorBody

ReposStatusReport
#

repos_status.ts view source

value + type

{ version: 18; workspace: string; registry: string; fetched: boolean; sessions: { kind: "available"; unscoped: { pid: number; cwd: string; worktree: string | null; process_cwd: string | null; source: "session_file" | "roster_worker"; }[]; } | { ...; }; entries: { ...; }[]; unregistered: ({ ...; } | ... 4 more ... | ... import {ReposStatusReport} from '@fuzdev/fuz_repos/repos_status.js';

The repos status --json report.

version

type 18

workspace

type string

registry

type string

fetched

type boolean

sessions

type ReposSessions

entries

type ReposEntryStatus[]

unregistered

type ReposUnregisteredClone[] | null

ReposSyncAction
#

repos_status.ts view source

value + type

{ kind: "push"; commits: number; } | { kind: "fast_forward"; commits: number; } | { kind: "move"; }

type { kind: "push"; commits: number; } | { kind: "fast_forward"; commits: number; } | { kind: "move"; }

import {ReposSyncAction} from '@fuzdev/fuz_repos/repos_status.js';

A sync action on a branch.

ReposUnavailable
#

repos_status.ts view source

value + type

{ kind: "home_unknown"; } | { kind: "relative_config_dir"; path: string; } | { kind: "unreadable"; path: string; error: string; } | { kind: "unparseable"; path: string; error: string; } | { kind: "foreign_pid_domain"; path: string; pid_domain: string; source: "session_file" | "roster_worker"; }

type { kind: "home_unknown"; } | { kind: "relative_config_dir"; path: string; } | { kind: "unreadable"; path: string; error: string; } | { kind: "unparseable"; path: string; error: string; } | { kind: "foreign_pid_domain"; path: string; pid_domain: string; source: "session_file" | "roster_worker"; }

import {ReposUnavailable} from '@fuzdev/fuz_repos/repos_status.js';

Why busy detection can't vouch for every live session.

ReposUncommitted
#

repos_status.ts view source

value + type

{ staged: number; unstaged: number; untracked: number; conflicted: number; } import {ReposUncommitted} from '@fuzdev/fuz_repos/repos_status.js';

A checkout's uncommitted work, by kind.

staged

type number

unstaged

type number

untracked

type number

conflicted

type number

ReposUnprobedWhy
#

repos_status.ts view source

value + type

{ kind: "prunable"; } | { kind: "missing"; } | { kind: "failed"; error: string; }

type { kind: "prunable"; } | { kind: "missing"; } | { kind: "failed"; error: string; }

import {ReposUnprobedWhy} from '@fuzdev/fuz_repos/repos_status.js';

Why a worktree wasn't probed.

ReposUnprobedWorktree
#

repos_status.ts view source

value + type

{ path: string; git_dir: string | null; head: { kind: "branch"; name: string; } | { kind: "detached"; commit: string; } | null; locked: boolean; in_progress: "rebase" | "merge" | "cherry_pick" | ... 4 more ... | null; why: { ...; } | ... 1 more ... | { ...; }; holds: { ...; } | null; } import {ReposUnprobedWorktree} from '@fuzdev/fuz_repos/repos_status.js';

A worktree of the repo that couldn't be probed.

path

type string

git_dir

type string | null

head

type { kind: "branch"; name: string; } | { kind: "detached"; commit: string; } | null

locked

type boolean

in_progress

type "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am" | null

why

type ReposUnprobedWhy

holds

type ReposGitDirHolds | null

ReposUnprobedWorktreeStatus
#

repos_status.ts view source

value + type

{ path: string; git_dir: string | null; head: { kind: "branch"; name: string; } | { kind: "detached"; commit: string; } | null; locked: boolean; in_progress: "rebase" | "merge" | "cherry_pick" | ... 4 more ... | null; why: { ...; } | ... 1 more ... | { ...; }; holds: { ...; } | null; prune: { ...; } | ... 2 more ...... import {ReposUnprobedWorktreeStatus} from '@fuzdev/fuz_repos/repos_status.js';

An unprobed worktree (flattened) with its prune verdict and live sessions.

path

type string

git_dir

type string | null

head

type { kind: "branch"; name: string; } | { kind: "detached"; commit: string; } | null

locked

type boolean

in_progress

type "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am" | null

why

type ReposUnprobedWhy

holds

type ReposGitDirHolds | null

prune

type { kind: "safe"; } | { kind: "loses"; losses: ({ kind: "operation"; op: "rebase" | "merge" | "cherry_pick" | "revert" | "bisect" | "sequencer" | "am"; } | { kind: "detached_head"; } | { kind: "unknown_head"; } | { kind: "missing_branch"; name: string; } | { kind: "submodules"; } | { kind: "worktree_refs"; } | { kind: "staged_changes"; } | { kind: "unmatched_git_dir"; } | { kind: "relative_gitdir"; git_dir: string; })[]; } | { kind: "moved"; to: string[]; } | null

busy

type ReposSession[]

ReposUnreachableCause
#

repos_status.ts view source

value + type

"dns" | "connection" | "host_key" | "auth"

type "dns" | "connection" | "host_key" | "auth"

import {ReposUnreachableCause} from '@fuzdev/fuz_repos/repos_status.js';

Why a remote couldn't be reached.

ReposUnregisteredClone
#

repos_status.ts view source

value + type

{ kind: "clone"; dir: string; origin: string | null; owned: boolean; } | { kind: "worktree"; dir: string; origin: string | null; owned: boolean; } | { kind: "moved_worktree"; entry: string; blocked_by: { ...; } | ... 6 more ... | null; exit_noise: string | null; dir: string; origin: string | null; owned: boolean; } ...

type { kind: "clone"; dir: string; origin: string | null; owned: boolean; } | { kind: "worktree"; dir: string; origin: string | null; owned: boolean; } | { kind: "moved_worktree"; entry: string; blocked_by: { kind: "rewrites"; path: string; git_dir: string; } | { kind: "claimed_dir"; git_dir: string; } | { kind: "swapped"; git_dir: string; with: string; } | { kind: "relative_gitdir"; git_dir: string; } | { kind: "unreadable_gitdir"; git_dir: string; } | { kind: "non_utf8_path"; } | { kind: "nul_in_gitdir"; git_dir: string; } | null; exit_noise: string | null; dir: string; origin: string | null; owned: boolean; } | { kind: "orphaned_worktree"; entry: string; dir: string; origin: string | null; owned: boolean; } | { kind: "shared_git_dir"; entry: string; with: string | null; dir: string; origin: string | null; owned: boolean; } | { kind: "unfinished_clone"; dir: string; origin: string | null; owned: boolean; }

import {ReposUnregisteredClone} from '@fuzdev/fuz_repos/repos_status.js';

A child of the workspace root holding a .git that no registry entry claims, its kind flattened beside its own fields.

ReposVerdict
#

repos_status.ts view source

value + type

{ kind: "quiet"; } | { kind: "act"; action: { kind: "push"; commits: number; } | { kind: "fast_forward"; commits: number; } | { kind: "move"; }; } | { kind: "held"; action: { kind: "push"; commits: number; } | { ...; } | { ...; }; by: "entry" | ... 7 more ... | "busy_unknown"; } | { ...; } | { ...; } | { ...; }

type { kind: "quiet"; } | { kind: "act"; action: { kind: "push"; commits: number; } | { kind: "fast_forward"; commits: number; } | { kind: "move"; }; } | { kind: "held"; action: { kind: "push"; commits: number; } | { kind: "fast_forward"; commits: number; } | { kind: "move"; }; by: "entry" | "pinned" | "push_url" | "fetch_failed" | "dirty_checkout" | "unprobed_worktree" | "several_checkouts" | "busy" | "busy_unknown"; } | { kind: "needs_human"; reason: "diverged" | "unmapped" | "archived_ahead" | "shallow_local_work" | "upstream_not_a_branch"; } | { kind: "local_only"; } | { kind: "cleanup"; reason: "merged" | "upstream_gone"; removable_worktree: string | null; }

import {ReposVerdict} from '@fuzdev/fuz_repos/repos_status.js';

What sync does about a branch.

ReposVisibility
#

repos_status.ts view source

value + type

"public" | "private"

type "public" | "private"

import {ReposVisibility} from '@fuzdev/fuz_repos/repos_status.js';

A repo's declared visibility on its host.

ReposVisibilityCheck
#

repos_status.ts view source

value + type

{ kind: "leak"; } | { kind: "private"; } | { kind: "unknown"; failure: { kind: "ref_gone"; refname: string; fix: { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { ...; }; } | ... 6 more ... | { ...; }; }

type { kind: "leak"; } | { kind: "private"; } | { kind: "unknown"; failure: { kind: "ref_gone"; refname: string; fix: { kind: "unset_refspec"; pattern: string; } | { kind: "set_branches"; branch: string | null; } | { kind: "by_hand"; }; } | { kind: "unreachable"; cause: "dns" | "connection" | "host_key" | "auth"; message: string; } | { kind: "repo_not_found"; message: string; } | { kind: "timed_out"; after_secs: number; } | { kind: "failed"; message: string; } | { kind: "refspec_outside_origin"; refspec: string; } | { kind: "origin_refs_shared"; remote: string; refspec: string; } | { kind: "legacy_remotes_unreadable"; path: string; }; }

import {ReposVisibilityCheck} from '@fuzdev/fuz_repos/repos_status.js';

What an anonymous read of a repo declared private found.

Imported by
#