feat(event): refuse subevents that escape the parent interval - #118
Conversation
A half-open subevent window must lie inside the parent event-time interval (ADR 0003).
|
Warning Review limit reachedNext included review available in 3 seconds. View limit detailsLimit details: You’ve used the included review currently available. You've used all free OSS reviews for now. Wait for the free limit to reset to keep reviewing this public repository. Review configuration: ⚙️ Run configurationConfiguration used: Organization UI Review profile: CHILL Plan: Pro Plus Run ID: ⛔ Files ignored due to path filters (1)
📒 Files selected for processing (17)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
# Conflicts: # CHANGELOG.md # docs/research/standards-and-literature.md # docs/validation/temporal-event-foundation.md
|
Current HEAD |
|
Current-head review refresh for 97c6363:
|
|
Rebased current head b8f4582 onto origin/main. The changelog conflict retains both feature and current-main entries; inherited documentation trailing whitespace was removed. Local merge-tree, git diff --cached --check, and cargo fmt --all -- --check pass. Exact-head hosted checks and required independent approvals remain required before protected merge. |
…nment # Conflicts: # ARCHITECTURE.md # CHANGELOG.md # Cargo.toml # README.md # docs/TRACEABILITY.md # docs/adr/0003-relational-event-multiple-membership.md # docs/adr/README.md # docs/validation/temporal-event-foundation.md # scripts/check_workspace_contract.py # tests/quality/test_check_docstrings.py
|
|
||
| International Organization for Standardization and International Electrotechnical Commission. (2011). *Information technology—Security techniques—Privacy framework* (ISO/IEC Standard No. 29100:2011). Data minimization informs `provider_receipt`; it is not a certification claim. | ||
|
|
||
| Allen, J. F. (1983). Maintaining knowledge about temporal intervals. *Communications of the ACM, 26*(11), 832–843. https://doi.org/10.1145/182.358434. The `during` relation informs `subevent_containment`; the crate does not implement Allen composition. |
There was a problem hiding this comment.
📝 Info: Temporal reference filed under privacy section
The Allen (1983) citation for subevent_containment at standards-and-literature.md is placed under ## Privacy and operational log/source separation, not the ## Time, events, and topic detection and tracking section (line 70) that already lists the same paper.
Was this helpful? React with 👍 or 👎 to provide feedback.
| pub fn interval_contains( | ||
| parent: EventInterval, | ||
| child: EventInterval, | ||
| ) -> Result<bool, SubeventContainmentError> { | ||
| Ok(child.start_seconds >= parent.start_seconds && child.end_seconds <= parent.end_seconds) | ||
| } |
There was a problem hiding this comment.
📝 Info: interval_contains documented as infallible yet returns Result
interval_contains at interval.rs always returns Ok(..) and its # Errors docstring states it is infallible; the Result wrapper and #[allow(clippy::unnecessary_wraps)] exist only to keep the public surface explicit. refuse_escaped_subevent propagates the never-taken ?. This is intentional per the docs but worth noting: consumers must still handle an error arm that can never occur, which slightly complicates the API contract.
Was this helpful? React with 👍 or 👎 to provide feedback.
| pub fn interval_contains( | ||
| parent: EventInterval, | ||
| child: EventInterval, | ||
| ) -> Result<bool, SubeventContainmentError> { | ||
| Ok(child.start_seconds >= parent.start_seconds && child.end_seconds <= parent.end_seconds) | ||
| } |
There was a problem hiding this comment.
📝 Info: Containment logic is correct for half-open intervals
interval_contains at interval.rs correctly implements half-open [start, end) containment: a child is contained iff child.start >= parent.start && child.end <= parent.end. EventInterval::new rejects zero-length/inverted intervals (end <= start), so the recovery and refusal paths cannot receive degenerate intervals. No correctness issue found.
Was this helpful? React with 👍 or 👎 to provide feedback.
| pub fn containment_recovery_rate( | ||
| truth: &[bool], | ||
| decided: &[bool], | ||
| ) -> Result<f64, SubeventContainmentError> { | ||
| if truth.is_empty() || truth.len() != decided.len() { | ||
| return Err(SubeventContainmentError::InvalidIntervalPayload); | ||
| } | ||
| let mut matches = 0_u32; | ||
| for (truth_flag, decided_flag) in truth.iter().zip(decided) { | ||
| if truth_flag == decided_flag { | ||
| matches += 1; | ||
| } | ||
| } | ||
| Ok(f64::from(matches) / truth.len() as f64) | ||
| } |
There was a problem hiding this comment.
📝 Info: Recovery-rate empty/length checks match documented contract
containment_recovery_rate at interval.rs returns InvalidIntervalPayload when truth.is_empty() or lengths differ. The docstring says "when either slice is empty or the lengths differ"; the empty-decided/non-empty-truth case is caught by the length check, and empty truth is caught directly, so the two conditions together cover all empty cases. Behavior is consistent with the contract.
Was this helpful? React with 👍 or 👎 to provide feedback.
| "tepp_simulation", | ||
| "validation_core", | ||
| "tepp_api", | ||
| "subevent_containment", |
There was a problem hiding this comment.
📝 Info: Workspace member ordering stays in sync across manifest, contract, and README
The new subevent_containment crate is appended consistently to Cargo.toml members and default-members, to EXPECTED_CRATES in check_workspace_contract.py (which enforces exact ordered equality of members/default-members), and the README crate list. The docstring test was updated to assert len(crate_roots) == len(contract.EXPECTED_CRATES) rather than a hardcoded 10, so it will not drift. The mechanical transformation appears complete and consistent.
Was this helpful? React with 👍 or 👎 to provide feedback.
Summary
subevent_containment: a half-open child interval that starts before or ends after the parent cannot attach.event_coremention/instance separation.Claim boundary
#45still owns0007).Test plan
containment_contractfailed withE0432cargo test -p subevent_containment --offline --lib --testscargo clippy -p subevent_containment --all-targets --offline -- -D warningscargo llvm-cov -p subevent_containmentlines 20/20; nightly-2026-08-01 branches 12/12