Skip to main content
Glama

search_content

Search for content in Alfresco using AFTS query language to find documents and files based on specific criteria.

Instructions

Search for content in Alfresco using AFTS query language.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
queryYes
max_resultsNo
node_typeNo

Implementation Reference

  • Core handler implementation: Performs Alfresco content search using AFTS query syntax. Validates inputs, ensures connection, executes search via search_client, formats results with node details (name, ID, type, created date). Handles progress reporting and errors.
    async def search_content_impl( search_query: str, max_results: int = 25, node_type: str = "cm:content", ctx: Optional[Context] = None ) -> str: """Search for content in Alfresco repository. Args: search_query: Search query string max_results: Maximum number of results to return (default: 25) node_type: Type of nodes to search for (default: "cm:content" - searches documents) ctx: MCP context for progress reporting Returns: Formatted search results """ # Parameter validation and extraction try: # Extract parameters with fallback handling if hasattr(search_query, 'value'): actual_query = str(search_query.value) else: actual_query = str(search_query) if hasattr(max_results, 'value'): actual_max_results = int(max_results.value) else: actual_max_results = int(max_results) if hasattr(node_type, 'value'): actual_node_type = str(node_type.value) else: actual_node_type = str(node_type) # Default to cm:content if empty if not actual_node_type.strip(): actual_node_type = "cm:content" # Clean and normalize for display (prevent Unicode encoding issues) safe_query_display = safe_format_output(str(actual_query)) safe_node_type_display = safe_format_output(str(actual_node_type)) except Exception as e: logger.error(f"Parameter extraction error: {e}") return safe_format_output(f"ERROR: Parameter error: {str(e)}") if not actual_query.strip(): return """Content Search Tool Usage: Provide a search query to search Alfresco repository content. Example searches: - admin (finds items with 'admin' in name or content) - name:test* (finds items with names starting with 'test') - modified:[2024-01-01 TO 2024-12-31] (finds items modified in 2024) - TYPE:"cm:content" (finds all documents) - TYPE:"cm:folder" (finds all folders) Search uses AFTS (Alfresco Full Text Search) syntax for flexible content discovery. By default, searches for documents (cm:content) unless a different type is specified. """ if ctx: await ctx.info(safe_format_output(f"Content search for: '{safe_query_display}'")) await ctx.report_progress(0.0) try: # Get all clients that ensure_connection() already created master_client = await ensure_connection() # Import search_utils from python_alfresco_api.utils import search_utils # Access the search client that was already created search_client = master_client.search logger.info(f"Content search for: '{safe_query_display}', type: '{safe_node_type_display}'") if ctx: await ctx.report_progress(0.3) # Build search query to include node_type filter final_query = actual_query # Add node_type filter if not already in query has_type_in_query = "TYPE:" in final_query.upper() if not has_type_in_query: if final_query == "*": final_query = f'TYPE:"{actual_node_type}"' else: final_query = f'({final_query}) AND TYPE:"{actual_node_type}"' # Use the correct working pattern: search_utils.simple_search with existing search_client try: search_results = search_utils.simple_search(search_client, final_query, max_items=actual_max_results) if search_results and hasattr(search_results, 'list_'): entries_list = search_results.list_.entries if search_results.list_ else [] logger.info(f"Found {len(entries_list)} content search results") if ctx: await ctx.report_progress(1.0) if not entries_list: return "0" result_text = f"Found {len(entries_list)} item(s) matching the search query:\n\n" for i, entry in enumerate(entries_list, 1): # Debug: Log the entry structure logger.debug(f"Entry {i} type: {type(entry)}, content: {entry}") # Handle different possible entry structures node = None if isinstance(entry, dict): if 'entry' in entry: node = entry['entry'] elif 'name' in entry: # Direct node structure node = entry else: logger.warning(f"Unknown entry structure: {entry}") continue elif hasattr(entry, 'entry'): # ResultSetRowEntry object node = entry.entry else: logger.warning(f"Entry is not a dict or ResultSetRowEntry: {type(entry)}") continue if node: # Handle both dict and ResultNode objects if isinstance(node, dict): name = str(node.get('name', 'Unknown')) node_id = str(node.get('id', 'Unknown')) node_type_actual = str(node.get('nodeType', 'Unknown')) created_at = str(node.get('createdAt', 'Unknown')) else: # ResultNode object - access attributes directly name = str(getattr(node, 'name', 'Unknown')) node_id = str(getattr(node, 'id', 'Unknown')) node_type_actual = str(getattr(node, 'node_type', 'Unknown')) created_at = str(getattr(node, 'created_at', 'Unknown')) # Clean JSON-friendly formatting (no markdown syntax) # Apply safe formatting to individual fields to prevent emoji encoding issues safe_name = safe_format_output(name) safe_node_id = safe_format_output(node_id) safe_node_type = safe_format_output(node_type_actual) safe_created_at = safe_format_output(created_at) result_text += f"{i}. {safe_name}\n" result_text += f" - ID: {safe_node_id}\n" result_text += f" - Type: {safe_node_type}\n" result_text += f" - Created: {safe_created_at}\n\n" return safe_format_output(result_text) else: return safe_format_output(f"ERROR: Content search failed - invalid response from Alfresco") except Exception as e: logger.error(f"Content search failed: {e}") return safe_format_output(f"ERROR: Content search failed: {str(e)}") except Exception as e: # Preserve Unicode characters in error messages error_msg = f"ERROR: Content search failed: {str(e)}" if ctx: await ctx.error(safe_format_output(error_msg)) return safe_format_output(error_msg) if ctx: await ctx.info(safe_format_output("Content search completed!"))
  • Tool registration using @mcp.tool decorator in FastMCP server. Defines input schema via type hints and docstring, delegates execution to search_content_impl.
    @mcp.tool async def search_content( query: str, max_results: int = 25, node_type: str = "", ctx: Context = None ) -> str: """Search for content in Alfresco using AFTS query language.""" return await search_content_impl(query, max_results, node_type, ctx)
  • Input schema defined by function parameters and type annotations for the search_content tool.
    async def search_content( query: str, max_results: int = 25, node_type: str = "", ctx: Context = None ) -> str: """Search for content in Alfresco using AFTS query language.""" return await search_content_impl(query, max_results, node_type, ctx)

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/stevereiner/python-alfresco-mcp-server'

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