Skip to main content
Glama
lamaalrajih

KiCad MCP Server

by lamaalrajih

list_projects

Locate and display all KiCad electronic design projects stored on your system to help users quickly access their PCB design files.

Instructions

Find and list all KiCad projects on this system.

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault

No arguments

Output Schema

TableJSON Schema
NameRequiredDescriptionDefault
resultYes

Implementation Reference

  • The main handler function for the 'list_projects' tool, decorated with @mcp.tool(). It calls find_kicad_projects() and returns the list of projects.
    @mcp.tool()
    def list_projects() -> List[Dict[str, Any]]:
        """Find and list all KiCad projects on this system."""
        logging.info(f"Executing list_projects tool...")
        projects = find_kicad_projects()
        logging.info(f"list_projects tool returning {len(projects)} projects.")
        return projects
  • The call to register_project_tools which registers the list_projects tool among others.
    register_project_tools(mcp)
  • The core helper function find_kicad_projects() that scans configured directories for KiCad project files (.kicad_pro) and returns a list of project dictionaries.
    def find_kicad_projects() -> List[Dict[str, Any]]:
        """Find KiCad projects in the user's directory.
        
        Returns:
            List of dictionaries with project information
        """
        projects = []
        logging.info("Attempting to find KiCad projects...") # Log start
        # Search directories to look for KiCad projects
        raw_search_dirs = [config.KICAD_USER_DIR] + config.ADDITIONAL_SEARCH_PATHS
        logging.info(f"Raw KICAD_USER_DIR: '{config.KICAD_USER_DIR}'")
        logging.info(f"Raw ADDITIONAL_SEARCH_PATHS: {config.ADDITIONAL_SEARCH_PATHS}")
        logging.info(f"Raw search list before expansion: {raw_search_dirs}")
    
        expanded_search_dirs = []
        for raw_dir in raw_search_dirs:
            expanded_dir = os.path.expanduser(raw_dir) # Expand ~ and ~user
            if expanded_dir not in expanded_search_dirs:
                expanded_search_dirs.append(expanded_dir)
            else:
                logging.info(f"Skipping duplicate expanded path: {expanded_dir}")
                
        logging.info(f"Expanded search directories: {expanded_search_dirs}")
    
        for search_dir in expanded_search_dirs:
            if not os.path.exists(search_dir):
                logging.warning(f"Expanded search directory does not exist: {search_dir}") # Use warning level
                continue
            
            logging.info(f"Scanning expanded directory: {search_dir}")
            # Use followlinks=True to follow symlinks if needed
            for root, _, files in os.walk(search_dir, followlinks=True):
                for file in files:
                    if file.endswith(config.KICAD_EXTENSIONS["project"]):
                        project_path = os.path.join(root, file)
                        # Check if it's a real file and not a broken symlink
                        if not os.path.isfile(project_path):
                            logging.info(f"Skipping non-file/broken symlink: {project_path}")
                            continue
                        
                        try:
                            # Attempt to get modification time to ensure file is accessible
                            mod_time = os.path.getmtime(project_path)
                            rel_path = os.path.relpath(project_path, search_dir)
                            project_name = get_project_name_from_path(project_path)
    
                            logging.info(f"Found accessible KiCad project: {project_path}")
                            projects.append({
                                "name": project_name,
                                "path": project_path,
                                "relative_path": rel_path,
                                "modified": mod_time
                            })
                        except OSError as e:
                            logging.error(f"Error accessing project file {project_path}: {e}") # Use error level
                            continue # Skip if we can't access it
        
        logging.info(f"Found {len(projects)} KiCad projects after scanning.")
        return projects
  • The registration function that defines and registers the project tools including list_projects via @mcp.tool() decorators.
    def register_project_tools(mcp: FastMCP) -> None:
        """Register project management tools with the MCP server.
        
        Args:
            mcp: The FastMCP server instance
        """
Behavior2/5

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

No annotations are provided, so the description carries the full burden of behavioral disclosure. It mentions 'Find and list all KiCad projects on this system,' which implies a read-only operation, but doesn't specify details like whether it searches recursively, includes hidden files, returns metadata, or has performance considerations. For a tool with zero annotation coverage, this leaves significant gaps in understanding its behavior.

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?

The description is a single, clear sentence that efficiently conveys the core action and resource without any wasted words. It's front-loaded with the key information ('Find and list all KiCad projects'), making it easy to grasp quickly, and every part of the sentence serves a purpose.

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

Completeness3/5

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

Given the tool has 0 parameters, 100% schema coverage, and an output schema exists, the description doesn't need to cover parameters or return values. However, as a read operation with no annotations, it lacks details on behavioral aspects like search scope or output format. It's minimally adequate but could benefit from more context to fully guide usage.

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?

The tool has 0 parameters, and schema description coverage is 100%, so there's no need for parameter details in the description. The description appropriately doesn't discuss parameters, focusing on the tool's purpose instead. A baseline of 4 is applied since no parameters exist, and it avoids unnecessary repetition of schema information.

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

Purpose4/5

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

The description clearly states the tool's purpose with a specific verb ('Find and list') and resource ('all KiCad projects on this system'), making it easy to understand what it does. However, it doesn't explicitly differentiate from sibling tools like 'get_project_structure' or 'open_project', which might also involve project-related operations, so it doesn't reach the highest score.

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

Usage Guidelines2/5

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

The description provides no guidance on when to use this tool versus alternatives. With siblings like 'get_project_structure' and 'open_project' that might overlap in project-related contexts, there's no indication of when this listing tool is preferred or what its specific scope (e.g., system-wide vs. workspace) entails, leaving usage ambiguous.

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/lamaalrajih/kicad-mcp'

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