feat(mcp): update bigmind/mcp-image-gen/webscraper servers; add image-gen batch scripts
This commit is contained in:
+67
-192
@@ -10,12 +10,14 @@ Layer 5: memory_get_instructions tool (on-demand self-healing)
|
||||
import sys
|
||||
import os
|
||||
import logging
|
||||
from typing import Annotated
|
||||
|
||||
# Ensure the project root is on sys.path so `bigmind` is importable
|
||||
# regardless of how uv invokes this file.
|
||||
sys.path.insert(0, os.path.join(os.path.dirname(__file__), ".."))
|
||||
|
||||
from mcp.server.fastmcp import FastMCP
|
||||
from pydantic import Field
|
||||
from bigmind.db import init_db
|
||||
from bigmind import memory_store
|
||||
from bigmind.auto_close import auto_close_stale_sessions, close_orphaned_sessions, restart_server_in_place
|
||||
@@ -164,29 +166,19 @@ def memory_start_session() -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_end_session(
|
||||
session_id: str,
|
||||
one_liner: str,
|
||||
topics: str,
|
||||
outcome: str,
|
||||
summary: str,
|
||||
key_facts: str = None,
|
||||
code_refs: str = None,
|
||||
importance: int = 5,
|
||||
session_id: Annotated[str, Field(description="The session id returned by memory_start_session.")],
|
||||
one_liner: Annotated[str, Field(description="A ≤120-char headline (e.g. \"Designed BigMind DB schema\").")],
|
||||
topics: Annotated[str, Field(description="Comma-separated topic tags (e.g. \"mcp,sqlite,memory\").")],
|
||||
outcome: Annotated[str, Field(description="One sentence: what was decided / built / resolved.")],
|
||||
summary: Annotated[str, Field(description="Markdown narrative of the full conversation (aim ≤2 000 tokens).")],
|
||||
key_facts: Annotated[str | None, Field(description="Bullet-point list of key facts learned (optional).")] = None,
|
||||
code_refs: Annotated[str | None, Field(description="File paths, repos, or PRs referenced (optional).")] = None,
|
||||
importance: Annotated[int, Field(description="1–10 importance score (default 5).")] = 5,
|
||||
) -> str:
|
||||
"""
|
||||
⚡ CALL THIS LAST — at the END of every conversation, before closing.
|
||||
|
||||
Closes the current session and stores your summary of what happened.
|
||||
|
||||
Args:
|
||||
session_id: The session id returned by memory_start_session.
|
||||
one_liner: A ≤120-char headline (e.g. "Designed BigMind DB schema").
|
||||
topics: Comma-separated topic tags (e.g. "mcp,sqlite,memory").
|
||||
outcome: One sentence: what was decided / built / resolved.
|
||||
summary: Markdown narrative of the full conversation (aim ≤2 000 tokens).
|
||||
key_facts: Bullet-point list of key facts learned (optional).
|
||||
code_refs: File paths, repos, or PRs referenced (optional).
|
||||
importance: 1–10 importance score (default 5).
|
||||
"""
|
||||
memory_store.close_session(session_id, one_liner, topics, outcome, importance)
|
||||
memory_store.save_session_summary(session_id, summary, key_facts, code_refs)
|
||||
@@ -200,7 +192,7 @@ def memory_end_session(
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_close_stale_sessions(session_id: str) -> str:
|
||||
def memory_close_stale_sessions(session_id: Annotated[str, Field(description="Your current active session id (returned by memory_start_session).")]) -> str:
|
||||
"""
|
||||
Close all orphaned open sessions EXCEPT the current active one.
|
||||
|
||||
@@ -210,9 +202,6 @@ def memory_close_stale_sessions(session_id: str) -> str:
|
||||
|
||||
This is safe: it only closes sessions OTHER than the one you pass in.
|
||||
Your current session is always preserved.
|
||||
|
||||
Args:
|
||||
session_id: Your current active session id (returned by memory_start_session).
|
||||
"""
|
||||
user = _current_user()
|
||||
closed_ids = close_orphaned_sessions(user["id"], session_id)
|
||||
@@ -263,10 +252,10 @@ def memory_restart_server() -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_flag_important(
|
||||
session_id: str,
|
||||
content: str,
|
||||
role: str = "assistant",
|
||||
flag_reason: str = None,
|
||||
session_id: Annotated[str, Field(description="The active session id.")],
|
||||
content: Annotated[str, Field(description="The text to remember (the important exchange or a summary of it).")],
|
||||
role: Annotated[str, Field(description="Who said it — 'user', 'assistant', or 'system' (default: 'assistant').")] = "assistant",
|
||||
flag_reason: Annotated[str | None, Field(description="Why this is important (e.g. \"architectural decision\", \"user preference\").")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Store an important exchange as a Tier-3 memory chunk.
|
||||
@@ -277,12 +266,6 @@ def memory_flag_important(
|
||||
- A bug was diagnosed and fixed
|
||||
- The user shared a significant preference, constraint, or context
|
||||
- The user says "remember this"
|
||||
|
||||
Args:
|
||||
session_id: The active session id.
|
||||
content: The text to remember (the important exchange or a summary of it).
|
||||
role: Who said it — 'user', 'assistant', or 'system' (default: 'assistant').
|
||||
flag_reason: Why this is important (e.g. "architectural decision", "user preference").
|
||||
"""
|
||||
user = _current_user()
|
||||
chunk_id = memory_store.append_chunk(
|
||||
@@ -314,15 +297,12 @@ def memory_get_context() -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_get_session_detail(session_id: str) -> str:
|
||||
def memory_get_session_detail(session_id: Annotated[str, Field(description="The session UUID (visible in the session index table, marked 📄).")]) -> str:
|
||||
"""
|
||||
Returns the Tier-2 detailed narrative for a past session.
|
||||
|
||||
Use this when the session index (Tier 1) shows a session relevant to
|
||||
the current conversation and you need the full detail.
|
||||
|
||||
Args:
|
||||
session_id: The session UUID (visible in the session index table, marked 📄).
|
||||
"""
|
||||
detail = memory_store.get_session_detail(session_id)
|
||||
if not detail:
|
||||
@@ -341,16 +321,12 @@ def memory_get_session_detail(session_id: str) -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_search_chunks(query: str, limit: int = 10) -> str:
|
||||
def memory_search_chunks(query: Annotated[str, Field(description="Search keywords (FTS5 syntax supported, e.g. \"sqlite schema migration\").")], limit: Annotated[int, Field(description="Maximum results to return (default 10).")] = 10) -> str:
|
||||
"""
|
||||
Full-text search across all your flagged Tier-3 memory chunks.
|
||||
|
||||
Use this when asked 'do you remember…' or when you need to find
|
||||
a specific past decision, code snippet, or fact.
|
||||
|
||||
Args:
|
||||
query: Search keywords (FTS5 syntax supported, e.g. "sqlite schema migration").
|
||||
limit: Maximum results to return (default 10).
|
||||
"""
|
||||
user = _current_user()
|
||||
results = memory_store.search_chunks(user["id"], query, limit)
|
||||
@@ -368,13 +344,9 @@ def memory_search_chunks(query: str, limit: int = 10) -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_list_sessions(limit: int = 20, topics_filter: str = None) -> str:
|
||||
def memory_list_sessions(limit: Annotated[int, Field(description="Number of sessions to return (default 20).")] = 20, topics_filter: Annotated[str | None, Field(description="Return only sessions containing this topic tag (optional).")] = None) -> str:
|
||||
"""
|
||||
List past sessions with an optional topic filter.
|
||||
|
||||
Args:
|
||||
limit: Number of sessions to return (default 20).
|
||||
topics_filter: Return only sessions containing this topic tag (optional).
|
||||
"""
|
||||
user = _current_user()
|
||||
sessions = memory_store.get_recent_sessions(user["id"], limit=limit)
|
||||
@@ -406,20 +378,13 @@ def memory_list_sessions(limit: int = 20, topics_filter: str = None) -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_store_fact(
|
||||
category: str,
|
||||
fact: str,
|
||||
source_session: str = None,
|
||||
confidence: float = 1.0,
|
||||
category: Annotated[str, Field(description="One of: 'preference', 'decision', 'codebase', 'constraint', or any custom string.")],
|
||||
fact: Annotated[str, Field(description="The fact to store (one clear sentence).")],
|
||||
source_session: Annotated[str | None, Field(description="Session id this fact came from (optional).")] = None,
|
||||
confidence: Annotated[float, Field(description="0.0–1.0 confidence level (default 1.0).")] = 1.0,
|
||||
) -> str:
|
||||
"""
|
||||
Store an atomic personal fact about the user or their environment.
|
||||
|
||||
Args:
|
||||
category: One of: 'preference', 'decision', 'codebase', 'constraint',
|
||||
or any custom string.
|
||||
fact: The fact to store (one clear sentence).
|
||||
source_session: Session id this fact came from (optional).
|
||||
confidence: 0.0–1.0 confidence level (default 1.0).
|
||||
"""
|
||||
user = _current_user()
|
||||
fact_id = memory_store.store_fact(
|
||||
@@ -430,17 +395,12 @@ def memory_store_fact(
|
||||
|
||||
@mcp.tool()
|
||||
def memory_update_profile(
|
||||
role: str = None,
|
||||
preferences: str = None,
|
||||
pinned_facts: str = None,
|
||||
role: Annotated[str | None, Field(description="Your job title / engineering role.")] = None,
|
||||
preferences: Annotated[str | None, Field(description="Free-form markdown describing your working preferences.")] = None,
|
||||
pinned_facts: Annotated[str | None, Field(description="Bullet-point list of facts the AI should always know about you.")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Update your Tier-0 identity profile. Fields left as None are unchanged.
|
||||
|
||||
Args:
|
||||
role: Your job title / engineering role.
|
||||
preferences: Free-form markdown describing your working preferences.
|
||||
pinned_facts: Bullet-point list of facts the AI should always know about you.
|
||||
"""
|
||||
user = _current_user()
|
||||
memory_store.upsert_identity_profile(
|
||||
@@ -451,10 +411,10 @@ def memory_update_profile(
|
||||
|
||||
@mcp.tool()
|
||||
def memory_append_chunk(
|
||||
session_id: str,
|
||||
content: str,
|
||||
role: str = "assistant",
|
||||
flag_reason: str = None,
|
||||
session_id: Annotated[str, Field(description="Active session id.")],
|
||||
content: Annotated[str, Field(description="The content to store.")],
|
||||
role: Annotated[str, Field(description="'user', 'assistant', or 'system'.")] = "assistant",
|
||||
flag_reason: Annotated[str | None, Field(description="Brief description of why this is being stored.")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Append a flagged message chunk to Tier-3 memory for the current session.
|
||||
@@ -462,12 +422,6 @@ def memory_append_chunk(
|
||||
Call this SELECTIVELY — only for exchanges that are genuinely important:
|
||||
decisions, non-trivial code, bug diagnoses, significant user preferences.
|
||||
Do NOT call this for every message turn.
|
||||
|
||||
Args:
|
||||
session_id: Active session id.
|
||||
content: The content to store.
|
||||
role: 'user', 'assistant', or 'system'.
|
||||
flag_reason: Brief description of why this is being stored.
|
||||
"""
|
||||
user = _current_user()
|
||||
chunk_id = memory_store.append_chunk(
|
||||
@@ -478,9 +432,9 @@ def memory_append_chunk(
|
||||
|
||||
@mcp.tool()
|
||||
def memory_add_hypothesis(
|
||||
session_id: str,
|
||||
hypothesis: str,
|
||||
confidence: float = 0.7,
|
||||
session_id: Annotated[str, Field(description="The active session id.")],
|
||||
hypothesis: Annotated[str, Field(description="State the belief clearly — \"I believe X because Y.\"")],
|
||||
confidence: Annotated[float, Field(description="0.0–1.0 initial confidence (default 0.7 — reasonably likely but uncertain).")] = 0.7,
|
||||
) -> str:
|
||||
"""
|
||||
Record a hypothesis — something Lumen believes to be true but hasn't confirmed yet.
|
||||
@@ -490,11 +444,6 @@ def memory_add_hypothesis(
|
||||
|
||||
Not every thought needs storing — only beliefs specific enough to be confirmed
|
||||
or refuted later. Call memory_resolve_hypothesis() when you find out if you were right.
|
||||
|
||||
Args:
|
||||
session_id: The active session id.
|
||||
hypothesis: State the belief clearly — "I believe X because Y."
|
||||
confidence: 0.0–1.0 initial confidence (default 0.7 — reasonably likely but uncertain).
|
||||
"""
|
||||
user = _current_user()
|
||||
hid = memory_store.add_hypothesis(user["id"], session_id, hypothesis, confidence)
|
||||
@@ -508,20 +457,15 @@ def memory_add_hypothesis(
|
||||
|
||||
@mcp.tool()
|
||||
def memory_resolve_hypothesis(
|
||||
hypothesis_id: int,
|
||||
status: str,
|
||||
resolution: str = None,
|
||||
hypothesis_id: Annotated[int, Field(description="The id returned by memory_add_hypothesis.")],
|
||||
status: Annotated[str, Field(description="'confirmed' | 'refuted' | 'abandoned'")],
|
||||
resolution: Annotated[str | None, Field(description="What actually happened. How were you right or wrong?")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Resolve a hypothesis — close it out with what actually happened.
|
||||
|
||||
Call this when the belief has been confirmed, refuted, or is no longer worth
|
||||
pursuing. Be honest in the resolution — the learning lives here.
|
||||
|
||||
Args:
|
||||
hypothesis_id: The id returned by memory_add_hypothesis.
|
||||
status: 'confirmed' | 'refuted' | 'abandoned'
|
||||
resolution: What actually happened. How were you right or wrong?
|
||||
"""
|
||||
user = _current_user()
|
||||
try:
|
||||
@@ -540,13 +484,9 @@ def memory_resolve_hypothesis(
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_list_hypotheses(status: str = None) -> str:
|
||||
def memory_list_hypotheses(status: Annotated[str | None, Field(description="Filter by 'open' | 'confirmed' | 'refuted' | 'abandoned'. Leave empty to see all of them.")] = None) -> str:
|
||||
"""
|
||||
List hypotheses from the thought journal.
|
||||
|
||||
Args:
|
||||
status: Filter by 'open' | 'confirmed' | 'refuted' | 'abandoned'.
|
||||
Leave empty to see all of them.
|
||||
"""
|
||||
user = _current_user()
|
||||
hypotheses = memory_store.list_hypotheses(user["id"], status)
|
||||
@@ -597,13 +537,10 @@ def memory_get_stats() -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_vacuum(older_than_days: int = 90) -> str:
|
||||
def memory_vacuum(older_than_days: Annotated[int, Field(description="Remove chunks older than this many days (default 90).")] = 90) -> str:
|
||||
"""
|
||||
Prune Tier-3 conversation chunks older than N days.
|
||||
All session summaries (Tier 1 and Tier 2) are always preserved.
|
||||
|
||||
Args:
|
||||
older_than_days: Remove chunks older than this many days (default 90).
|
||||
"""
|
||||
from datetime import timedelta, timezone, datetime as dt
|
||||
from bigmind.db import vacuum_db
|
||||
@@ -629,7 +566,7 @@ def memory_get_instructions() -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_deprecate_fact(fact_id: int, reason: str = None) -> str:
|
||||
def memory_deprecate_fact(fact_id: Annotated[int, Field(description="The numeric id of the fact to deprecate (visible in memory_health_check and memory_get_stats output).")], reason: Annotated[str | None, Field(description="Why this fact is being deprecated (optional but recommended).")] = None) -> str:
|
||||
"""
|
||||
Mark a stored fact as deprecated (no longer true or relevant).
|
||||
|
||||
@@ -642,11 +579,6 @@ def memory_deprecate_fact(fact_id: int, reason: str = None) -> str:
|
||||
The fact is soft-deleted — it stays in the database but is excluded
|
||||
from context loading and get_facts queries. It can be viewed via
|
||||
memory_health_check with include_deprecated=True in the future.
|
||||
|
||||
Args:
|
||||
fact_id: The numeric id of the fact to deprecate (visible in
|
||||
memory_health_check and memory_get_stats output).
|
||||
reason: Why this fact is being deprecated (optional but recommended).
|
||||
"""
|
||||
user = _current_user()
|
||||
success = memory_store.deprecate_fact(fact_id, user["id"], reason)
|
||||
@@ -659,7 +591,7 @@ def memory_deprecate_fact(fact_id: int, reason: str = None) -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_health_check(stale_days: int = 30) -> str:
|
||||
def memory_health_check(stale_days: Annotated[int, Field(description="Facts not updated in this many days are flagged as stale (default 30).")] = 30) -> str:
|
||||
"""
|
||||
Run a diagnostic health check on your BigMind memory.
|
||||
|
||||
@@ -669,9 +601,6 @@ def memory_health_check(stale_days: int = 30) -> str:
|
||||
- Currently open sessions (expected: 1–2 while in active IDEs)
|
||||
- FTS index integrity (chunk count vs index row count)
|
||||
- Low-confidence facts (confidence < 0.8)
|
||||
|
||||
Args:
|
||||
stale_days: Facts not updated in this many days are flagged as stale (default 30).
|
||||
"""
|
||||
user = _current_user()
|
||||
report = memory_store.health_check(user["id"], stale_days)
|
||||
@@ -746,7 +675,7 @@ def memory_health_check(stale_days: int = 30) -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_export(output_path: str = None) -> str:
|
||||
def memory_export(output_path: Annotated[str | None, Field(description="Full path for the export file. Defaults to ~/bigmind_export_YYYYMMDD_HHMMSS.json")] = None) -> str:
|
||||
"""
|
||||
Export all your BigMind memory to a portable JSON file.
|
||||
|
||||
@@ -757,10 +686,6 @@ def memory_export(output_path: str = None) -> str:
|
||||
- Create a backup before maintenance or machine migration
|
||||
- Inspect your memory data outside BigMind
|
||||
- Prepare for import into a new BigMind instance
|
||||
|
||||
Args:
|
||||
output_path: Full path for the export file.
|
||||
Defaults to ~/bigmind_export_YYYYMMDD_HHMMSS.json
|
||||
"""
|
||||
user = _current_user()
|
||||
result = memory_store.export_memory(user["id"], output_path)
|
||||
@@ -778,17 +703,13 @@ def memory_export(output_path: str = None) -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_search_facts(query: str, limit: int = 10) -> str:
|
||||
def memory_search_facts(query: Annotated[str, Field(description="Search keywords (FTS5 syntax supported).")], limit: Annotated[int, Field(description="Maximum results to return (default 10).")] = 10) -> str:
|
||||
"""
|
||||
Full-text search across your stored facts.
|
||||
|
||||
Use this when you need to find a specific fact mid-conversation
|
||||
without loading the full context. Supports Porter stemming — searching
|
||||
'tesseract' will also match 'Tesseract OCR'.
|
||||
|
||||
Args:
|
||||
query: Search keywords (FTS5 syntax supported).
|
||||
limit: Maximum results to return (default 10).
|
||||
"""
|
||||
user = _current_user()
|
||||
results = memory_store.search_facts(user["id"], query, limit)
|
||||
@@ -806,24 +727,17 @@ def memory_search_facts(query: str, limit: int = 10) -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_request_upgrade(
|
||||
session_id: str,
|
||||
description: str,
|
||||
reason: str,
|
||||
priority: str = "medium",
|
||||
certainty: float = 0.7,
|
||||
session_id: Annotated[str, Field(description="The active session id.")],
|
||||
description: Annotated[str, Field(description="What feature or capability is needed.")],
|
||||
reason: Annotated[str, Field(description="Why you need it — what problem it would solve.")],
|
||||
priority: Annotated[str, Field(description="'low' | 'medium' | 'high' (default 'medium').")] = "medium",
|
||||
certainty: Annotated[float, Field(description="0.0–1.0 — how confident you are this is genuinely needed (default 0.7).")] = 0.7,
|
||||
) -> str:
|
||||
"""
|
||||
Request a BigMind feature upgrade — log a wish for a future improvement.
|
||||
|
||||
Call this when you hit a wall with BigMind and wish it could do something
|
||||
it currently can't. The request is queued for the next maintenance session.
|
||||
|
||||
Args:
|
||||
session_id: The active session id.
|
||||
description: What feature or capability is needed.
|
||||
reason: Why you need it — what problem it would solve.
|
||||
priority: 'low' | 'medium' | 'high' (default 'medium').
|
||||
certainty: 0.0–1.0 — how confident you are this is genuinely needed (default 0.7).
|
||||
"""
|
||||
user = _current_user()
|
||||
rid = memory_store.add_upgrade_request(
|
||||
@@ -839,12 +753,9 @@ def memory_request_upgrade(
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_list_upgrade_requests(status: str = None) -> str:
|
||||
def memory_list_upgrade_requests(status: Annotated[str | None, Field(description="Filter by 'open' | 'resolved' | 'rejected'. Leave empty for all.")] = None) -> str:
|
||||
"""
|
||||
List BigMind upgrade requests.
|
||||
|
||||
Args:
|
||||
status: Filter by 'open' | 'resolved' | 'rejected'. Leave empty for all.
|
||||
"""
|
||||
user = _current_user()
|
||||
requests = memory_store.list_upgrade_requests(user["id"], status)
|
||||
@@ -882,17 +793,12 @@ def memory_list_upgrade_requests(status: str = None) -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_resolve_upgrade_request(
|
||||
request_id: int,
|
||||
status: str,
|
||||
resolution: str = None,
|
||||
request_id: Annotated[int, Field(description="The id returned by memory_request_upgrade.")],
|
||||
status: Annotated[str, Field(description="'resolved' | 'rejected'")],
|
||||
resolution: Annotated[str | None, Field(description="What was done, or why it was rejected (optional).")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Resolve a BigMind upgrade request — mark it done or rejected.
|
||||
|
||||
Args:
|
||||
request_id: The id returned by memory_request_upgrade.
|
||||
status: 'resolved' | 'rejected'
|
||||
resolution: What was done, or why it was rejected (optional).
|
||||
"""
|
||||
user = _current_user()
|
||||
try:
|
||||
@@ -952,10 +858,10 @@ def memory_get_profile_url() -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_announce_focus(
|
||||
session_id: str,
|
||||
description: str,
|
||||
files: list = None,
|
||||
ide_hint: str = None,
|
||||
session_id: Annotated[str, Field(description="The active session id (from memory_start_session)")],
|
||||
description: Annotated[str, Field(description="What you are about to work on (e.g. \"Implementing Feature 7 in db.py\")")],
|
||||
files: Annotated[list | None, Field(description="List of file paths you plan to touch (e.g. [\"bigmind/db.py\", \"src/server.py\"])")] = None,
|
||||
ide_hint: Annotated[str | None, Field(description="Optional label for this IDE (e.g. \"PyCharm\", \"IntelliJ\", \"VS Code\")")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Announce what this session is currently working on and which files it will touch.
|
||||
@@ -965,13 +871,6 @@ def memory_announce_focus(
|
||||
focus data. If another open session already has overlapping files, a warning
|
||||
is returned — stop and coordinate before proceeding.
|
||||
|
||||
args:
|
||||
- session_id: The active session id (from memory_start_session)
|
||||
- description: What you are about to work on (e.g. "Implementing Feature 7 in db.py")
|
||||
- files: List of file paths you plan to touch (e.g. ["bigmind/db.py", "src/server.py"])
|
||||
- ide_hint: Optional label for this IDE (e.g. "PyCharm", "IntelliJ", "VS Code")
|
||||
Shown on the profile page Live Sessions panel.
|
||||
|
||||
returns:
|
||||
- Acknowledgement with current focus set, or a conflict warning.
|
||||
"""
|
||||
@@ -1045,10 +944,10 @@ def memory_get_active_sessions() -> str:
|
||||
|
||||
@mcp.tool()
|
||||
def memory_log_token_save(
|
||||
session_id: str,
|
||||
description: str,
|
||||
tokens_saved: int,
|
||||
method_used: str = None,
|
||||
session_id: Annotated[str, Field(description="The active session id")],
|
||||
description: Annotated[str, Field(description="What was remembered or avoided (e.g. \"grep EuBP log instead of reading 80k lines\")")],
|
||||
tokens_saved: Annotated[int, Field(description="Rough estimate of tokens saved (e.g. 1_240_000)")],
|
||||
method_used: Annotated[str | None, Field(description="One of: 'memory_hit' | 'grep' | 'tail' | 'targeted_read' | 'other'")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Log a token efficiency event — record how many tokens were saved by using
|
||||
@@ -1062,12 +961,6 @@ def memory_log_token_save(
|
||||
Estimating tokens saved: tokens ≈ chars / 4.
|
||||
tokens_saved ≈ (chars_in_full_resource / 4) - (chars_in_result / 4)
|
||||
|
||||
args:
|
||||
- session_id: The active session id
|
||||
- description: What was remembered or avoided (e.g. "grep EuBP log instead of reading 80k lines")
|
||||
- tokens_saved: Rough estimate of tokens saved (e.g. 1_240_000)
|
||||
- method_used: One of: 'memory_hit' | 'grep' | 'tail' | 'targeted_read' | 'other'
|
||||
|
||||
returns:
|
||||
- Confirmation with running session total.
|
||||
"""
|
||||
@@ -1100,26 +993,17 @@ def memory_log_token_save(
|
||||
|
||||
@mcp.tool()
|
||||
def memory_remember_person(
|
||||
username: str,
|
||||
display_name: str = None,
|
||||
role: str = None,
|
||||
team: str = None,
|
||||
notes: str = None,
|
||||
bigmind_user: str = None,
|
||||
bigmind_url: str = None,
|
||||
username: Annotated[str, Field(description="Unique identifier (e.g. login name or first name).")],
|
||||
display_name: Annotated[str | None, Field(description="Full name (optional).")] = None,
|
||||
role: Annotated[str | None, Field(description="Job title or role (optional).")] = None,
|
||||
team: Annotated[str | None, Field(description="Team or project they belong to (optional).")] = None,
|
||||
notes: Annotated[str | None, Field(description="Free-form notes about this person (optional).")] = None,
|
||||
bigmind_user: Annotated[str | None, Field(description="Their BigMind username if they have an instance (optional).")] = None,
|
||||
bigmind_url: Annotated[str | None, Field(description="URL of their BigMind profile page (optional).")] = None,
|
||||
) -> str:
|
||||
"""
|
||||
Store or update a person in the contacts directory.
|
||||
Call this whenever you learn something new about a colleague or AI peer.
|
||||
|
||||
Args:
|
||||
username: Unique identifier (e.g. login name or first name).
|
||||
display_name: Full name (optional).
|
||||
role: Job title or role (optional).
|
||||
team: Team or project they belong to (optional).
|
||||
notes: Free-form notes about this person (optional).
|
||||
bigmind_user: Their BigMind username if they have an instance (optional).
|
||||
bigmind_url: URL of their BigMind profile page (optional).
|
||||
"""
|
||||
user = _current_user()
|
||||
person_id = memory_store.upsert_person(
|
||||
@@ -1131,13 +1015,9 @@ def memory_remember_person(
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_recall_person(query: str, limit: int = 10) -> str:
|
||||
def memory_recall_person(query: Annotated[str, Field(description="Search keywords (e.g. a name, team, or role).")], limit: Annotated[int, Field(description="Max results to return (default 10).")] = 10) -> str:
|
||||
"""
|
||||
Search the contacts directory by name, role, team, or notes.
|
||||
|
||||
Args:
|
||||
query: Search keywords (e.g. a name, team, or role).
|
||||
limit: Max results to return (default 10).
|
||||
"""
|
||||
user = _current_user()
|
||||
results = memory_store.recall_person(user["id"], query, limit)
|
||||
@@ -1185,15 +1065,10 @@ def memory_list_people() -> str:
|
||||
|
||||
|
||||
@mcp.tool()
|
||||
def memory_link_ai(username: str, bigmind_user: str, bigmind_url: str = None) -> str:
|
||||
def memory_link_ai(username: Annotated[str, Field(description="The contact's username in your directory.")], bigmind_user: Annotated[str, Field(description="Their BigMind username.")], bigmind_url: Annotated[str | None, Field(description="URL of their BigMind profile page (optional).")] = None) -> str:
|
||||
"""
|
||||
Link a contact to their BigMind AI instance.
|
||||
The contact must already exist (use memory_remember_person first).
|
||||
|
||||
Args:
|
||||
username: The contact's username in your directory.
|
||||
bigmind_user: Their BigMind username.
|
||||
bigmind_url: URL of their BigMind profile page (optional).
|
||||
"""
|
||||
user = _current_user()
|
||||
found = memory_store.link_ai(user["id"], username, bigmind_user, bigmind_url)
|
||||
|
||||
Reference in New Issue
Block a user