Tools API Reference¶
Tools provide the interface for AI agents to interact with data.
Tool Base Class¶
Tool¶
class Tool(ABC):
name: str
description: str
@abstractmethod
async def execute(self, ctx: RunContext, **kwargs) -> ToolResult:
...
ToolResult¶
@dataclass
class ToolResult:
success: bool
data: Any
error: str | None = None
metadata: dict = field(default_factory=dict)
Read Tools¶
DescribeSchemaTool¶
Describe available models and fields.
Signature¶
Response¶
{
"models": {
"User": {
"fields": ["id", "name", "email"],
"relations": ["orders"],
"writable": false
},
"Order": {
"fields": ["id", "status", "total"],
"relations": ["user", "items"],
"writable": true
}
}
}
QueryTool¶
Query multiple records.
Signature¶
async def execute(
self,
ctx: RunContext,
model: str,
filters: list[dict] = [],
select: list[str] | None = None,
order: list[dict] = [],
include: list[dict] = [],
limit: int = 50,
cursor: str | None = None,
) -> ToolResult:
Parameters¶
| Parameter | Type | Description |
|---|---|---|
model |
str |
Model name |
filters |
list[dict] |
Filter conditions |
select |
list[str] \| None |
Fields to return |
order |
list[dict] |
Ordering directives |
include |
list[dict] |
Relations to include |
limit |
int |
Maximum rows (default: 50) |
cursor |
str \| None |
Pagination cursor |
Response¶
GetTool¶
Fetch a single record by ID.
Signature¶
async def execute(
self,
ctx: RunContext,
model: str,
id: Any,
select: list[str] | None = None,
include: list[dict] = [],
) -> ToolResult:
Response¶
Returns single record or error if not found.
AggregateTool¶
Compute aggregations.
Signature¶
async def execute(
self,
ctx: RunContext,
model: str,
filters: list[dict] = [],
aggregations: list[dict],
group_by: list[str] = [],
) -> ToolResult:
Parameters¶
| Parameter | Type | Description |
|---|---|---|
model |
str |
Model name |
filters |
list[dict] |
Filter conditions |
aggregations |
list[dict] |
Aggregation operations |
group_by |
list[str] |
Grouping fields |
Aggregation Format¶
{
"function": "count" | "sum" | "avg" | "min" | "max",
"field": "field_name", # Required for sum, avg, min, max
"alias": "output_name"
}
Write Tools¶
CreateTool¶
Create a new record.
Signature¶
Response¶
Returns created record with generated fields (id, timestamps).
UpdateTool¶
Update an existing record.
Signature¶
DeleteTool¶
Delete a record.
Signature¶
BulkUpdateTool¶
Update multiple records.
Signature¶
async def execute(
self,
ctx: RunContext,
model: str,
filters: list[dict],
data: dict,
) -> ToolResult:
Response¶
ToolRegistry¶
Manages tool registration and lookup.
Constructor¶
Methods¶
register¶
get¶
items¶
to_openai_functions¶
to_anthropic_tools¶
Example¶
registry = ToolRegistry()
registry.register(QueryTool(adapter, policy))
registry.register(GetTool(adapter, policy))
registry.register(CreateTool(adapter, policy))
# Get tool by name
tool = registry.get("query")
# Export for LLM
functions = registry.to_openai_functions()
DeferredExecutor¶
Handles operations requiring approval.
Constructor¶
Methods¶
defer¶
execute¶
cancel¶
status¶
DeferredResult¶
@dataclass
class DeferredResult:
id: str
status: str # "pending_approval", "approved", "rejected", "expired"
tool_name: str
model: str
created_at: datetime
expires_at: datetime
Approval Gates¶
ApprovalGate (Abstract)¶
from ormai.utils import ApprovalGate
class ApprovalGate(ABC):
@abstractmethod
async def request_approval(self, operation: dict) -> str:
"""Returns approval request ID."""
@abstractmethod
async def check_approval(self, request_id: str) -> str:
"""Returns status: pending, approved, rejected."""
AutoApproveGate¶
Automatically approves all operations (for testing).
CallbackApprovalGate¶
Uses a callback for approval decisions.
from ormai.utils import CallbackApprovalGate
async def check(operation: dict) -> bool:
# Custom approval logic
return await my_approval_service.check(operation)
gate = CallbackApprovalGate(callback=check)
InMemoryApprovalQueue¶
Queue-based approval for development.
from ormai.utils import InMemoryApprovalQueue
queue = InMemoryApprovalQueue()
# In your application
pending = await queue.get_pending()
await queue.approve(pending[0].id)
# or
await queue.reject(pending[0].id, reason="Invalid operation")
ToolsetFactory¶
Generate complete toolsets.
Constructor¶
Methods¶
create_read_toolset¶
create_full_toolset¶
def create_full_toolset(
self,
approval_gate: ApprovalGate | None = None,
) -> ToolRegistry:
"""Create toolset with all tools."""