devtu-create-tool

安装量: 143
排名: #5991

安装

npx skills add https://github.com/mims-harvard/tooluniverse --skill devtu-create-tool
ToolUniverse Tool Creator
Create new scientific tools following established patterns.
Top 7 Mistakes (90% of Failures)
Missing
default_config.py
Entry
— tools silently won't load
Non-nullable Mutually Exclusive Parameters
— validation errors (#1 issue in 2026)
Fake test_examples
— tests fail, agents get bad examples
Single-level Testing
— misses registration bugs
Skipping
test_new_tools.py
— misses schema/API issues
Tool Names > 55 chars
— breaks MCP compatibility
Raising Exceptions
— should return error dicts instead
Two-Stage Architecture
Stage 1: Tool Class Stage 2: Wrappers (Auto-Generated)
@register_tool("MyTool") MyAPI_list_items()
class MyTool(BaseTool): MyAPI_search()
def run(arguments): MyAPI_get_details()
One class handles multiple operations. JSON defines individual wrappers. Need BOTH.
Three-Step Registration
Step 1
Class registration via
@register_tool("MyAPITool")
Step 2
(MOST COMMONLY MISSED): Config registration in
default_config.py
:
TOOLS_CONFIGS
=
{
"my_category"
:
os
.
path
.
join
(
current_dir
,
"data"
,
"my_category_tools.json"
)
,
}
Step 3
Automatic wrapper generation on
tu.load_tools()
Implementation Guide
Files to Create
src/tooluniverse/my_api_tool.py
— implementation
src/tooluniverse/data/my_api_tools.json
— tool definitions
tests/tools/test_my_api_tool.py
— tests
Python Tool Class (Multi-Operation Pattern)
from
typing
import
Dict
,
Any
from
tooluniverse
.
tool
import
BaseTool
from
tooluniverse
.
tool_utils
import
register_tool
import
requests
@register_tool
(
"MyAPITool"
)
class
MyAPITool
(
BaseTool
)
:
BASE_URL
=
"https://api.example.com/v1"
def
init
(
self
,
tool_config
)
:
super
(
)
.
init
(
tool_config
)
self
.
parameter
=
tool_config
.
get
(
"parameter"
,
{
}
)
self
.
required
=
self
.
parameter
.
get
(
"required"
,
[
]
)
def
run
(
self
,
arguments
:
Dict
[
str
,
Any
]
)
-
>
Dict
[
str
,
Any
]
:
operation
=
arguments
.
get
(
"operation"
)
if
not
operation
:
return
{
"status"
:
"error"
,
"error"
:
"Missing: operation"
}
if
operation
==
"search"
:
return
self
.
_search
(
arguments
)
return
{
"status"
:
"error"
,
"error"
:
f"Unknown:
{
operation
}
"
}
def
_search
(
self
,
arguments
:
Dict
[
str
,
Any
]
)
-
>
Dict
[
str
,
Any
]
:
query
=
arguments
.
get
(
"query"
)
if
not
query
:
return
{
"status"
:
"error"
,
"error"
:
"Missing: query"
}
try
:
response
=
requests
.
get
(
f"
{
self
.
BASE_URL
}
/search"
,
params
=
{
"q"
:
query
}
,
timeout
=
30
)
response
.
raise_for_status
(
)
data
=
response
.
json
(
)
return
{
"status"
:
"success"
,
"data"
:
data
.
get
(
"results"
,
[
]
)
}
except
requests
.
exceptions
.
Timeout
:
return
{
"status"
:
"error"
,
"error"
:
"Timeout after 30s"
}
except
requests
.
exceptions
.
HTTPError
as
e
:
return
{
"status"
:
"error"
,
"error"
:
f"HTTP
{
e
.
response
.
status_code
}
"
}
except
Exception
as
e
:
return
{
"status"
:
"error"
,
"error"
:
str
(
e
)
}
JSON Configuration
[
{
"name"
:
"MyAPI_search"
,
"class"
:
"MyAPITool"
,
"description"
:
"Search items. Returns array of results. Supports Boolean operators. Example: 'protein AND membrane'."
,
"parameter"
:
{
"type"
:
"object"
,
"required"
:
[
"operation"
,
"query"
]
,
"properties"
:
{
"operation"
:
{
"const"
:
"search"
,
"description"
:
"Operation (fixed)"
}
,
"query"
:
{
"type"
:
"string"
,
"description"
:
"Search term"
}
,
"limit"
:
{
"type"
:
[
"integer"
,
"null"
]
,
"description"
:
"Max results (1-100)"
}
}
}
,
"return_schema"
:
{
"oneOf"
:
[
{
"type"
:
"object"
,
"properties"
:
{
"data"
:
{
"type"
:
"array"
}
}
}
,
{
"type"
:
"object"
,
"properties"
:
{
"error"
:
{
"type"
:
"string"
}
}
,
"required"
:
[
"error"
]
}
]
}
,
"test_examples"
:
[
{
"operation"
:
"search"
,
"query"
:
"protein"
,
"limit"
:
10
}
]
}
]
Critical Requirements
return_schema MUST have oneOf
success + error schemas
test_examples MUST use real IDs
NO "TEST", "DUMMY", "PLACEHOLDER"
Tool name <= 55 chars
:
{API}{action}
template
Description 150-250 chars
what, format, example, notes
NEVER raise in run()
return {"status": "error", "error": "..."} Set timeout on all HTTP requests (30s) Standard response : {"status": "success|error", "data": {...}} Parameter Design Mutually Exclusive Parameters (CRITICAL — #1 issue) When tool accepts EITHER id OR name , BOTH must be nullable: { "id" : { "type" : [ "integer" , "null" ] , "description" : "Numeric ID" } , "name" : { "type" : [ "string" , "null" ] , "description" : "Name (alternative to id)" } } Without "null" , validation fails when user provides only one parameter. Common cases: id OR name , gene_id OR gene_symbol , any optional filters. API Key Configuration Optional keys (tool works without, better with): { "optional_api_keys" : [ "NCBI_API_KEY" ] } self . api_key = os . environ . get ( "NCBI_API_KEY" , "" )

Read from env only

Required keys (tool won't work without): { "required_api_keys" : [ "NVIDIA_API_KEY" ] } Rules: Never add api_key as tool parameter for optional keys. Use env vars only. Testing (MANDATORY) Full guide: references/testing-guide.md Quick Testing Checklist Level 1 — Direct class test: import class, call run() , check response Level 2 — ToolUniverse test: tu.tools.YourTool_op1(...) , check registration Level 3 — Real API test: use real IDs, verify actual responses MANDATORY — Run python scripts/test_new_tools.py your_tool -v → 0 failures Verification Script

Check all 3 registration steps

python3 -c " import sys; sys.path.insert(0, 'src') from tooluniverse.tool_registry import get_tool_registry import tooluniverse.your_tool_module assert 'YourToolClass' in get_tool_registry(), 'Step 1 FAILED' from tooluniverse.default_config import TOOLS_CONFIGS assert 'your_category' in TOOLS_CONFIGS, 'Step 2 FAILED' from tooluniverse import ToolUniverse tu = ToolUniverse(); tu.load_tools() assert hasattr(tu.tools, 'YourCategory_op1'), 'Step 3 FAILED' print('All 3 steps verified!') " Quick Commands python3 -m json.tool src/tooluniverse/data/your_tools.json

Validate JSON

python3 -m py_compile src/tooluniverse/your_tool.py

Check syntax

grep "your_category" src/tooluniverse/default_config.py

Verify config

python scripts/test_new_tools.py your_tool -v

MANDATORY test

References Testing guide : references/testing-guide.md Advanced patterns (async, SOAP, pagination): references/advanced-patterns.md Implementation guide (full checklist): references/implementation-guide.md Tool improvement checklist : references/tool-improvement-checklist.md

返回排行榜