Build a tool-calling workflow with clear function boundaries
How to design tools that let a model act inside a workflow without gaining broad, unsafe access to your product.
Open source docReal workflow example
An assistant needs to help a proposal team find relevant tenders. It should search, compare, and summarize records, but it should not change eligibility status or archive opportunities by itself.
Expose read-only tools such as search_qualified_tenders and get_tender_documents first. Keep destructive or workflow-changing actions behind explicit user approvals, server authorization, and ordinary UI buttons.
The model becomes useful for discovery and explanation while the product keeps ownership of final state transitions.
Implementation approach
This guide is anchored in OpenAI function calling guide. Use the official API behavior as the boundary, then design the surrounding product state so the feature can be reviewed, retried, and improved.
- Name tools after the business action, such as searchQualifiedTenders or createHandoffSummary.
- Keep the input schema small and use IDs from your system instead of letting the model invent resources.
- Validate tool arguments before execution and reject unknown fields.
- Return structured, minimal data that helps the next model step without leaking unrelated records.
- Log tool requests, execution result, duration, and authorization decision.
Narrow custom tool definition
const searchQualifiedTenders = {
type: "function",
name: "search_qualified_tenders",
description: "Find tender records that match an approved industry, deadline, and region filter.",
parameters: {
type: "object",
additionalProperties: false,
required: ["industry", "deadlineBefore", "region"],
properties: {
industry: { type: "string" },
deadlineBefore: { type: "string", description: "ISO date" },
region: { enum: ["EU", "US", "Balkans", "Global"] },
},
},
};
Field notes
- Tools should express product capabilities, not database tables.
- Every tool needs narrow inputs, predictable outputs, and explicit authorization.
- The model can request a tool call, but your server decides whether it is allowed.
Mistakes to avoid
- Do not expose a generic run_sql or update_record tool.
- Do not let the model supply tenant, role, or owner values.
- Do not return records the current user cannot see in the product UI.
Ready checklist
- Server-side authorization
- Argument schema validation
- No destructive tool without approval
- Operational logging
- Tool output is scoped to the workflow
