Skip to content

Commit 0b78521

Browse files
feat(core): enforce hosted memory provenance (OpenCoven#105 OpenCoven#106 OpenCoven#112)
Fixes OpenCoven#105. Fixes OpenCoven#106. Fixes OpenCoven#112. - enforce hosted memory frontmatter scope and trust - preserve provenance metadata in hosted memory context - require structured review output to cite memory refs Signed-off-by: Timothy Wayne Gregg <Timothy.Gregg@complete.tech>
1 parent 7658331 commit 0b78521

9 files changed

Lines changed: 511 additions & 24 deletions

File tree

docs/configuration.md

Lines changed: 21 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -350,7 +350,12 @@ AGENTS.md files may begin with optional YAML frontmatter to control loading:
350350
---
351351
memory_type: project
352352
priority: 10
353-
scope: project
353+
scope: repo
354+
trust: maintainer_approved
355+
visibility: public_review
356+
source: github_pr
357+
source_ref: OpenCoven/coven-code#123
358+
expires_at: 2099-12-31
354359
---
355360

356361
# My Project Notes
@@ -362,9 +367,22 @@ Frontmatter fields:
362367

363368
| Field | Description |
364369
|-------|-------------|
365-
| `memory_type` | Informal label (currently informational only). |
370+
| `id` | Stable memory id used for hosted review citation, for example `mem_auth_policy`. If omitted, Coven Code derives a stable id from path and content. |
371+
| `memory_type` | Memory category label such as `project`, `user`, `reference`, or `feedback`. |
366372
| `priority` | Integer sort priority (lower numbers are prepended first within the same scope). |
367-
| `scope` | Informational label for documentation purposes. |
373+
| `scope` | Intended scope, such as `user`, `tenant`, `installation`, `repo`, `branch`, or `pr`. |
374+
| `trust` | Source trust. Hosted review enforces this against `hostedReview.memoryTrustThreshold`. Supported values include `system_policy`, `maintainer_approved`, `default_branch_code`, `model_inferred`, `contributor_input`, `fork_input`, and `unknown`. |
375+
| `visibility` | Intended review visibility: `public_review`, `private_review`, or `security_private`. Hosted public reviews exclude `security_private` memory by default. |
376+
| `source` | Provenance source kind, for example `manual`, `github_pr`, `github_pr_review`, or `session_memory_extraction`. |
377+
| `source_ref` | Source reference such as `owner/repo#123`, a commit SHA, or another non-secret audit handle. |
378+
| `expires_at` | Optional expiry date in `YYYY-MM-DD` format. Expired hosted memory is ignored. |
379+
| `created_at`, `created_by`, `session_id`, `transcript_ref`, `confidence` | Optional provenance fields for audit and review artifacts. |
380+
381+
Local mode tolerates missing metadata for backward compatibility. Hosted review
382+
mode treats missing trust as `unknown`, ignores expired memory, and excludes
383+
memory below the configured trust threshold. Tagged hosted memory is injected
384+
with memory ids and provenance metadata; findings that rely on memory should
385+
include those ids in `memory_refs`.
368386

369387
### @include directives
370388

Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
# Hosted Review Phase 4 PR Notes
2+
3+
## Linked issues
4+
5+
Fixes #105.
6+
Fixes #106.
7+
Fixes #112.
8+
9+
## Summary
10+
11+
- Extends AGENTS.md frontmatter with enforceable hosted metadata: stable id, trust, visibility, source, source_ref, expiry, created_at, created_by, session_id, transcript_ref, and confidence.
12+
- Enforces hosted memory metadata during loading: missing trust is lowest trust, expired memory is ignored, security-private memory is excluded from public hosted review, and trust must meet the configured threshold.
13+
- Renders hosted memory as tagged entries with stable ids, trust, visibility, source, source_ref, and session metadata so review output can cite memory refs.
14+
- Threads session-scoped provenance into hosted auto-extracted memory candidates.
15+
- Adds structured review-output parsing and validation helpers for `memory_refs` on memory-dependent findings.
16+
- Documents the hosted frontmatter contract and citation behavior.
17+
18+
## Test evidence
19+
20+
- `cargo fmt --all -- --check`
21+
- `cargo check --workspace`
22+
- `cargo clippy --workspace --all-targets -- -D warnings`
23+
- `cargo test -p claurst-core --lib claudemd --quiet`
24+
- `cargo test -p claurst-core --lib system_prompt --quiet`
25+
- `cargo test -p claurst-core --lib --quiet`
26+
- `cargo test -p claurst-query session_memory --quiet`
27+
- `cargo test -p claurst-commands structured_review_output --quiet`
28+
- `cargo test --workspace --quiet`
29+
30+
## Risk notes
31+
32+
- The slash `/review` command remains markdown-first; the structured review parser is available for hosted integrations that request JSON review artifacts.
33+
- Hosted memory without trust metadata is intentionally ignored unless policy lowers the trust threshold.
34+
- Provenance stores references and ids, not secret values.

src-rust/crates/commands/src/lib.rs

Lines changed: 59 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3382,6 +3382,39 @@ impl SlashCommand for LearnCommand {
33823382

33833383
// ---- /review -------------------------------------------------------------
33843384

3385+
#[derive(Debug, Clone, serde::Deserialize, PartialEq, Eq)]
3386+
pub struct StructuredReviewOutput {
3387+
#[serde(default)]
3388+
pub findings: Vec<StructuredReviewFinding>,
3389+
}
3390+
3391+
#[derive(Debug, Clone, serde::Deserialize, PartialEq, Eq)]
3392+
pub struct StructuredReviewFinding {
3393+
pub title: String,
3394+
#[serde(default)]
3395+
pub memory_refs: Vec<String>,
3396+
#[serde(default)]
3397+
pub memory_dependent: bool,
3398+
}
3399+
3400+
pub fn parse_structured_review_output(text: &str) -> Option<StructuredReviewOutput> {
3401+
serde_json::from_str::<StructuredReviewOutput>(text).ok()
3402+
}
3403+
3404+
pub fn validate_structured_review_memory_refs(review: &StructuredReviewOutput) -> Vec<String> {
3405+
review
3406+
.findings
3407+
.iter()
3408+
.filter(|finding| finding.memory_dependent && finding.memory_refs.is_empty())
3409+
.map(|finding| {
3410+
format!(
3411+
"finding '{}' is marked memory-dependent but has no memory_refs",
3412+
finding.title
3413+
)
3414+
})
3415+
.collect()
3416+
}
3417+
33853418
#[async_trait]
33863419
impl SlashCommand for ReviewCommand {
33873420
fn name(&self) -> &str {
@@ -3527,7 +3560,8 @@ impl SlashCommand for ReviewCommand {
35273560
(1-3 sentences describing what changed)\n\n\
35283561
## Issues\n\
35293562
(bulleted list: [CRITICAL|MAJOR|MINOR] file:line — description; \
3530-
omit section if none)\n\n\
3563+
omit section if none; if the issue depends on a loaded memory entry, \
3564+
include memory_refs: [\"mem_...\"] on that bullet)\n\n\
35313565
## Suggestions\n\
35323566
(bulleted list of optional improvements; omit section if none)\n\n\
35333567
## Verdict\n\
@@ -10488,6 +10522,30 @@ mod tests {
1048810522
}
1048910523
}
1049010524

10525+
#[test]
10526+
fn structured_review_output_parses_memory_refs() {
10527+
let review = parse_structured_review_output(
10528+
r#"{"findings":[{"title":"Auth check","memory_refs":["mem_auth"],"memory_dependent":true}]}"#,
10529+
)
10530+
.unwrap();
10531+
10532+
assert_eq!(review.findings[0].memory_refs, vec!["mem_auth"]);
10533+
assert!(validate_structured_review_memory_refs(&review).is_empty());
10534+
}
10535+
10536+
#[test]
10537+
fn structured_review_output_warns_when_memory_refs_missing() {
10538+
let review = parse_structured_review_output(
10539+
r#"{"findings":[{"title":"Auth check","memory_dependent":true}]}"#,
10540+
)
10541+
.unwrap();
10542+
10543+
let warnings = validate_structured_review_memory_refs(&review);
10544+
assert_eq!(warnings.len(), 1);
10545+
assert!(warnings[0].contains("Auth check"));
10546+
assert!(warnings[0].contains("memory_refs"));
10547+
}
10548+
1049110549
#[tokio::test]
1049210550
async fn test_learn_resolves_and_emits_skill_prompt() {
1049310551
// Resolvable by name and by alias.

0 commit comments

Comments
 (0)