Skip to main content
Glama

search_notes

Find existing Anki flashcards using Anki's search syntax to locate notes by content, deck, tags, or card state.

Instructions

Search for notes in Anki using the powerful built-in search syntax.

This tool allows you to find existing notes/flashcards using Anki's query language. Results include note IDs which can be used for follow-up actions. ## Common Search Patterns **Simple text search:** - `dog` - notes containing "dog" (matches "doggy", "underdog") - `dog cat` - notes with both "dog" AND "cat" - `dog or cat` - notes with "dog" OR "cat" - `-cat` - notes WITHOUT "cat" - `"a dog"` - exact phrase match - `w:dog` - whole word match only **Field-specific search:** - `front:dog` - Front field exactly equals "dog" - `front:*dog*` - Front field contains "dog" - `front:` - Front field is empty - `front:_*` - Front field is non-empty **Deck and tag filters:** - `deck:French` - cards in French deck (including subdecks) - `deck:French -deck:French::*` - only top-level French deck - `tag:vocab` - notes with "vocab" tag - `tag:none` - notes without any tags - `note:Basic` - notes using "Basic" note type **Card state:** - `is:due` - cards due for review - `is:new` - new cards not yet studied - `is:learn` - cards in learning phase - `is:review` - review cards - `is:suspended` - suspended cards - `is:buried` - buried cards **Card properties:** - `prop:ivl>=10` - interval >= 10 days - `prop:due=0` - due today - `prop:due=1` - due tomorrow - `prop:lapses>3` - lapsed more than 3 times - `prop:ease<2.5` - easier than default - `prop:reps<10` - reviewed fewer than 10 times **Recent activity:** - `added:7` - added in last 7 days - `edited:3` - edited in last 3 days - `rated:1` - answered today - `rated:7:1` - answered "Again" in last 7 days - `introduced:30` - first answered in last 30 days **Combining searches:** - `deck:Spanish tag:verb is:due` - due Spanish verbs - `added:7 -is:review` - new cards added this week - `(dog or cat) deck:Animals` - dog or cat in Animals deck Args: query: The Anki search query string. limit: Maximum notes to return (1-100, default 20). Returns: JSON array of matching notes with their fields, tags, and note IDs.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
queryYesAnki search query string
limitNoMaximum number of notes to return

Implementation Reference

  • Registers the search_notes tool with FastMCP using the @mcp.tool() decorator. The handle_anki_connection_error decorator wraps it for error handling.
    @mcp.tool()
  • The core handler function for the search_notes tool. It uses AnkiConnect to find notes matching the query, limits the results, fetches note info, formats them, and returns a JSON string with the results.
    async def search_notes( query: str = Field(description="Anki search query string"), limit: int = Field(default=20, ge=1, le=100, description="Maximum number of notes to return"), ) -> str: """Search for notes in Anki using the powerful built-in search syntax. This tool allows you to find existing notes/flashcards using Anki's query language. Results include note IDs which can be used for follow-up actions. ## Common Search Patterns **Simple text search:** - `dog` - notes containing "dog" (matches "doggy", "underdog") - `dog cat` - notes with both "dog" AND "cat" - `dog or cat` - notes with "dog" OR "cat" - `-cat` - notes WITHOUT "cat" - `"a dog"` - exact phrase match - `w:dog` - whole word match only **Field-specific search:** - `front:dog` - Front field exactly equals "dog" - `front:*dog*` - Front field contains "dog" - `front:` - Front field is empty - `front:_*` - Front field is non-empty **Deck and tag filters:** - `deck:French` - cards in French deck (including subdecks) - `deck:French -deck:French::*` - only top-level French deck - `tag:vocab` - notes with "vocab" tag - `tag:none` - notes without any tags - `note:Basic` - notes using "Basic" note type **Card state:** - `is:due` - cards due for review - `is:new` - new cards not yet studied - `is:learn` - cards in learning phase - `is:review` - review cards - `is:suspended` - suspended cards - `is:buried` - buried cards **Card properties:** - `prop:ivl>=10` - interval >= 10 days - `prop:due=0` - due today - `prop:due=1` - due tomorrow - `prop:lapses>3` - lapsed more than 3 times - `prop:ease<2.5` - easier than default - `prop:reps<10` - reviewed fewer than 10 times **Recent activity:** - `added:7` - added in last 7 days - `edited:3` - edited in last 3 days - `rated:1` - answered today - `rated:7:1` - answered "Again" in last 7 days - `introduced:30` - first answered in last 30 days **Combining searches:** - `deck:Spanish tag:verb is:due` - due Spanish verbs - `added:7 -is:review` - new cards added this week - `(dog or cat) deck:Animals` - dog or cat in Animals deck Args: query: The Anki search query string. limit: Maximum notes to return (1-100, default 20). Returns: JSON array of matching notes with their fields, tags, and note IDs. """ async with get_anki_client() as anki: logger.debug(f"Searching notes with query: {query}") note_ids = await anki.find_notes(query=query) logger.info(f"Found {len(note_ids)} notes for query: {query}") if not note_ids: return json.dumps({ "query": query, "total_found": 0, "notes": [], "message": "No notes found matching the query." }, indent=2) # Limit results limited_note_ids = note_ids[:limit] # Fetch note details notes_info = await anki.notes_info(limited_note_ids) # Format results formatted_results = _format_search_results(notes_info) result = { "query": query, "total_found": len(note_ids), "returned": len(formatted_results), "notes": formatted_results, } if len(note_ids) > limit: result["message"] = f"Showing {limit} of {len(note_ids)} matching notes. Refine your query or increase limit for more results." return json.dumps(result, indent=2, ensure_ascii=False)
  • Input schema defined using Pydantic Field for the query parameter (required string) and optional limit (int, 1-100, default 20). Output is a formatted JSON string.
    query: str = Field(description="Anki search query string"), limit: int = Field(default=20, ge=1, le=100, description="Maximum number of notes to return"), ) -> str:
  • Helper function used by search_notes to format the retrieved notes_info into a list of simplified dictionaries including noteId, modelName, cleaned fields, and tags.
    def _format_search_results(notes_info: List[dict]) -> List[dict]: """Formats note search results for LLM consumption. Includes note IDs to enable follow-up actions like editing or deletion. """ results = [] for note in notes_info: processed_fields = {} for name, field_data in note.get("fields", {}).items(): value = field_data.get("value", "") # Clean up code formatting for readability processed_value = value.replace("<pre><code>", "<code>").replace("</code></pre>", "</code>") processed_fields[name] = processed_value result = { "noteId": note.get("noteId"), "modelName": note.get("modelName", "UnknownModel"), "fields": processed_fields, "tags": note.get("tags", []), } results.append(result) return results

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/samefarrar/mcp-ankiconnect'

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