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
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
//! **Retention** — the one policy that turns a released candidate into a
//! discarded one (VISION §4.10 items 4 and 6; DESIGN §3.8).
//!
//! §4.10 item 6, verbatim: *"Losers stay inspectable until yog's retention
//! policy (world config, severable) asks balls to clean them."* This is that
//! policy, and it is an entry in the file yog's clock already owns — a sibling
//! of `cadence:`, `fleet:` and the monitor's block, a row rather than a
//! rebuild:
//!
//! ```text
//! retention:
//! /home/u/dev/yog:
//! keep_min: 1440
//! ```
//!
//! **Absence is never discard**, and that default is deliberate for exactly the
//! reason the armed loop's `lease_min` is absent by default
//! ([`crate::fleet::arming`]: *"a reap releases a claim and yog must not do that
//! on an opinion"*). Deleting a source ref destroys the only remaining record of
//! a rejected candidate — balls itself never sweeps attempts — so yog will not
//! do it on a default it invented. **Severability is deleting the entry**: what
//! goes is config, never code.
//!
//! The entry key is the **project** path, not a workspace: retention is about
//! refs in a project repo, and every workspace that fans that project is
//! spending the same ref namespace.
use Path;
use ;
use attempt_branch;
use crateentry_field;
/// The column-0 block key, beside [`fleet`](crate::fleet::arming::BLOCK).
pub const BLOCK: &str = "retention";
/// How long a candidate's source ref is kept, in whole minutes.
pub const KEEP_MIN: &str = "keep_min";
/// How long this project keeps a candidate's source ref. `None` — the default,
/// and the answer for every project with no entry — keeps it forever.
/// Whether a candidate of this `age` has outlived `keep`. An undeclared
/// retention never expires, and an unreadable age
/// ([`age`] answering `None`) never expires either — yog discards on a fact or
/// not at all.
/// How long ago this candidate's source ref last moved — the committer time of
/// `attempt/<handle>`'s tip, against `now`. The ref name is balls'
/// ([`attempt_branch`]), never a literal here.
///
/// `None` when the ref does not resolve, when git will not run, or when the tip
/// is in the future (an unusable clock): in each the caller keeps the ref, which
/// is the standing default.