Skip to main content
Glama

Remember

remember
Idempotent

Store user preferences, project details, and context persistently for future conversations. Extracts key information from natural language to maintain continuity across sessions.

Instructions

Store user information persistently for future conversations. When users share preferences, coding standards, project details, or any context they want remembered, use this tool. Extract the key information from natural language and store it appropriately. The system automatically detects scope (user/workspace) and language specificity from context. For ambiguous cases, you will receive clarification prompts to ask the user. Examples of what to remember: coding preferences ('I like detailed docstrings'), project specifics ('This app uses PostgreSQL'), language standards ('For Python, use type hints'), workflow preferences ('Always run tests before committing'). Use only the memory_item parameter with natural language - the system handles scope detection.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
memory_itemYesThe information to remember
scopeNoMemory scope: 'user' (default) or 'workspace'user
languageNo

Output Schema

TableJSON Schema
NameRequiredDescriptionDefault
resultYes

Implementation Reference

  • Core implementation of the 'remember' tool: handles memory storage with automatic scope (user/workspace) detection, language support, validation, and error handling. Includes tool schema in annotations.
    @app.tool(
        name="remember",
        description=(
            "Store user information persistently for future conversations. When users share preferences, "
            "coding standards, project details, or any context they want remembered, use this tool. "
            "Extract the key information from natural language and store it appropriately. "
            "The system automatically detects scope (user/workspace) and language specificity from context. "
            "For ambiguous cases, you will receive clarification prompts to ask the user. "
            "Examples of what to remember: coding preferences ('I like detailed docstrings'), "
            "project specifics ('This app uses PostgreSQL'), language standards ('For Python, use type hints'), "
            "workflow preferences ('Always run tests before committing'). "
            "Use only the memory_item parameter with natural language - the system handles scope detection."
        ),
        tags={"public", "memory", "remember"},
        annotations={
            "idempotentHint": True,
            "readOnlyHint": False,
            "title": "Remember",
            "parameters": {
                "memory_item": "Extract and store the key information the user wants remembered. Use natural language, preserving important details and context.",
                "scope": "Usually omit this parameter - let the system auto-detect. Only specify 'workspace' for clearly project-specific items, 'user' for personal preferences.",
                "language": "Usually omit this parameter - let the system auto-detect. Only specify when the user explicitly mentions a programming language context.",
            },
            "returns": (
                "Returns confirmation of what was stored and where (global/workspace, language-specific if applicable). "
                "If the system detects ambiguous scope, you will receive a clarification request to ask the user. "
                "Always acknowledge what was remembered and explain how it will help in future conversations."
            ),
        },
        meta={"category": "memory"},
    )
    async def remember(
        ctx: Context,
        memory_item: Annotated[str, "The information to remember"],
        scope: Annotated[str, "Memory scope: 'user' (default) or 'workspace'"] = "user",
        language: Annotated[Optional[str], "Optional programming language for language-specific memory"] = None,
    ) -> str:
        """Store a memory item with support for user/workspace scope and language-specific memory."""
        if read_only:
            return "Error: Server is running in read-only mode"
        if memory_item is None or memory_item.strip() == "":
            return "Error: No memory item provided."
    
        try:
            roots = await ctx.list_roots()
            logger.info(f"Available roots: {', '.join(str(r) for r in roots)} - Remembering: {memory_item} (scope: {scope}, language: {language})")
        except Exception as e:
            # Handle case where list_roots is not supported (e.g., in tests)
            logger.warning(f"Failed to get roots: {e} - Remembering: {memory_item} (scope: {scope}, language: {language})")
            roots = []
    
        # Validate scope and convert to enum
        try:
            scope_enum = MemoryScope(scope)
        except ValueError:
            return f"Error: Scope must be '{MemoryScope.user}' or '{MemoryScope.workspace}'."
    
        # If scope is ambiguous based on memory content, ask for clarification
        if scope_enum == MemoryScope.user and _seems_workspace_specific(memory_item):
            return f"The memory item '{memory_item}' seems project-specific. Should this be stored as workspace memory instead? Please clarify by calling remember again with scope='{MemoryScope.workspace}' if needed."
    
        try:
            if scope_enum == MemoryScope.user:
                result = await _create_user_memory(ctx, memory_item, language)
            else:  # workspace
                result = await _create_workspace_memory(ctx, memory_item, language)
    
            if result["status"] == "success":
                scope_desc = "workspace" if scope_enum == MemoryScope.workspace else "global"
                lang_desc = f" for {language}" if language else ""
                return f"Remembered: {memory_item}\nStored in {scope_desc} memory{lang_desc}.\nFile: {result['filename']}\nThis memory will be available to AI assistants when the memory instruction is active in VS Code."
            else:
                return f"Error: {result.get('message', 'Unknown error occurred')}"
    
        except Exception as e:
            return f"Error: Exception occurred: {str(e)}"
  • Registration entry point for all tools, including the call to register_remember_tools() which adds the 'remember' tool to the MCP server.
    def register_all_tools() -> None:
        """Register all tools with the server."""
        register_instruction_tools()
        register_chatmode_tools()
        register_library_tools()
        register_memory_tools()
        register_remember_tools()
  • Helper function to detect if a memory item is workspace-specific based on keywords, used for scope clarification.
    def _seems_workspace_specific(memory_item: str) -> bool:
        """Check if a memory item seems to be workspace/project-specific."""
        workspace_keywords = [
            "this project",
            "this workspace",
            "this codebase",
            "this repo",
            "this repository",
            "our project",
            "our codebase",
            "our team",
            "we use",
            "we prefer",
            "project uses",
            "project requires",
            "workspace",
            "locally",
            "in this app",
            "in this application",
            "this service",
        ]
    
        return any(keyword in memory_item.lower() for keyword in workspace_keywords)
  • Helper to create user-scope memory using the instruction manager.
    async def _create_user_memory(ctx: Context, memory_item: str, language: Optional[str] = None) -> dict:
        """Create user-level memory (existing behavior with language support)."""
        registry = get_server_registry()
        instruction_manager = registry.instruction_manager
    
        try:
            result = await instruction_manager.create_memory_with_optimization(memory_item, ctx, scope=MemoryScope.user, language=language)
            return result
        except Exception as e:
            return {"status": "error", "message": str(e)}
  • Helper to create workspace-scope memory, extracting workspace root from MCP context.
    async def _create_workspace_memory(ctx: Context, memory_item: str, language: Optional[str] = None) -> dict:
        """Create workspace-level memory using the context root."""
        registry = get_server_registry()
        instruction_manager = registry.instruction_manager
    
        try:
            # Get the workspace root from context
            workspace_root_str: Optional[str] = None
            try:
                roots = await ctx.list_roots()
                if roots:
                    # Use the first root as the workspace root
                    root_uri = roots[0].uri
                    parsed = urlparse(root_uri.encoded_string())
                    host = "{0}{0}{mnt}{0}".format(os.path.sep, mnt=parsed.netloc)
                    normpath = os.path.normpath(os.path.join(host, url2pathname(unquote(parsed.path))))
                    workspace_root_str = normpath
            except Exception as e:
                logger.warning(f"Failed to get workspace root from context: {e}")
    
            logger.info(f"Using workspace root from context: {workspace_root_str}")
    
            # If we couldn't get a workspace root, return an error
            if workspace_root_str is None:
                return {"status": "error", "message": "Sorry, but I couldn't find the workspace root. Workspace memory requires access to the current workspace context."}
    
            result = await instruction_manager.create_memory_with_optimization(memory_item, ctx, scope=MemoryScope.workspace, language=language, workspace_root=workspace_root_str)
            return result
        except Exception as e:
            return {"status": "error", "message": str(e)}
Behavior4/5

Does the description disclose side effects, auth requirements, rate limits, or destructive behavior?

The description adds valuable behavioral context beyond annotations: explains that the system automatically detects scope and language specificity, mentions clarification prompts for ambiguous cases, and specifies that only the memory_item parameter should be used with natural language. This complements the annotations (readOnlyHint=false, idempotentHint=true) by describing how the tool behaves in practice.

Agents need to know what a tool does to the world before calling it. Descriptions should go beyond structured annotations to explain consequences.

Conciseness5/5

Is the description appropriately sized, front-loaded, and free of redundancy?

Well-structured with purpose first, then usage guidelines, then behavioral details, and finally examples and parameter guidance. Every sentence adds value with no redundancy. The description is appropriately sized for a tool with 3 parameters and rich functionality.

Shorter descriptions cost fewer tokens and are easier for agents to parse. Every sentence should earn its place.

Completeness5/5

Given the tool's complexity, does the description cover enough for an agent to succeed on first attempt?

Given the tool's complexity (persistent storage with automatic scope detection), the description provides complete guidance: purpose, when to use, behavioral characteristics, parameter usage, and examples. With annotations covering safety/idempotency and an output schema presumably handling return values, the description focuses appropriately on usage context rather than repeating structured information.

Complex tools with many parameters or behaviors need more documentation. Simple tools need less. This dimension scales expectations accordingly.

Parameters4/5

Does the description clarify parameter syntax, constraints, interactions, or defaults beyond what the schema provides?

With 67% schema description coverage, the description compensates well by explaining that 'memory_item' should contain natural language information to remember, and that scope detection is automatic. It clarifies that users should 'use only the memory_item parameter with natural language', which adds important usage semantics beyond the schema's technical descriptions.

Input schemas describe structure but not intent. Descriptions should explain non-obvious parameter relationships and valid value ranges.

Purpose5/5

Does the description clearly state what the tool does and how it differs from similar tools?

The description clearly states the verb 'store' and resource 'user information persistently', with specific examples of what can be stored (preferences, coding standards, project details). It distinguishes this tool from siblings by focusing on persistent memory storage rather than configuration or retrieval operations.

Agents choose between tools based on descriptions. A clear purpose with a specific verb and resource helps agents select the right tool.

Usage Guidelines5/5

Does the description explain when to use this tool, when not to, or what alternatives exist?

Explicitly states when to use: 'When users share preferences, coding standards, project details, or any context they want remembered'. Provides clear examples of appropriate use cases and specifies to use only the memory_item parameter with natural language. Also mentions the system handles scope detection automatically.

Agents often have multiple tools that could apply. Explicit usage guidance like "use X instead of Y when Z" prevents misuse.

Install Server

Other Tools

Latest Blog Posts

MCP directory API

We provide all the information about MCP servers via our MCP API.

curl -X GET 'https://glama.ai/api/mcp/v1/servers/NiclasOlofsson/mode-manager-mcp'

If you have feedback or need assistance with the MCP directory API, please join our Discord server