building-tools
Skill0 starsChanged 6 months agoMITView on GitHub
Creates tools for lauren-ai agents using @tool() on async functions or classes. Use when implementing a @tool() function or class, working with ToolContext for DI injection, adding caching, HITL approval, or using built-in skills like WebSearchTool, HttpFetchTool, or CodeExecutionTool.
1 other project uses a version of this.
Adopted by
Most recently taken up by
- celigo/aitheir own version, first seen Nov 5, 2026
Other versions1 project uses a version of this.
Word for word · 0
None found.
Edited · 0
None found.
Wrote their own version · 1
- celigo/ai★ 4same name
How matches are found. Word for word: the exact same text. Edited: shares passages with this file (“99% same” means 99% of its five-word phrases also appear here; 10% or more counts). Their own version: similar meaning, or, weakest, the same name. We can’t tell which project had it first. Projects are counted among the 200 most-starred candidates, and mentions are links to the repository we found, up to 50 per site, so both counts are a floor.
In this repository65 other files it gives its agents.
- AGENTS.mdAGENTS.md
- skills/building-agents/agents.mdAGENTS.md
- CLAUDE.mdCLAUDE.md
- llms-full.txtllms.txt
- llms.txtllms.txt
- adding-guardrailsSkill
- agent-health-timeoutSkill
- agent-permission-scopingSkill
- agent-session-isolationSkill
- agent-step-loggingSkill
- agent-supervisor-routerSkill
- agent-telemetrySkill
- async-agent-backgroundSkill
- building-agentsSkill
- building-teamsSkill
- calendar-scheduling-toolSkill
- callback-tracing-handlerSkill
- chain-of-thought-promptingSkill
- chat-model-configurationSkill
- code-execution-sandboxSkill
- common-agent-patternsSkill
- context-window-managementSkill
- conversation-memorySkill
- conversation-state-dbSkill
- database-query-toolSkill
- document-loadersSkill
- document-rerankingSkill
- email-notification-toolSkill
- embedding-model-ingestionSkill
- fallback-model-chainSkill
- few-shot-injectionSkill
- filesystem-toolSkill
- human-in-the-loopSkill
- hybrid-searchSkill
- inspecting-streamsSkill
- integrating-with-laurenSkill
- json-schema-enforcementSkill
- llm-provider-connectionSkill
- llm-rate-limitingSkill
- long-term-vector-memorySkill
- managing-memorySkill
- migrating-to-lauren-aiSkill
- multi-agent-delegationSkill
- multi-tool-orchestrationSkill
- multi-turn-tool-stateSkill
- output-guardrailsSkill
- plan-and-execute-agentSkill
- prompt-injection-defenseSkill
- prompt-versioningSkill
- rag-pipelineSkill
- react-agent-loopSkill
- response-validation-retrySkill
- rest-api-toolSkill
- securing-agentsSkill
- semantic-cacheSkill
- streaming-response-handlerSkill
- structured-output-parsingSkill
- sub-agent-spawningSkill
- system-prompt-templatingSkill
- testing-agentsSkill
- The first 60 shown.
The file
We split this skill into the rules it gives an agent
2 rules. About 0 are common, 0 are distinctive, and 2 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈0
Distinctive · estimate
This author's own choices. Worth a look.
2
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Very specific: line 60
Use a class when the tool needs injected dependencies.
- Very specific: line 100
Read the authenticated user identity from ctx.execution_context.request.state
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
Use
codemap find "SymbolName"to locate any symbol before reading — it gives exact file + line range and is faster than grep across the whole repo.
Building Tools with lauren-ai
Critical rule — tool annotations must resolve
from __future__ import annotations is supported, but every type used by @tool() must resolve when schema generation runs.
@tool() resolves annotations when it builds the JSON schema. Future
annotations are supported, but unresolved forward references and circular
imports in function-form tool files still break schema generation.
A safe reminder comment is:
# @tool() resolves parameter annotations when this module is imported.
# Keep tool signature types importable and avoid unresolved forward refs.Quick start — function-form tool
from lauren_ai import tool
@tool()
async def get_price(item: str) -> dict:
"""Look up an item's current price.
Args:
item: Product name to look up.
"""
return {"item": item, "price": 9.99}Attach it to an agent:
from lauren_ai import agent, use_tools
@agent(model="claude-opus-4-6", system="You are a helpful shop assistant.")
@use_tools(get_price)
class ShopAgent: ...Quick start — class-form tool
Use a class when the tool needs injected dependencies. The method must be
named run() — not __call__(). The @tool() decorator looks for run;
a __call__ is silently ignored and the decorator will raise ValueError.
from lauren_ai import tool, ToolContext
@tool()
class SendEmailTool:
"""Send an email to a recipient.
Args:
to: Recipient email address.
subject: Email subject line.
body: Email body text (plain text).
"""
def __init__(self, smtp_client: SmtpClient) -> None:
self._smtp = smtp_client
async def run(
self,
to: str,
subject: str,
body: str,
ctx: ToolContext | None = None,
) -> dict:
await self._smtp.send(to=to, subject=subject, body=body)
return {"sent": True, "to": to}ToolContext — DI injection, not LLM input
ToolContext is never included in the JSON schema sent to the LLM.
ToolExecutor injects it automatically at call time. Use it to:
- Access the agent's
AgentContextviactx.agent_context - Read the authenticated user identity from
ctx.execution_context.request.state - Identify the current turn number via
ctx.turn
@tool()
async def whoami(ctx: ToolContext | None = None) -> dict:
"""Return the authenticated user's ID.
(No additional parameters — all identity comes from context.)
"""
if ctx is None or ctx.execution_context is None:
return {"user_id": None}
state = getattr(ctx.execution_context.request, "state", None)
user_id = state.get("user_id") if state else None
return {"user_id": user_id}The generated schema contains zero parameters:
{
"name": "whoami",
"input_schema": {"type": "object", "properties": {}, "required": []}
}Schema generation rules
| Python annotation | JSON Schema type | Required? |
str | "string" | yes (unless Optional) |
int / float | "number" | yes (unless Optional) |
bool | "boolean" | yes (unless Optional) |
dict | "object" | yes (unless Optional) |
list | "array" | yes (unless Optional) |
Optional[T] / T | None | type T | no |
ctx: ToolContext / ctx: ToolContext | None = None | — | excluded entirely |
| parameter with default value | type T | no |
Parameter descriptions come from the Args: section of the Google-style
docstring. Always document every parameter.
Safety invariants
| Rule | Why |
run() not __call__() | @tool() looks for run; a __call__ method is silently ignored |
| Resolvable tool annotations | Future annotations are supported, but @tool() still needs every referenced type to resolve when it builds the schema |
Decorate with @tool() (parentheses required) | Bare @tool raises DecoratorUsageError |
| Never use LLM-supplied identity | Read from ctx.execution_context.request.state — see security.md |
Always return a dict | LLM receives the JSON-serialised return value as the tool result |
Reference files
| File | Contents |
| tools.md | Full reference: schema rules, HITL approval, caching, on_tool_result hook, built-in skills |
| ../securing-agents/security.md | Secure tool patterns using ToolContext.execution_context |
| ../building-agents/agents.md | @agent, lifecycle hooks, attaching tools via @use_tools |
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

