#![forbid(unsafe_code)]
#![deny(missing_docs)]
use std::io::{self, BufRead, Write};
use std::path::PathBuf;
use mnem_mcp::Server;
fn main() -> anyhow::Result<()> {
let repo_path = parse_repo_path();
let mut server = Server::new(repo_path);
if !server.allow_labels {
eprintln!(
"mnem mcp: labels DISABLED (MNEM_LABELS=0 or MNEM_BENCH=0); \
caller-supplied `label`/`ntype` will be coerced to Node::DEFAULT_NTYPE."
);
}
let stdin = io::stdin();
let stdout = io::stdout();
let mut stdout = stdout.lock();
for line in stdin.lock().lines() {
let line = line?;
if line.trim().is_empty() {
continue;
}
if let Some(response) = server.handle_line(&line) {
writeln!(stdout, "{response}")?;
stdout.flush()?;
}
}
Ok(())
}
fn parse_repo_path() -> PathBuf {
let mut args = std::env::args().skip(1);
while let Some(arg) = args.next() {
match arg.as_str() {
"--repo" => {
if let Some(p) = args.next() {
return PathBuf::from(p);
}
}
"--version" | "-V" => {
println!("mnem mcp {}", env!("CARGO_PKG_VERSION"));
std::process::exit(0);
}
"--help" | "-h" => {
print_help();
std::process::exit(0);
}
_ => {}
}
}
std::env::var("MNEM_REPO")
.map(PathBuf::from)
.unwrap_or_else(|_| PathBuf::from(".mnem"))
}
fn print_help() {
eprintln!(
"mnem mcp {}\nModel Context Protocol server for mnem\n\n\
USAGE:\n mnem mcp [--repo PATH]\n\n\
Speaks JSON-RPC 2.0 over stdio. Intended to be launched by an\n\
MCP client (Claude Desktop, Cursor, Windsurf, Claude Code, ...).\n\n\
OPTIONS:\n \
--repo PATH Repository directory (default: .mnem, env: MNEM_REPO)\n \
-V, --version Print version and exit\n \
-h, --help Print this help and exit\n",
env!("CARGO_PKG_VERSION")
);
}