1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
//! What:
//! The longest the wrapper waits for each thing it waits for without a person at the keyboard, with the measurement or the
//! decision beside each number.
//! Why:
//! The owner, 2026-11-03: "nothing should ever wait forever or indefinitely". Every wait on the commit path ends at one of these,
//! the request is withdrawn so it never lands later, the person's index and worktree stay as they were, and the command exits
//! non-zero naming the blocker (`doc/planning/cli-git-no-unbounded-waits.md`). The data was read on 2026-11-03 from this
//! repository's commit timing log (1,329 records) and the commit service's journal (1,335 landings).
//!
//! In TS you'd write (pseudocode):
//! ```ts
//! export const ANSWER_CEILING_MS = 20 * 60 * 1000;
//! ```
use Duration;
/// The longest a client waits for the commit service's answer to a request, heartbeats or not.
/// Measured: the longest answer wait in the timing log was 308,267 ms (99th percentile 50,344 ms) and the longest whole commit
/// 750,604 ms. Twenty minutes is 3.9 times the longest answer wait and 1.6 times the longest whole commit.
pub const ANSWER_CEILING: Duration = from_secs;
/// The longest a client waits for the service to start when it can ask the service manager how the start goes.
/// Measured: the slowest of 52 cold starts took 1,041 ms (`startWaitMs`, `reachMs`). One minute is 58 times that.
pub const START_CEILING: Duration = from_secs;
/// The longest a landing, a merge or an index reconciliation waits for a foreign program's `index.lock`.
/// Unmeasured: no log holds a wait behind a foreign holder (no `lock_looks` in the service journal, no waiting notice in the
/// timing log). Ten minutes is below `ANSWER_CEILING`, so the service ends its own wait and answers before the client gives up;
/// a person's `git commit` with its editor open for longer than this makes ours stop with the error.
pub const LOCK_CEILING: Duration = from_secs;
/// The longest a forwarded `git add`, `rm` or `mv` waits for the commit service's hold on the index, and the longest its whole
/// series of reruns lasts. Measured: the longest of 715 logged service holds was 119,721 ms (disk sync of the new index). Ten
/// minutes is five times that.
pub const SERVICE_HOLD_CEILING: Duration = from_secs;
/// The longest a client waits for the service to answer a withdrawal of its request. The service answers it as soon as the landing
/// it is in the middle of ends, which `LOCK_CEILING` and the step bounds limit; the number is the longest observed landing
/// (journal `landing_ms` 119,836 ms) with the same margin of five.
pub const WITHDRAW_CEILING: Duration = from_secs;
/// The longest a connected push may show no progress before it is ended and left to the service's retry plan.
/// Unmeasured, labelled as the other quiet windows are: no log holds a quiet gap of a connected push. It is twice the longest
/// whole push in the journal (72.4 s of 794 pushes), which includes the connected time.
pub const CONNECTED_PUSH_QUIET_WINDOW: Duration = from_secs;
/// The longest a test marker compiled into the release executable waits for its release file; the marker is armed only by an
/// environment variable. Five minutes is the longest any test may run (`.config/nextest.toml`: a test is stopped after
/// `slow-timeout` 60 s times `terminate-after` 5), so the marker never outlives the control that armed it.
pub const PHASE_PATIENCE: Duration = from_secs;
/// The longest a quick Git query step (`rev-parse`, `for-each-ref`, `cat-file`, `write-tree`, ...) runs before the wrapper ends it,
/// even while it shows signs of work. Measured: the longest read step of the service's landings was 9,663 ms (`reads_ms`, 1,651
/// landings); two minutes is 12 times that. It is below `ANSWER_CEILING`, so the service answers first.
pub const PLUMBING_STEP_CEILING: Duration = from_secs;
/// The longest a bulk Git step (`fast-import`, `add`, `reset`, the commit Git builds in a scratch repository, ...) runs before the
/// wrapper ends it, even while it shows signs of work. Measured: the longest client-side preparation of the timing log was
/// 250,280 ms (`prepareMs`, 1,400 records) and the longest build 183,296 ms; the service's object step took at most 1,358 ms
/// (`objects_ms`). Ten minutes is 2.4 times the longest preparation and below `ANSWER_CEILING`.
pub const OBJECT_STEP_CEILING: Duration = from_secs;
/// The longest a reference update (`update-ref`), the step that is not safe to run twice, runs before the wrapper ends it. Measured:
/// the longest of 1,651 reference updates took 3,438 ms (`ref_ms`); one minute is 17 times that. Git writes a reference by creating
/// its lock file and renaming it, so ending the step leaves either the old reference or the new one, and the lock file it may leave
/// is removed by the stale-lock sweep once the process is gone.
pub const REFERENCE_STEP_CEILING: Duration = from_secs;