-
Notifications
You must be signed in to change notification settings - Fork 613
[BUG]: Tag filter returns 500 Exception for list tools api #2329
Description
🐞 Bug Summary
The tags query parameter in the /tools endpoint does not work after the schema change from List[str] to List[Dict[str, str]]. The tag filtering logic compares plain strings against dictionary objects, which always fails. Attempting to filter tools by tag either returns a 500 Internal Server Error (database path) or returns 0 results (in-memory path), even when matching tools exist.
🧩 Affected Component
Select the area of the project impacted:
-
mcpgateway- API -
mcpgateway- UI (admin panel) -
mcpgateway.wrapper- stdio wrapper - Federation or Transports
- CLI, Makefiles, or shell scripts
- Container setup (Docker/Podman/Compose)
- Other (explain below)
🔁 Steps to Reproduce
-
Create a tool with tags in the new dict format:
[{"id": "automation", "label": "automation"}, {"id": "data-analysis", "label": "data-analysis"}] -
Attempt to filter tools using the tags query parameter:
GET /tools?tags=automationResult: 500 Internal Server Error
-
Attempt to filter using visibility parameter (triggers in-memory filter path):
GET /tools?visibility=public&tags=automationResult: Returns 0 tools, even though tools with
automationtag exist -
Verify tools exist without the tag filter:
GET /tools?include_inactive=trueResult: Returns all tools including those with
automationtag
🤔 Expected Behavior
The API should return all tools that have a tag with id or label matching the provided filter value. For example, GET /tools?tags=automation should return all tools where any tag dict has "id": "automation" or "label": "automation".
📓 Logs / Error Output
Path 1 - Database filter (500 error):
When calling GET /tools?tags=automation, the json_contains_expr function in sqlalchemy_modifier.py fails because it's designed for plain string arrays (["automation"]) but the tags column now contains dict arrays ([{"id": "automation", "label": "automation"}]).
Path 2 (0 results):
When calling GET /tools?visibility=public&tags=automation, the filtering logic at main.py:2587 performs:
any(tag in tool.tags for tag in tags_list)This checks if string "automation" is in the list [{"id": "automation", ...}], which evaluates to False because string equality against dict objects never matches.
🧠 Environment Info
| Key | Value |
|---|---|
| Version or commit | Post-migration 9e028ecf59c4 (tag dict format) |
| Runtime | Python 3.13 |
| Platform / OS | Windows 10 |
| Container | N/A |
🧩 Additional Context (optional)
Affected files:
mcpgateway/main.py
Schema change reference:
- Migration:
9e028ecf59c4_tag_records_changes_list_str_to_list_.py - Tags changed from
List[str]toList[Dict[str, str]]with format{"id": "<tag>", "label": "<tag>"}
Related: The same issue likely affects tag filtering in other entity list endpoints (resources, prompts, servers, gateways, a2a_agents) that use the same tag filtering pattern.