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
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
//! Pluggable lifecycle hooks (requirement: "exit probes / heartbeats are
//! optional, hookable — use the default, or supply your own").
//!
//! Every default facility in the `malkuth` crate (signal-based exit, HTTP
//! probes, timed heartbeats) is wired through one of these traits. If the
//! default does not fit — e.g. you want drain to be triggered when your server
//! receives an application-level "stop" command, or you want heartbeats to
//! carry your own payload — implement the trait and hand it to the supervisor.
//! Nothing here depends on a runtime or a wire framework.
use Duration;
use async_trait;
use crate::;
/// Why an [`ExitSource`] fired.
/// Source of process-exit / drain triggers.
///
/// The default implementation (in the `malkuth` crate) installs OS signal
/// handlers (`SIGTERM`/`SIGINT`/`SIGHUP`/`SIGQUIT`). A custom implementation
/// might instead trigger drain when the server receives an in-band "stop"
/// command, when a parent supervisor sends a control message over IPC, or when
/// an orchestrator flips a file bit.
///
/// Implementations **must** call `ctrl.begin_drain(reason.kind)` (and arrange
/// process exit if `reason.should_exit`) when their condition fires.
/// Readiness/liveness state as observed by probes (HTTP `/readyz` or RPC
/// `Lifecycle.Status`). Implementations decide *how* the state is computed
/// (read atomics, ping a dependency, query a registry, …).
/// Heartbeat report produced by a [`Heartbeat`] source.
/// A periodic liveness heartbeat. The default implementation emits a beat on a
/// fixed cadence; a custom one can embed domain-specific state, rate-limit, or
/// suppress beats conditionally.
/// A drain hook: run arbitrary graceful-shutdown work when drain begins.
///
/// Wired in by the supervisor between "stop accepting new work" and "exit".
/// Examples: close WebSocket frames, flush buffers, disconnect upstream pools,
/// release locks. This is the seam where each application injects its own
/// drain closure (the design doc §5.3 step 3–6).