Skip to main content
Glama
rishijatia

Fantasy Premier League MCP Server

search_fpl_players

Find Fantasy Premier League players by name with optional filters for position and team to help users identify and compare footballers for their fantasy team selection.

Instructions

Search for FPL players by name with optional filtering

    Args:
        query: Player name or partial name to search for
        position: Optional position filter (GKP, DEF, MID, FWD)
        team: Optional team name filter
        limit: Maximum number of results to return

    Returns:
        List of matching players with details
    

Input Schema

TableJSON Schema
NameRequiredDescriptionDefault
queryYes
positionNo
teamNo
limitNo

Implementation Reference

  • MCP tool handler for 'search_fpl_players'. Handles input validation for dictionary-wrapped query and delegates to the search_players helper function.
    async def search_fpl_players(
        query: str,
        position: Optional[str] = None,
        team: Optional[str] = None,
        limit: int = 5
    ) -> Dict[str, Any]:
        """Search for FPL players by name with optional filtering
    
        Args:
            query: Player name or partial name to search for
            position: Optional position filter (GKP, DEF, MID, FWD)
            team: Optional team name filter
            limit: Maximum number of results to return
    
        Returns:
            List of matching players with details
        """
        # Handle case when a dictionary is passed instead of string
        if isinstance(query, dict) and 'query' in query:
            query = query['query']
            
        return await search_players(query, position, team, limit)
  • Core helper function implementing the player search logic: fetches candidates via find_players_by_name, applies position and team filters, limits results, and formats the response.
    async def search_players(
        query: str,
        position: Optional[str] = None,
        team: Optional[str] = None,
        limit: int = 5
    ) -> Dict[str, Any]:
        """
        Search for players by name with optional filtering by position and team.
    
        Args:
            query: Player name or partial name to search for
            position: Optional position filter (GKP, DEF, MID, FWD)
            team: Optional team name filter
            limit: Maximum number of results to return
    
        Returns:
            List of matching players with details
        """
        logger = logging.getLogger(__name__)
        logger.info(f"Searching players: query={query}, position={position}, team={team}")
    
        # Find players by name
        matches = await find_players_by_name(query, limit=limit * 2)  # Get more than needed for filtering
    
        # Apply position filter if specified
        if position and matches:
            matches = [p for p in matches if p.get("position") == position.upper()]
    
        # Apply team filter if specified
        if team and matches:
            matches = [
                p for p in matches
                if team.lower() in p.get("team", "").lower() or
                team.lower() in p.get("team_short", "").lower()
            ]
    
        # Limit results
        matches = matches[:limit]
    
        return {
            "query": query,
            "filters": {
                "position": position,
                "team": team,
            },
            "total_matches": len(matches),
            "players": matches
        }
  • Module-level registration function that defines and registers the 'search_fpl_players' tool (and get_player_information) using @mcp.tool() decorator when called with the MCP instance.
    def register_tools(mcp):
        """Register player-related tools with MCP."""
        @mcp.tool()
        async def get_player_information(
            player_id: Optional[int] = None,
            player_name: Optional[str] = None,
            start_gameweek: Optional[int] = None,
            end_gameweek: Optional[int] = None,
            include_history: bool = True,
            include_fixtures: bool = True
        ) -> Dict[str, Any]:
            """Get detailed information and statistics for a specific player
    
            Args:
                player_id: FPL player ID (if provided, takes precedence over player_name)
                player_name: Player name to search for (used if player_id not provided)
                start_gameweek: Starting gameweek for filtering player history
                end_gameweek: Ending gameweek for filtering player history
                include_history: Whether to include gameweek-by-gameweek history
                include_fixtures: Whether to include upcoming fixtures
    
            Returns:
                Comprehensive player information including stats and history
            """
            # Handle case when a dictionary is passed instead of expected types
            if isinstance(player_name, dict):
                if 'player_name' in player_name:
                    player_name = player_name['player_name']
                elif 'query' in player_name:
                    player_name = player_name['query']
                    
            return await get_player_info(
                player_id,
                player_name,
                start_gameweek,
                end_gameweek,
                include_history,
                include_fixtures
            )
    
        @mcp.tool()
        async def search_fpl_players(
            query: str,
            position: Optional[str] = None,
            team: Optional[str] = None,
            limit: int = 5
        ) -> Dict[str, Any]:
            """Search for FPL players by name with optional filtering
    
            Args:
                query: Player name or partial name to search for
                position: Optional position filter (GKP, DEF, MID, FWD)
                team: Optional team name filter
                limit: Maximum number of results to return
    
            Returns:
                List of matching players with details
            """
            # Handle case when a dictionary is passed instead of string
            if isinstance(query, dict) and 'query' in query:
                query = query['query']
                
            return await search_players(query, position, team, limit)
    
    
    # Register tools
    register_tools = register_tools
  • Top-level registration call in the main MCP server entrypoint. register_player_tools is imported from fpl.tools.__init__.py (alias for players.py:register_tools) and invoked to register all player tools including 'search_fpl_players'.
    register_player_tools(mcp)
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 'search' and returns a list, implying a read-only operation, but doesn't address key behavioral aspects such as authentication requirements, rate limits, error handling, or pagination. For a tool with no annotation coverage, this is a significant gap in transparency.

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 well-structured and appropriately sized. It starts with a clear purpose statement, followed by a bulleted list of arguments and returns, with each sentence adding value. There's no redundant information, and it's easy to parse, making it highly efficient for an AI agent.

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 complexity (4 parameters, no annotations, no output schema), the description is moderately complete. It covers parameter semantics well but lacks behavioral context and output details. Without an output schema, it doesn't explain the structure of returned player details, leaving gaps. It's adequate for basic use but could be more comprehensive for a search tool in a multi-tool environment.

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

Parameters5/5

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

The description adds substantial meaning beyond the input schema, which has 0% schema description coverage. It explains each parameter's purpose: 'query' for player name search, 'position' with allowed values (GKP, DEF, MID, FWD), 'team' for filtering by team name, and 'limit' for result count. This compensates fully for the lack of schema descriptions, making the parameters clear and actionable.

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: 'Search for FPL players by name with optional filtering.' It specifies the verb ('search'), resource ('FPL players'), and scope ('by name with optional filtering'), which is clear and specific. However, it doesn't explicitly differentiate from sibling tools like 'analyze_players' or 'get_player_information,' which might have overlapping functionality, 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. It doesn't mention sibling tools like 'analyze_players' or 'get_player_information,' nor does it specify prerequisites or exclusions. This lack of contextual guidance makes it harder for an AI agent to choose the right tool in a server with multiple player-related tools.

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/rishijatia/fantasy-pl-mcp'

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