remem-ai 0.6.62

Local-first coding agent memory for Claude Code and OpenAI Codex
Documentation
use rmcp::handler::server::wrapper::Parameters;
use rmcp::{tool, tool_router};

use super::super::types::{CommitLookupParams, SessionCommitsParams};
use super::errors::{self, McpToolError, McpToolResult};
use super::MemoryServer;

#[tool_router(router = tool_router_commit, vis = "pub(super)")]
impl MemoryServer {
    #[tool(
        description = "Look up git commit metadata and linked memory sessions by full or short SHA. Its poisoning gate may quarantine the newest eligible unsafe linked session summary. The response separates git metadata from memory-derived summaries so missing links are not inferred."
    )]
    pub(super) fn lookup_commit(
        &self,
        Parameters(params): Parameters<CommitLookupParams>,
    ) -> McpToolResult<String> {
        const TOOL: &str = "lookup_commit";
        crate::log::info(
            "mcp",
            &format!(
                "lookup_commit called sha={} project={:?}",
                params.sha, params.project
            ),
        );
        if params.sha.trim().is_empty() {
            return Err(McpToolError::invalid_request(
                TOOL,
                "commit SHA is required",
            ));
        }
        self.with_conn(TOOL, |conn| {
            let results =
                crate::git_trace::lookup_commit(conn, params.project.as_deref(), &params.sha)
                    .map_err(|err| {
                        crate::log::warn("mcp", &format!("lookup_commit failed: {}", err));
                        McpToolError::db_query(TOOL, err)
                    })?;
            errors::to_json_pretty(TOOL, &results)
        })
    }

    #[tool(
        description = "List git commits linked to a content session ID or remem memory session ID. Its poisoning gate may quarantine the newest eligible unsafe linked session summary. Returns link evidence plus git metadata; it does not guess commit intent when no link exists."
    )]
    pub(super) fn commits_for_session(
        &self,
        Parameters(params): Parameters<SessionCommitsParams>,
    ) -> McpToolResult<String> {
        const TOOL: &str = "commits_for_session";
        crate::log::info(
            "mcp",
            &format!(
                "commits_for_session called session_id={} project={:?} limit={}",
                params.session_id,
                params.project,
                params.limit.unwrap_or(20)
            ),
        );
        if params.session_id.trim().is_empty() {
            return Err(McpToolError::invalid_request(
                TOOL,
                "session_id is required",
            ));
        }
        self.with_conn(TOOL, |conn| {
            let results = crate::git_trace::commits_for_session(
                conn,
                params.project.as_deref(),
                &params.session_id,
                params.limit.unwrap_or(20),
            )
            .map_err(|err| {
                crate::log::warn("mcp", &format!("commits_for_session failed: {}", err));
                McpToolError::db_query(TOOL, err)
            })?;
            errors::to_json_pretty(TOOL, &results)
        })
    }
}