feat(aura-engine): Source::resident_records — probe ring residency via the trait

The residency probe was an inherent method on the concrete M1FieldSource, so a Box<dyn Source> consumer could not read it without downcasting (the adjacent friction noted in #95). Hoist it onto the Source trait as resident_records(&self) -> Option<usize> with a default of None, mirroring bounds()'s Option-for-unknown idiom: None = "does not report" (the eager VecSource, which has no streaming ring), distinct from Some(0) = "reports, holds none" (e.g. exhausted).

M1FieldSource overrides it to return Some(chunk len). Callers updated (streaming_seam, the two deep-dive fieldtest bins). Tests: a hermetic VecSource default-is-None check, and a &dyn Source probe in the gated residency test proving M1FieldSource residency is readable without a downcast.

refs #95
This commit is contained in:
2026-06-17 23:32:50 +02:00
parent 0d7c2c16f4
commit f66036bd61
5 changed files with 49 additions and 18 deletions
+22
View File
@@ -70,6 +70,18 @@ pub trait Source {
/// open-ended. Cursor-independent: a property of the data extent, not the
/// read position.
fn bounds(&self) -> Option<(Timestamp, Timestamp)>;
/// Records this source holds resident right now — the streaming-ring probe
/// (#95). `None` (the default) means the source does not report a residency:
/// the eager [`VecSource`] materializes its whole stream and has no bounded
/// ring. A lazy chunk source overrides this to return `Some(len)` of the chunk
/// it currently borrows, so a `Box<dyn Source>` consumer can budget memory
/// without downcasting. Mirrors [`bounds`](Source::bounds)' Option idiom:
/// `None` = "not reported," distinct from `Some(0)` = "reports, holds none"
/// (e.g. exhausted). Probes the aura source ring only, not whole-process RSS.
fn resident_records(&self) -> Option<usize> {
None
}
}
/// A `Source` over a fully materialized stream — the cycle-0011 eager shape,
@@ -493,6 +505,16 @@ mod tests {
points.iter().map(|&(t, v)| (Timestamp(t), Scalar::f64(v))).collect()
}
#[test]
fn vec_source_reports_no_residency_by_default() {
// The eager VecSource has no streaming ring, so it takes the Source trait
// default: residency is "not reported" (None), distinct from Some(0). The
// probe is reachable through `&dyn Source` without downcasting (#95).
let v = VecSource::new(f64_stream(&[(1, 1.0), (2, 2.0)]));
let probe: &dyn Source = &v;
assert_eq!(probe.resident_records(), None);
}
#[test]
fn seeded_source_same_seed_same_stream() {
// Same seed -> bit-identical stream (C1/C12 determinism).