Skip to main content
You want a complete picture of what your agent did — not just tool calls, but LLM generations, workflow steps, MCP interactions, handoffs between agents, and errors. Apie provides wrappers and track* methods for each event category. When you finish this page, you’ll know which API to use for each kind of telemetry and how events appear in the session timeline.

Workflow steps

Name logical steps inside a run for readable session replays:
await apie.withWorkflowStep(
  {
    runId: run.id,
    sessionId: session.id,
    stepKey: "triage-ticket",
    stepName: "Triage ticket",
    stepIndex: 1,
    payloadSummary: { channel: "email" },
  },
  async () => triageTicket(ticketId),
);
Events: agent.workflow.step.started, agent.workflow.step.completed, agent.workflow.step.failed

LLM calls

Track model invocations with token and latency metadata:
await apie.withLlmCall(
  {
    runId: run.id,
    model: { provider: "openai", name: "gpt-4o" },
    inputSummary: "Summarize incident feed",
  },
  async () => openai.chat.completions.create({ /* ... */ }),
);
Events: agent.llm.called, agent.llm.completed, agent.llm.failed

MCP calls

For in-process MCP clients (not the proxy), track MCP tool invocations:
import { withMcpToolCall } from "@apie-sh/sdk";

await withMcpToolCall(
  apie,
  {
    runId: run.id,
    server: "internal-cicd",
    tool: "trigger_pipeline",
    actionType: "execute",
    resourceType: "pipeline_run",
    environment: "production",
    riskLevel: "high",
  },
  async () => mcpClient.callTool("trigger_pipeline", { service: "api" }),
);
Events: agent.mcp.called, agent.mcp.completed, agent.mcp.failed

Handoffs

When one agent delegates work to another, track the handoff lifecycle:
await apie.trackHandoffRequested({
  sessionId: session.id,
  sourceRunId: orchestratorRun.id,
  reason: "Delegate customer response draft",
  payloadSummary: { ticketId: "SUP-123" },
});

// ... worker run executes ...

await apie.trackHandoffCompleted({
  sessionId: session.id,
  runId: workerRun.id,
});
Events: agent.handoff.requested, agent.handoff.accepted, agent.handoff.completed, agent.handoff.failed

Errors

Capture errors without failing the run:
try {
  await riskyOperation();
} catch (error) {
  apie.captureError({ runId: run.id, error });
  throw error;
}
Event: agent.error

Low-level tracking

For events that don’t fit a wrapper, use track* methods or track directly:
await apie.trackActionRequested({
  runId: run.id,
  action: { type: "read", name: "fetch_logs" },
  resource: { type: "observability_event" },
});

await apie.track({ type: "custom.event", payload: { key: "value" } });
See the Events reference for the full catalog.

Next steps

Multi-agent pipelines

Combine steps, handoffs, and child runs.

Events reference

Full event type catalog.