Skip to content

Commit 402e6cb

Browse files
committed
improve tool doc for project info
Signed-off-by: phernandez <paul@basicmachines.co>
1 parent 8cb3568 commit 402e6cb

13 files changed

Lines changed: 83 additions & 89 deletions

src/basic_memory/mcp/project_context.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,7 @@ async def resolve_project_parameter(project: Optional[str] = None) -> Optional[s
2020
"""Resolve project parameter using three-tier hierarchy.
2121
2222
Resolution order:
23-
1. CLI constraint (BASIC_MEMORY_MCP_PROJECT env var) - highest priority
23+
1. Single Project Mode (--project cli arg, or BASIC_MEMORY_MCP_PROJECT env var) - highest priority
2424
2. Explicit project parameter - medium priority
2525
3. Default project if default_project_mode=true - lowest priority
2626

src/basic_memory/mcp/tools/build_context.py

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -50,11 +50,15 @@ async def build_context(
5050
5151
This tool enables natural continuation of discussions by loading relevant context
5252
from memory:// URIs. It uses pattern matching to find relevant content and builds
53-
a rich context graph of related information. Uses stateless architecture - each
54-
call requires explicit project parameter.
53+
a rich context graph of related information.
54+
55+
Project Resolution:
56+
Server resolves projects in this order: Single Project Mode → project parameter → default project.
57+
If project unknown, use list_memory_projects() or recent_activity() first.
5558
5659
Args:
57-
project: Required project name to build context from. Must be an existing project.
60+
project: Project name to build context from. Optional - server will resolve using hierarchy.
61+
If unknown, use list_memory_projects() to discover available projects.
5862
url: memory:// URI pointing to discussion content (e.g. memory://specs/search)
5963
depth: How many relation hops to traverse (1-3 recommended for performance)
6064
timeframe: How far back to look. Supports natural language like "2 days ago", "last week"

src/basic_memory/mcp/tools/canvas.py

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,12 +30,16 @@ async def canvas(
3030
3131
This tool creates a .canvas file compatible with Obsidian's Canvas feature,
3232
allowing visualization of relationships between concepts or documents.
33-
Uses stateless architecture - each call requires explicit project parameter.
33+
34+
Project Resolution:
35+
Server resolves projects in this order: Single Project Mode → project parameter → default project.
36+
If project unknown, use list_memory_projects() or recent_activity() first.
3437
3538
For the full JSON Canvas 1.0 specification, see the 'spec://canvas' resource.
3639
3740
Args:
38-
project: Required project name to create canvas in. Must be an existing project.
41+
project: Project name to create canvas in. Optional - server will resolve using hierarchy.
42+
If unknown, use list_memory_projects() to discover available projects.
3943
nodes: List of node objects following JSON Canvas 1.0 spec
4044
edges: List of edge objects following JSON Canvas 1.0 spec
4145
title: The title of the canvas (will be saved as title.canvas)

src/basic_memory/mcp/tools/delete_note.py

Lines changed: 8 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -154,15 +154,17 @@ async def delete_note(
154154
) -> bool | str:
155155
"""Delete a note from the knowledge base.
156156
157-
Permanently removes a note from the specified project. Uses stateless
158-
architecture - each call requires explicit project parameter.
157+
Permanently removes a note from the specified project. The note is identified
158+
by title or permalink. If the note doesn't exist, the operation returns False
159+
without error. If deletion fails due to other issues, helpful error messages are provided.
159160
160-
The note is identified by title or permalink. If the note doesn't exist,
161-
the operation returns False without error. If deletion fails due to other
162-
issues, helpful error messages are provided.
161+
Project Resolution:
162+
Server resolves projects in this order: Single Project Mode → project parameter → default project.
163+
If project unknown, use list_memory_projects() or recent_activity() first.
163164
164165
Args:
165-
project: Required project name to delete from. Must be an existing project.
166+
project: Project name to delete from. Optional - server will resolve using hierarchy.
167+
If unknown, use list_memory_projects() to discover available projects.
166168
identifier: Note title or permalink to delete
167169
Can be a title like "Meeting Notes" or permalink like "notes/meeting-notes"
168170
context: Optional FastMCP context for performance caching.

src/basic_memory/mcp/tools/edit_note.py

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -142,10 +142,10 @@ async def edit_note(
142142
"""Edit an existing markdown note in the knowledge base.
143143
144144
Makes targeted changes to existing notes without rewriting the entire content.
145-
Supports three project resolution modes:
146-
1. Explicit project parameter (highest priority)
147-
2. Default project mode (if enabled in config)
148-
3. CLI constraint mode (--project flag)
145+
146+
Project Resolution:
147+
Server resolves projects in this order: Single Project Mode → project parameter → default project.
148+
If project unknown, use list_memory_projects() or recent_activity() first.
149149
150150
Args:
151151
identifier: The exact title, permalink, or memory:// URL of the note to edit.
@@ -157,8 +157,8 @@ async def edit_note(
157157
- "find_replace": Replace occurrences of find_text with content
158158
- "replace_section": Replace content under a specific markdown header
159159
content: The content to add or use for replacement
160-
project: Optional project name. If not provided, uses default_project (if default_project_mode=true)
161-
. If unknown, use list_memory_projects() to discover available projects.
160+
project: Project name to edit in. Optional - server will resolve using hierarchy.
161+
If unknown, use list_memory_projects() to discover available projects.
162162
section: For replace_section operation - the markdown header to replace content under (e.g., "## Notes", "### Implementation")
163163
find_text: For find_replace operation - the text to find and replace
164164
expected_replacements: For find_replace operation - the expected number of replacements (validation will fail if actual doesn't match)

src/basic_memory/mcp/tools/list_directory.py

Lines changed: 3 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,7 @@ async def list_directory(
2525
2626
This tool provides 'ls' functionality for browsing the knowledge base directory structure.
2727
It can list immediate children or recursively explore subdirectories with depth control,
28-
and supports glob pattern filtering for finding specific files. Uses stateless architecture -
29-
each call requires explicit project parameter.
28+
and supports glob pattern filtering for finding specific files.
3029
3130
Args:
3231
dir_name: Directory path to list (default: root "/")
@@ -35,9 +34,8 @@ async def list_directory(
3534
Higher values show subdirectory contents recursively
3635
file_name_glob: Optional glob pattern for filtering file names
3736
Examples: "*.md", "*meeting*", "project_*"
38-
project: Optional project name to list directory from. If not provided, uses default_project
39-
(if default_project_mode=true). If unknown, use list_memory_projects()
40-
to discover available projects.
37+
project: Project name to list directory from. Optional - server will resolve using hierarchy.
38+
If unknown, use list_memory_projects() to discover available projects.
4139
context: Optional FastMCP context for performance caching.
4240
4341
Returns:

src/basic_memory/mcp/tools/move_note.py

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -349,16 +349,15 @@ async def move_note(
349349
350350
Moves a note from one location to another within the project, updating all
351351
database references and maintaining semantic content. Uses stateless architecture -
352-
each call requires explicit project parameter.
352+
project parameter optional with server resolution.
353353
354354
Args:
355355
identifier: Exact entity identifier (title, permalink, or memory:// URL).
356356
Must be an exact match - fuzzy matching is not supported for move operations.
357357
Use search_notes() or read_note() first to find the correct identifier if uncertain.
358358
destination_path: New path relative to project root (e.g., "work/meetings/2025-05-26.md")
359-
project: Optional project name to move within. If not provided, uses default_project
360-
(if default_project_mode=true). If unknown, use list_memory_projects()
361-
to discover available projects.
359+
project: Project name to move within. Optional - server will resolve using hierarchy.
360+
If unknown, use list_memory_projects() to discover available projects.
362361
context: Optional FastMCP context for performance caching.
363362
364363
Returns:

src/basic_memory/mcp/tools/read_content.py

Lines changed: 3 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -156,7 +156,7 @@ async def read_content(
156156
157157
This tool provides direct access to file content in the knowledge base,
158158
handling different file types appropriately. Uses stateless architecture -
159-
each call requires explicit project parameter.
159+
project parameter optional with server resolution.
160160
161161
Supported file types:
162162
- Text files (markdown, code, etc.) are returned as plain text
@@ -168,9 +168,8 @@ async def read_content(
168168
- A regular file path (docs/example.md)
169169
- A memory URL (memory://docs/example)
170170
- A permalink (docs/example)
171-
project: Optional project name to read from. If not provided, uses default_project
172-
(if default_project_mode=true). If unknown, use list_memory_projects()
173-
to discover available projects.
171+
project: Project name to read from. Optional - server will resolve using hierarchy.
172+
If unknown, use list_memory_projects() to discover available projects.
174173
context: Optional FastMCP context for performance caching.
175174
176175
Returns:

src/basic_memory/mcp/tools/read_note.py

Lines changed: 6 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -29,24 +29,20 @@ async def read_note(
2929
3030
Finds and retrieves a note by its title, permalink, or content search,
3131
returning the raw markdown content including observations, relations, and metadata.
32-
Uses stateless architecture - each call requires explicit project parameter.
3332
34-
Project Selection:
35-
If you don't know which project to use:
36-
1. Call list_memory_projects() to discover available projects
37-
2. Or call recent_activity() to see project activity and get recommendations
38-
3. Ask the user which project to read from
39-
4. Remember their choice for the entire conversation session
40-
5. Only ask again if the user explicitly mentions switching projects
33+
Project Resolution:
34+
Server resolves projects in this order: Single Project Mode → project parameter → default project.
35+
If project unknown, use list_memory_projects() or recent_activity() first.
4136
4237
This tool will try multiple lookup strategies to find the most relevant note:
4338
1. Direct permalink lookup
4439
2. Title search fallback
4540
3. Text search as last resort
4641
4742
Args:
48-
project: Required project name to read from. Must be an existing project.
49-
If unknown, use list_memory_projects() to discover available projects.
43+
project: Project name to read from. Optional - server will resolve using the
44+
hierarchy above. If unknown, use list_memory_projects() to discover
45+
available projects.
5046
identifier: The title or permalink of the note to read
5147
Can be a full memory:// URL, a permalink, a title, or search text
5248
page: Page number for paginated results (default: 1)

src/basic_memory/mcp/tools/recent_activity.py

Lines changed: 25 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -40,13 +40,21 @@ async def recent_activity(
4040
) -> str:
4141
"""Get recent activity for a specific project or across all projects.
4242
43-
This tool works in two modes based on the project parameter:
44-
45-
**Discovery Mode (project=None)**: Returns activity summary across all projects,
46-
enabling project discovery and cross-project activity overview.
47-
48-
**Project-Specific Mode (project provided)**: Returns detailed activity for a
49-
specific project with filtering and graph traversal capabilities.
43+
Project Resolution:
44+
The server resolves projects in this order:
45+
1. Single Project Mode - server constrained to one project, parameter ignored
46+
2. Explicit project parameter - specify which project to query
47+
3. Default project - server configured default if no project specified
48+
49+
Discovery Mode:
50+
When no specific project can be resolved, returns activity across all projects
51+
to help discover available projects and their recent activity.
52+
53+
Project Discovery (when project is unknown):
54+
1. Call list_memory_projects() to see available projects
55+
2. Or use this tool without project parameter to see cross-project activity
56+
3. Ask the user which project to focus on
57+
4. Remember their choice for the conversation
5058
5159
Args:
5260
type: Filter by content type(s). Can be a string or list of strings.
@@ -62,34 +70,30 @@ async def recent_activity(
6270
- Relative: "2 days ago", "last week", "yesterday"
6371
- Points in time: "2024-01-01", "January 1st"
6472
- Standard format: "7d", "24h"
65-
project: Optional project name. If not provided, uses default_project (if default_project_mode=true)
66-
or returns activity across all projects for discovery.
67-
If unknown, use list_memory_projects() to discover available projects.
73+
project: Project name to query. Optional - server will resolve using the
74+
hierarchy above. If unknown, use list_memory_projects() to discover
75+
available projects.
6876
context: Optional FastMCP context for performance caching.
6977
7078
Returns:
71-
- ProjectActivitySummary: When project=None (discovery mode)
72-
- GraphContext: When project is specified (project-specific mode)
79+
Human-readable summary of recent activity. When no specific project is
80+
resolved, returns cross-project discovery information. When a specific
81+
project is resolved, returns detailed activity for that project.
7382
7483
Examples:
75-
# Default project mode or discovery mode
84+
# Cross-project discovery mode
7685
recent_activity()
7786
recent_activity(timeframe="yesterday")
7887
79-
# Project-specific mode - detailed activity for one project
80-
recent_activity(type="entity", timeframe="yesterday")
81-
recent_activity(type=["entity"], timeframe="yesterday")
82-
recent_activity(type=["relation", "observation"], timeframe="today")
83-
recent_activity(type="entity", depth=2, timeframe="2 weeks ago")
84-
85-
# Explicit project specification
88+
# Project-specific activity
8689
recent_activity(project="work-docs", type="entity", timeframe="yesterday")
90+
recent_activity(project="research", type=["entity", "relation"], timeframe="today")
91+
recent_activity(project="notes", type="entity", depth=2, timeframe="2 weeks ago")
8792
8893
Raises:
8994
ToolError: If project doesn't exist or type parameter contains invalid values
9095
9196
Notes:
92-
- Discovery mode enables project selection without session state
9397
- Higher depth values (>3) may impact performance with large result sets
9498
- For focused queries, consider using build_context with a specific URI
9599
- Max timeframe is 1 year in the past

0 commit comments

Comments
 (0)