Skip to main content

Documentation Index

Fetch the complete documentation index at: https://veryfront.com/docs/llms.txt

Use this file to discover all available pages before exploring further.

Agents

Create an AI agent with a system prompt, tools, and memory. Route examples below use the default app router. Veryfront Code also supports mounting the same handlers under pages/api/** when router: "pages" is enabled. For the normal path, omit model. Veryfront Code uses runtime conventions: local inference by default, and Veryfront Cloud defaults when VERYFRONT_API_TOKEN plus project context are available.

Prerequisites

  • A Veryfront project running locally (see Quickstart).
  • A provider configured for inference (see Providers).
  • The agents/ directory exists. If you customised ai.agents.discovery.paths in Configuration, use that directory instead.

Define an agent

Create a file in agents/:
// agents/assistant.ts
import { agent } from "veryfront/agent";

export default agent({
  id: "assistant",
  system: "You are a helpful assistant. Answer concisely.",
});
The id is how you reference the agent later with getAgent("assistant"). You can also define an agent with markdown when the agent only needs persona, model, and step configuration:
---
name: Support
description: Helps users with support questions
model: openai/gpt-5.4
max-steps: 6
---

You are a support assistant. Answer clearly and ask for missing details before acting.
The file path provides the agent id. For example, agents/support.md registers support and can be invoked through the same project runtime and control-plane surfaces as agents/support.ts.

Add tools

Agents call tools to take actions or fetch data. Reference tools by name: the framework resolves them from the tools/ directory:
// agents/assistant.ts
import { agent } from "veryfront/agent";

export default agent({
  id: "assistant",
  system: "You are a weather assistant.",
  tools: { getWeather: true },
  maxSteps: 5,
});
maxSteps limits how many tool-call iterations the agent can perform per request. See Tools for how to define getWeather.

Enable skills

Skills are reusable instruction packs discovered from your project’s skills/ directory.
// agents/assistant.ts
import { agent } from "veryfront/agent";

export default agent({
  id: "assistant",
  system: "You are a support engineer. Use skills when they match the task.",
  skills: ["incident-response", "repo-maintainer"], // or `true` for all discovered skills
  tools: {
    Read: true,
    "github:list-issues": true,
  },
});
When skills is enabled, the runtime automatically registers these skill tools:
  • load-skill
  • load-skill-reference
  • execute-skill-script
See Project structure for skills/ conventions and Configuration for discovery paths.

Skill execution flow

For skill-aware agents, the recommended flow is:
  1. Call load-skill({ skillId }) to load the skill instructions and policy.
  2. Optionally call load-skill-reference(...) to read files from references/ or assets/.
  3. Optionally call execute-skill-script(...) to run scripts from scripts/.
  4. Continue with normal tool calls under the active skill policy.
The runtime enforces that non-skill tools cannot run before a successful load-skill when both are emitted in the same step.

Skill script execution

Skill scripts run in one of two modes, selected automatically:
  • Local (development): When no Veryfront Cloud sandbox credentials are available, scripts run as direct subprocesses on your machine via runCommand(). No remote sandbox is needed.
  • Cloud (production): When SANDBOX_AUTH_TOKEN, VERYFRONT_API_TOKEN, or request-scoped Veryfront credentials are available, scripts are uploaded to and executed inside a remote sandbox session.
Local development does not require sandbox infrastructure. Scripts run as direct subprocesses.

Skill safety model

  • allowed-tools in SKILL.md is enforced at planning time and execution time (fail-closed).
  • Skill file reads are restricted to the skill root and allowed subdirectories.
  • Symlinked paths are rejected for skill file access.
  • Script execution timeout defaults to 60000 ms and is capped at 300000 ms.

Connect to a route

Use createAgUiHandler() to expose a registered agent through an AG-UI stream:
// app/api/ag-ui/route.ts
import { createAgUiHandler } from "veryfront/agent";

export const POST = createAgUiHandler("assistant");
Try it with the dev server running:
curl -N http://localhost:3000/api/ag-ui \
  -H "Content-Type: application/json" \
  -d '{"messages":[{"id":"1","role":"user","parts":[{"type":"text","text":"Say hello in one sentence."}]}]}'
The response streams AG-UI SSE. Pair it with useChat({ api: "/api/ag-ui" }) in browser UI code. If the route returns Agent not found, ensure the agent file is in agents/ and its id matches the value passed to createAgUiHandler().

Non-streaming response

For server-side generation (e.g., in getServerData), use generate():
import { getAgent } from "veryfront/agent";

const agent = getAgent("assistant");
const result = await agent.generate({
  input: "Summarize the latest news about AI.",
});

console.log(result.text); // The agent's response
console.log(result.toolCalls); // Tools the agent called
console.log(result.usage); // Token usage

Dynamic system prompts

The system property accepts a string, a function, or an async function:
export default agent({
  id: "assistant",
  system: async () => {
    const date = new Date().toLocaleDateString();
    return `You are a helpful assistant. Current date: ${date}.`;
  },
});
For step-boundary refresh during a long-lived run, use resolveRuntimeState instead of relying on system() to run again mid-turn.
import { agent } from "veryfront/agent";

export default agent({
  id: "assistant",
  system: "You are a project assistant.",
  resolveRuntimeState: async ({ step }) => {
    if (step === 0) return;

    return {
      system: "Use the latest project instructions before continuing.",
    };
  },
});

Agent configuration

PropertyTypeDescription
idstringUnique identifier used with getAgent()
namestringHuman-readable display name for listings
descriptionstringOptional summary for listings
modelstringOptional provider/model override. Omit or use "auto" for runtime defaults.
systemstring | () => string | Promise<string>System prompt
resolveRuntimeState(request: RuntimeStateRequest) => ResolvedRuntimeState | Promise<ResolvedRuntimeState | undefined>Refresh system/context before later model steps in the same run
toolsRecord<string, boolean | Tool>Tools the agent can use
maxStepsnumberMax tool-call iterations per request
memoryMemoryConfigConversation memory settings
streamingbooleanEnable streaming (default: true)
middlewareAgentMiddleware[]Execution middleware
allowedModelsstring[]Restrict runtime model overrides to these provider/model strings
skillstrue | string[]Enable all skills (true) or only specific skill IDs

Verify it worked

Save the agent file, restart veryfront dev, and hit the AG-UI route:
curl -N http://localhost:3000/api/ag-ui \
  -H "Content-Type: application/json" \
  -d '{"messages":[{"id":"1","role":"user","parts":[{"type":"text","text":"Hello"}]}]}'
The server should stream AG-UI events that end with a RunFinished event. If the response is 404, the AG-UI route file is missing; if it is 500, check the dev-server log for the agent registration or provider error.

Next