pub struct RuleSet<'a> { /* private fields */ }decode only.Expand description
A set of rules judged tick by tick over one event stream — the
watchdog’s per-tick body, lifted out of watchdog so a second driver
can run it (#218).
The driver owns the stream, the drain loop and the sweep; this owns
everything the rules know: per-rule counters, the last sample and drop
instants, the per-tick decode budget, and the transition detectors. Feed
it every sample (observe_sample) and every drop
(observe_drop) the stream yields, then
evaluate once per tick and get back only what changed.
Why the seam exists. A trigger capture (zenctl record --on) must
judge the same event stream it records: one subscription, one drop
ledger. Had the capture run a watchdog of its own beside its recorder,
the drops the judge saw and the drops in the file would have been two
different facts about two different observers — and a {"dropped": n}
in the file would say nothing about whether the rule that fired was
judged over a clean window. With the body a value, the recorder drains
one stream and hands every item to both the ring and the rules.
Sample attribution is by key-expression intersection against each rule’s
selector; a sample whose key does not parse as one counts for no rule.
Time is tokio::time::Instant, so a driver under paused time judges
exact windows.
Implementations§
Source§impl<'a> RuleSet<'a>
impl<'a> RuleSet<'a>
Sourcepub fn new(
rules: &[Condition],
base: &'a str,
slices: Option<&'a SliceSet>,
) -> Result<Self>
pub fn new( rules: &[Condition], base: &'a str, slices: Option<&'a SliceSet>, ) -> Result<Self>
Compile the rules. Fails on a selector that is not a key expression —
before anything is declared, so the ? has nothing to tear down
(#336). The watch clock starts here: CondWindow::observed_s is
measured from construction, so build the set right before the
subscriptions are declared.
Sourcepub fn watched(&self) -> &[String]
pub fn watched(&self) -> &[String]
The distinct selectors the rules observe — what the driver must subscribe to before the first window opens (O4).
Sourcepub fn wants_doctor(&self) -> bool
pub fn wants_doctor(&self) -> bool
Some rule judges a doctor run, so the driver owes one per tick.
Sourcepub fn wants_roster(&self) -> bool
pub fn wants_roster(&self) -> bool
Some rule judges the liveliness roster, so the driver owes one ask per tick.
Sourcepub fn wants_decode(&self) -> bool
pub fn wants_decode(&self) -> bool
Some rule judges payload validity, so the driver owes a warmed,
sealed schema store (#337) and a decode per
wants_verdict.
Sourcepub fn wants_verdict(&mut self, s: &SampleView) -> bool
pub fn wants_verdict(&mut self, s: &SampleView) -> bool
Whether this sample should be decoded before it is observed: an
invalid-payload rule matches its key and the key’s per-tick decode
budget has room. Spends the budget — ask once per sample, then hand
the verdict to observe_sample. The decode
stays the driver’s, because it is async and this is not.
Sourcepub fn observe_sample(
&mut self,
s: &SampleView,
facts_cache: &mut FactsCache,
verdict: Option<&Verdict>,
)
pub fn observe_sample( &mut self, s: &SampleView, facts_cache: &mut FactsCache, verdict: Option<&Verdict>, )
Count one observed sample against every rule its key matches.
verdict is the decode the driver ran when
wants_verdict said so; None means the
sample was not checked, which is counted as exactly that.
Sourcepub fn observe_drop(&mut self, n: u64)
pub fn observe_drop(&mut self, n: u64)
The stream dropped n samples here (RFC 09 §5.1 O6): unattributable
to any one selector, so it taints every completeness claim this tick.
Sourcepub fn evaluate(
&mut self,
now: Instant,
at: &str,
sweep: SweepOutcome<'_>,
) -> Vec<Transition>
pub fn evaluate( &mut self, now: Instant, at: &str, sweep: SweepOutcome<'_>, ) -> Vec<Transition>
Close the tick: judge every rule over the window measured since the
last evaluation, reset the per-tick counts, and hand back only the
genuine changes — none for an unchanged rule. at is the wall-clock
stamp the transitions carry.
Sourcepub fn last_eval(&self) -> Instant
pub fn last_eval(&self) -> Instant
When the last tick closed (construction, before the first): the driver’s next deadline is measured from here, so a slow consumer of the transitions widens the next window rather than skipping one.
Sourcepub fn transitions(&self) -> u64
pub fn transitions(&self) -> u64
Transitions emitted so far.
Auto Trait Implementations§
impl<'a> Freeze for RuleSet<'a>
impl<'a> RefUnwindSafe for RuleSet<'a>
impl<'a> Send for RuleSet<'a>
impl<'a> Sync for RuleSet<'a>
impl<'a> Unpin for RuleSet<'a>
impl<'a> UnsafeUnpin for RuleSet<'a>
impl<'a> UnwindSafe for RuleSet<'a>
Blanket Implementations§
Source§impl<Source> AccessAs for Source
impl<Source> AccessAs for Source
Source§impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedExplicit<'a, E> for Twhere
T: 'a,
Source§impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
impl<'a, T, E> AsTaggedImplicit<'a, E> for Twhere
T: 'a,
Source§impl<T> BorrowMut<T> for Twhere
T: ?Sized,
impl<T> BorrowMut<T> for Twhere
T: ?Sized,
Source§fn borrow_mut(&mut self) -> &mut T
fn borrow_mut(&mut self) -> &mut T
impl<ST, DT> CastableFrom<ST, Initialized, Initialized> for DT
impl<ST, DT> CastableFrom<ST, Uninit, Uninit> for DT
Source§impl<T> Instrument for T
impl<T> Instrument for T
Source§fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
fn instrument(self, span: Span) -> Instrumented<Self> ⓘ
Source§fn in_current_span(self) -> Instrumented<Self> ⓘ
fn in_current_span(self) -> Instrumented<Self> ⓘ
Source§impl<T> IntoEither for T
impl<T> IntoEither for T
Source§fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
fn into_either(self, into_left: bool) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left is true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read moreSource§fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
fn into_either_with<F>(self, into_left: F) -> Either<Self, Self> ⓘ
self into a Left variant of Either<Self, Self>
if into_left(&self) returns true.
Converts self into a Right variant of Either<Self, Self>
otherwise. Read more