remem-ai 0.6.70

Local-first coding agent memory for Claude Code and OpenAI Codex
Documentation
use anyhow::Result;
use rusqlite::{params, Connection};

use super::*;

fn migrated_connection() -> Result<Connection> {
    let conn = Connection::open_in_memory()?;
    crate::migrate::run_migrations(&conn)?;
    Ok(conn)
}

fn insert_active_memory(conn: &Connection) -> Result<i64> {
    conn.execute(
        "INSERT INTO memories(
             session_id, project, topic_key, title, content, memory_type,
             created_at_epoch, updated_at_epoch, status
         ) VALUES ('s1', 'project-web', 'web-governance', 'Web memory',
                   'Content', 'decision', 1, 1, 'active')",
        [],
    )?;
    Ok(conn.last_insert_rowid())
}

fn request<'a>(
    memory_id: i64,
    action: WebMemoryGovernanceAction,
    version: i64,
    operation_id: &'a str,
) -> WebMemoryGovernanceRequest<'a> {
    WebMemoryGovernanceRequest {
        memory_id,
        action,
        expected_version: version,
        operation_id,
        reason: "  keep the original normalized reason  ",
        actor: "api",
    }
}

fn applied(decision: WebMemoryGovernanceDecision) -> WebMemoryGovernanceResult {
    match decision {
        WebMemoryGovernanceDecision::Applied(result) => result,
        other => panic!("expected applied decision, got {other:?}"),
    }
}

fn insert_archive_ledger(
    conn: &Connection,
    operation_id: &str,
    result: &WebMemoryGovernanceResult,
) -> Result<()> {
    let response = serde_json::json!({
        "response_schema_version": 1,
        "operation_id": operation_id,
        "audit_id": result.audit_id,
        "memory_id": result.memory_id,
        "action": "archive",
        "before_status": "active",
        "after_status": "archived",
        "version": result.version,
        "occurred_at_epoch": result.occurred_at_epoch,
        "replayed": false,
    })
    .to_string();
    conn.execute(
        "INSERT INTO api_mutation_requests(
             idempotency_key_hash, request_hash, operation_id, resource_kind,
             resource_id, action, response_schema_version, response_json,
             audit_id, created_at_epoch
         ) VALUES (?1, ?2, ?3, 'memory', ?4, 'archive', 1, ?5, ?6, ?7)",
        params![
            format!("hash-{operation_id}"),
            format!("request-{operation_id}"),
            operation_id,
            result.memory_id,
            response,
            result.audit_id,
            result.occurred_at_epoch
        ],
    )?;
    Ok(())
}

#[test]
fn web_archive_sets_marker_versions_state_and_writes_exact_audit() -> Result<()> {
    let conn = migrated_connection()?;
    let memory_id = insert_active_memory(&conn)?;
    let result = applied(govern_memory_for_web_in_transaction(
        &conn,
        &request(
            memory_id,
            WebMemoryGovernanceAction::Archive,
            1,
            "op_archive_domain",
        ),
    )?);

    assert_eq!(result.before_status, "active");
    assert_eq!(result.after_status, "archived");
    assert_eq!(result.version, 2);
    let (status, version, marker): (String, i64, Option<String>) = conn.query_row(
        "SELECT status, version, web_archive_operation_id FROM memories WHERE id = ?1",
        [memory_id],
        |row| Ok((row.get(0)?, row.get(1)?, row.get(2)?)),
    )?;
    assert_eq!(
        (status.as_str(), version, marker.as_deref()),
        ("archived", 2, Some("op_archive_domain"))
    );
    let detail: String = conn.query_row(
        "SELECT detail FROM events WHERE id = ?1",
        [result.audit_id],
        |row| row.get(0),
    )?;
    let detail: serde_json::Value = serde_json::from_str(&detail)?;
    assert_eq!(detail["reason"], "  keep the original normalized reason  ");
    assert_eq!(detail["operation_id"], "op_archive_domain");
    assert_eq!(detail["previous_status"], "active");
    assert_eq!(detail["new_status"], "archived");
    Ok(())
}

#[test]
fn web_restore_requires_current_exact_archive_provenance() -> Result<()> {
    let conn = migrated_connection()?;
    let memory_id = insert_active_memory(&conn)?;
    let archive = applied(govern_memory_for_web_in_transaction(
        &conn,
        &request(
            memory_id,
            WebMemoryGovernanceAction::Archive,
            1,
            "op_archive_provenance",
        ),
    )?);
    assert_eq!(
        govern_memory_for_web_in_transaction(
            &conn,
            &request(
                memory_id,
                WebMemoryGovernanceAction::Restore,
                archive.version,
                "op_restore_before_ledger",
            ),
        )?,
        WebMemoryGovernanceDecision::NotRecoverable
    );

    insert_archive_ledger(&conn, "op_archive_provenance", &archive)?;
    let restored = applied(govern_memory_for_web_in_transaction(
        &conn,
        &request(
            memory_id,
            WebMemoryGovernanceAction::Restore,
            archive.version,
            "op_restore_domain",
        ),
    )?);
    assert_eq!(restored.after_status, "active");
    assert_eq!(restored.version, archive.version + 1);
    let marker: Option<String> = conn.query_row(
        "SELECT web_archive_operation_id FROM memories WHERE id = ?1",
        [memory_id],
        |row| row.get(0),
    )?;
    assert_eq!(marker, None);
    Ok(())
}

#[test]
fn historical_ledger_does_not_authorize_non_web_archive() -> Result<()> {
    let conn = migrated_connection()?;
    let memory_id = insert_active_memory(&conn)?;
    let archive = applied(govern_memory_for_web_in_transaction(
        &conn,
        &request(
            memory_id,
            WebMemoryGovernanceAction::Archive,
            1,
            "op_historical_archive",
        ),
    )?);
    insert_archive_ledger(&conn, "op_historical_archive", &archive)?;
    let restored = applied(govern_memory_for_web_in_transaction(
        &conn,
        &request(
            memory_id,
            WebMemoryGovernanceAction::Restore,
            archive.version,
            "op_historical_restore",
        ),
    )?);
    conn.execute(
        "UPDATE memories SET status = 'archived', updated_at_epoch = updated_at_epoch + 1 WHERE id = ?1",
        [memory_id],
    )?;
    let version: i64 = conn.query_row(
        "SELECT version FROM memories WHERE id = ?1",
        [memory_id],
        |row| row.get(0),
    )?;
    assert_eq!(version, restored.version + 1);
    assert_eq!(
        govern_memory_for_web_in_transaction(
            &conn,
            &request(
                memory_id,
                WebMemoryGovernanceAction::Restore,
                version,
                "op_non_web_restore",
            ),
        )?,
        WebMemoryGovernanceDecision::NotRecoverable
    );
    Ok(())
}

#[test]
fn guarded_decisions_do_not_mutate_or_audit() -> Result<()> {
    let conn = migrated_connection()?;
    let memory_id = insert_active_memory(&conn)?;
    assert_eq!(
        govern_memory_for_web_in_transaction(
            &conn,
            &request(
                memory_id,
                WebMemoryGovernanceAction::Archive,
                99,
                "op_stale",
            ),
        )?,
        WebMemoryGovernanceDecision::VersionConflict
    );
    assert_eq!(
        govern_memory_for_web_in_transaction(
            &conn,
            &request(
                memory_id,
                WebMemoryGovernanceAction::Restore,
                1,
                "op_active_restore",
            ),
        )?,
        WebMemoryGovernanceDecision::NotRecoverable
    );
    assert_eq!(
        govern_memory_for_web_in_transaction(
            &conn,
            &request(
                memory_id + 100,
                WebMemoryGovernanceAction::Restore,
                1,
                "op_missing_restore",
            ),
        )?,
        WebMemoryGovernanceDecision::NotRecoverable
    );
    let state: (String, i64) = conn.query_row(
        "SELECT status, version FROM memories WHERE id = ?1",
        [memory_id],
        |row| Ok((row.get(0)?, row.get(1)?)),
    )?;
    assert_eq!(state, ("active".to_string(), 1));
    let audits: i64 = conn.query_row(
        "SELECT COUNT(*) FROM events WHERE event_type = 'memory_governance'",
        [],
        |row| row.get(0),
    )?;
    assert_eq!(audits, 0);
    Ok(())
}