zotero_advanced_search
Search your Zotero research library with advanced criteria, combining multiple conditions to filter, sort, and retrieve precise results efficiently.
Instructions
Perform an advanced search with multiple criteria.
Input Schema
TableJSON Schema
| Name | Required | Description | Default |
|---|---|---|---|
| conditions | Yes | ||
| join_mode | No | all | |
| limit | No | ||
| sort_by | No | ||
| sort_direction | No | asc |
Implementation Reference
- src/zotero_mcp/server.py:918-1079 (handler)The main handler function for the 'zotero_advanced_search' tool. It creates a temporary saved search in Zotero using the provided conditions, executes it, formats the results in markdown, and cleans up the saved search afterward.name="zotero_advanced_search", description="Perform an advanced search with multiple criteria." ) def advanced_search( conditions: List[Dict[str, str]], join_mode: Literal["all", "any"] = "all", sort_by: Optional[str] = None, sort_direction: Literal["asc", "desc"] = "asc", limit: Union[int, str] = 50, *, ctx: Context ) -> str: """ Perform an advanced search with multiple criteria. Args: conditions: List of search condition dictionaries, each containing: - field: The field to search (title, creator, date, tag, etc.) - operation: The operation to perform (is, isNot, contains, etc.) - value: The value to search for join_mode: Whether all conditions must match ("all") or any condition can match ("any") sort_by: Field to sort by (dateAdded, dateModified, title, creator, etc.) sort_direction: Direction to sort (asc or desc) limit: Maximum number of results to return ctx: MCP context Returns: Markdown-formatted search results """ try: if not conditions: return "Error: No search conditions provided" ctx.info(f"Performing advanced search with {len(conditions)} conditions") zot = get_zotero_client() # Prepare search parameters params = {} # Add sorting parameters if specified if sort_by: params["sort"] = sort_by params["direction"] = sort_direction if isinstance(limit, str): limit = int(limit) # Add limit parameter params["limit"] = limit # Build search conditions search_conditions = [] for i, condition in enumerate(conditions): if "field" not in condition or "operation" not in condition or "value" not in condition: return f"Error: Condition {i+1} is missing required fields (field, operation, value)" # Map common field names to Zotero API fields if needed field = condition["field"] operation = condition["operation"] value = condition["value"] # Handle special fields if field == "author" or field == "creator": field = "creator" elif field == "year": field = "date" # Convert year to partial date format for matching value = str(value) search_conditions.append({ "condition": field, "operator": operation, "value": value }) # Add join mode condition search_conditions.append({ "condition": "joinMode", "operator": join_mode, "value": "" }) # Create a saved search search_name = f"temp_search_{uuid.uuid4().hex[:8]}" saved_search = zot.saved_search( search_name, search_conditions ) # Extract the search key from the result if not saved_search.get("success"): return f"Error creating saved search: {saved_search.get('failed', 'Unknown error')}" search_key = next(iter(saved_search.get("success", {}).values()), None) # Execute the saved search try: results = zot.collection_items(search_key) finally: # Clean up the temporary saved search try: zot.delete_saved_search([search_key]) except Exception as cleanup_error: ctx.warn(f"Error cleaning up saved search: {str(cleanup_error)}") # Format the results if not results: return "No items found matching the search criteria." output = ["# Advanced Search Results", ""] output.append(f"Found {len(results)} items matching the search criteria:") output.append("") # Add search criteria summary output.append("## Search Criteria") output.append(f"Join mode: {join_mode.upper()}") for i, condition in enumerate(conditions, 1): output.append(f"{i}. {condition['field']} {condition['operation']} \"{condition['value']}\"") output.append("") # Format results output.append("## Results") for i, item in enumerate(results, 1): data = item.get("data", {}) title = data.get("title", "Untitled") item_type = data.get("itemType", "unknown") date = data.get("date", "No date") key = item.get("key", "") # Format creators creators = data.get("creators", []) creators_str = format_creators(creators) # Build the formatted entry output.append(f"### {i}. {title}") output.append(f"**Type:** {item_type}") output.append(f"**Item Key:** {key}") output.append(f"**Date:** {date}") output.append(f"**Authors:** {creators_str}") # Add abstract snippet if present if abstract := data.get("abstractNote"): # Limit abstract length for search results abstract_snippet = abstract[:150] + "..." if len(abstract) > 150 else abstract output.append(f"**Abstract:** {abstract_snippet}") # Add tags if present if tags := data.get("tags"): tag_list = [f"`{tag['tag']}`" for tag in tags] if tag_list: output.append(f"**Tags:** {' '.join(tag_list)}") output.append("") # Empty line between items return "\n".join(output) except Exception as e: ctx.error(f"Error in advanced search: {str(e)}") return f"Error in advanced search: {str(e)}"
- src/zotero_mcp/server.py:918-920 (registration)The @mcp.tool decorator registers the advanced_search function as the 'zotero_advanced_search' tool.name="zotero_advanced_search", description="Perform an advanced search with multiple criteria." )