feat: enforce single tool type with port config

- Replace interfaces array with interface_type string and requires_port boolean
- Add database migration for schema change
- Update backend model, API schemas, and validation
- Update frontend types and tool workshop UI
- Add dropdown for interface type selection
- Conditionally show/hide port fields based on requires_port
- Update tests and mock data
- All frontend tests pass (37/37)
- Frontend typecheck and lint pass
This commit is contained in:
2026-05-22 20:32:10 +00:00
parent 5c17de0c3c
commit 0fa926284c
18 changed files with 558 additions and 232 deletions
+10 -5
View File
@@ -137,7 +137,8 @@ async def seed_builtin_tool_types():
"display_name": "VS Code Server",
"description": "VS Code running in the browser via code-server",
"category": "editor",
"interfaces": ["web"],
"interface_type": "web",
"requires_port": True,
"compose_template": """version: "3.8"
services:
code-server:
@@ -160,7 +161,8 @@ services:
"display_name": "Jupyter Notebook",
"description": "Jupyter Lab for interactive development",
"category": "notebook",
"interfaces": ["web"],
"interface_type": "web",
"requires_port": True,
"default_port": 8888,
"compose_template": """version: "3.8"
services:
@@ -181,7 +183,8 @@ services:
"display_name": "OpenCode",
"description": "AI coding assistant - run opencode in terminal",
"category": "ai-assistant",
"interfaces": ["terminal"],
"interface_type": "terminal",
"requires_port": False,
"default_port": 3000,
"compose_template": """version: "3.8"
services:
@@ -227,7 +230,8 @@ volumes:
display_name=tool_data["display_name"],
description=tool_data["description"],
category=tool_data["category"],
interfaces=tool_data["interfaces"],
interface_type=tool_data["interface_type"],
requires_port=tool_data["requires_port"],
definition_type="compose",
compose_template=tool_data["compose_template"],
required_variables=tool_data["required_variables"],
@@ -241,7 +245,8 @@ volumes:
existing.display_name = tool_data["display_name"]
existing.description = tool_data["description"]
existing.category = tool_data["category"]
existing.interfaces = tool_data["interfaces"]
existing.interface_type = tool_data["interface_type"]
existing.requires_port = tool_data["requires_port"]
existing.definition_type = "compose"
existing.compose_template = tool_data["compose_template"]
existing.required_variables = tool_data["required_variables"]