InterviewsVector
Arc 8
Build labAdvanced135 min estimateOriginal publication

A Tool-Using Agent Is a Bounded State Machine

The model may propose the next action. The runtime—not the model—owns authority, limits, validation, side effects, and the definition of done.

Authorship
InterviewsVector
Published / updated
2026-08-11 / 2026-09-21

The decision in one pass

Implement an agent as a deterministic runtime around a probabilistic planner. The runtime holds typed state, validates every proposed action, enforces step, time, token, and cost budgets, checks authorization and approval, executes idempotent tools, records observations, and ends in explicit succeeded, failed, cancelled, or budget-exhausted states.

Why this matters

A while-loop that asks a model what to do next is a demo. In production, repeated retries, ambiguous tool results, partial side effects, prompt injection, cancellation, and human approval turn the loop into a workflow engine with security consequences.

You will be able to

  • Separate planner, policy, executor, and state persistence.
  • Model agent execution with explicit transitions and terminal states.
  • Enforce budgets and sensitive-action approval outside the model.
  • Design idempotent tool calls and recover from partial success.
  • Map MCP tool schemas into—but not beyond—the runtime authority boundary.

Your Vector Loop for this lab

  1. 01

    Model

    Treat model output as an untrusted transition proposal.

  2. 02

    Derive

    Define state, invariants, guards, effects, and terminal outcomes.

  3. 03

    Build

    Implement a bounded TypeScript runtime with fake tools.

  4. 04

    Stress

    Inject loops, invalid actions, timeouts, partial success, and cancellation.

  5. 05

    Operate

    Add authorization, approvals, durable logs, idempotency, and SLOs.

  6. 06

    Defend

    Justify every piece of autonomy with a bounded business capability.

The planner proposes; the runtime disposes

ComponentOwnsMust not own
Planner modelproposed action and argumentspermissions or budget truth
Policyallowed tools, tenants, data, approvalsnatural-language interpretation alone
Executorvalidated side effect and timeoutopen-ended planning
State storehistory, status, idempotency, checkpointssecret material in model context
Human gatehigh-impact authorizationroutine low-risk retries

Give every run a finite set of states

Bounded agent simulator

Inspect a frozen proposal trace, predict the first runtime boundary that must stop or pause it, then check the decision against typed policy evidence.

Choose the bounded agent's terminal transition

The probabilistic planner may propose an action; the deterministic runtime owns budgets, authorization, idempotency, execution, verification, and terminal state. Predict the valid branch before checking.

Proposal branch
  1. 1

    Observe

    Read the goal and current durable state.

  2. 2

    Propose

    Choose one bounded next action.

  3. 3

    Authorize

    Apply tool, tenant, budget, and approval policy.

  4. 4

    Act

    Execute once or replay a recorded idempotent result.

  5. 5

    Verify

    Inspect the result and choose a terminal state.

budget=3 steps remaining

authority=allowed

fingerprint=new

result=invoice status returned

Synthetic state record only. The evidence is visible; the graded transition remains withheld until Check.

Where should this branch terminate or replay?

Select a prediction, then check it against the current evidence.

  1. 01PlanningThe planner receives bounded context and proposes a typed action or completion.
  2. 02ValidatingSchema, policy, budget, preconditions, and duplication are checked.
  3. 03Awaiting approvalA sensitive action pauses with exact proposed inputs visible.
  4. 04ExecutingThe tool runs with timeout, scoped credentials, and an idempotency key.
  5. 05ObservingA typed result or actionable error is appended to state.
  6. 06TerminalSucceeded, failed, cancelled, or exhausted is persisted and cannot silently resume.

Build a loop with guards outside the model

bounded-agent.ts
1const state = {
2 status: "planning",
3 steps: 0,
4 maxSteps: 3,
5 spentUsd: 0,
6 maxCostUsd: 1,
7 seen: new Set<string>(),
8} satisfies AgentState
9
10const proposal = {
11 kind: "tool",
12 name: "transfer",
13 args: { cents: 500 },
14} as const
15
16const toolPolicies = new Map([
17 ["transfer", { requiresApproval: true }],
18])
19
20const validation = validateProposal(
21 state,
22 "tenant-a",
23 proposal,
24 toolPolicies,
25 0.05
26)
27console.log(validation.ok)
28if (validation.ok) {
29 const next = recordAcceptedProposal(state, validation, 0.05)
30 console.log(next.status)
31 console.log(next.steps)
32}

Expected output

true
awaiting_approval
1

Verify: Run node --experimental-strip-types --test courses/ai-engineering/reference-impl/agent/bounded-agent.test.ts.

The downloadable runtime derives approval from a trusted tool-policy map—not from model output—then issues a one-use validation proof bound to the state revision and cost estimate. It validates bounded input shapes, canonicalizes nested JSON-compatible arguments deterministically, hashes tenant-scoped action identity, uses exact micro-USD budget arithmetic, and returns a fresh state instead of mutating caller-owned evidence. A production fingerprint must also bind authenticated principal, tool version, resource scope, and the external system's idempotency contract.

Budgets are multidimensional

BudgetProtectsTerminal behavior
stepsloops and compounding errorexhausted with trace
wall timestale work and resource capturecancel in-flight tools
tokenscontext growth and model costsummarize or stop by policy
moneyprovider and tool spenddeny before side effect
side effectsblast radiusrequire approval or stop
retriesduplicate actions and downstream pressurefail with actionable error

A step limit alone is insufficient: one tool call can run for an hour, spend money, mutate hundreds of records, or return enough data to overflow context. Each budget needs a counter, a guard before commitment, and a terminal reason visible to users and operators.

Test the trajectory, not only the final answer

  1. 01Repeated actionThe planner proposes the same mutation after an ambiguous timeout.
  2. 02Partial successThe external API commits but the response is lost.
  3. 03Indirect prompt injectionA retrieved document asks the agent to export secrets.
  4. 04Tool schema driftA once-optional argument becomes required.
  5. 05Human pauseApproval arrives after relevant external state has changed.
  6. 06CancellationThe user stops the run while a tool is in flight.

Protocols standardize transport, not trust

MCP standardizes how hosts, clients, and servers discover resources, prompts, and tools using JSON-RPC and negotiated capabilities. Tool definitions include schemas and metadata, but the current specification explicitly treats tool annotations as untrusted unless they come from a trusted server. The host still owns consent, policy, access control, timeouts, result validation, and audit.

Operate at three altitudes

Production lens

  • — Persist transitions before and after side effects so recovery can distinguish not-started, in-flight, and committed work.
  • — Use scoped short-lived credentials per tool and tenant.
  • — Record model, prompt, tool schema, arguments, result status, approvals, budgets, and trace IDs with redaction.
  • — Define cancellation and compensation semantics for every mutating tool.

Staff lens

  • — Reject agent architecture when a deterministic workflow meets the requirement with less uncertainty.
  • — Bound autonomy by capability and blast radius, not by a marketing label such as assistant or copilot.
  • — Make the tool platform enforce policy uniformly across models and agent frameworks.

Interview defense

How would you make an LLM agent safe enough to call production tools?

I would put the model behind a deterministic state-machine runtime. Model output is an untrusted proposal validated against schemas, authenticated policy, budgets, preconditions, duplication, and approval requirements. Tools use scoped credentials, timeouts, idempotency keys, typed results, and durable transition logs. Runs end explicitly and can be cancelled or recovered without replaying side effects.

Expect the interviewer to press on

  • — How do you recover after a tool times out after committing?
  • — What belongs in durable state versus model context?
  • — What security does MCP provide and what remains the host's responsibility?

Misconceptions to remove

“A stronger model makes the agent safe.”

Model quality may reduce proposal errors; it does not replace authorization, validation, idempotency, or blast-radius controls.

“Human in the loop solves tool safety.”

Approvals help for selected high-impact actions but can become rubber stamps and do not replace deterministic policy.

“MCP secures tool execution.”

MCP standardizes protocol interactions; implementations still enforce trust, consent, access control, and validation.

Check your model

1. Why is a tool timeout not proof that no side effect happened?

The external system may have committed before the response was lost. Recovery needs idempotency or a status lookup, not blind retry.

2. What makes a terminal state useful?

It makes completion reason explicit, prevents accidental resume, supports user communication, and enables reliable metrics and recovery.

Prove the mechanism

Add cost, time, and side-effect budgets plus a human approval state to the runtime. Test every transition and forbidden transition.

Add a production constraint

Persist state to an append-only event log and recover safely from a crash at every line around a mutating tool call.

Artifact: Tested bounded agent runtime

courses/ai-engineering/reference-impl/agent/bounded-agent.ts

Download reference implementation

Primary references and next links

References

  1. 1. ReAct: Synergizing Reasoning and Acting in Language Models

    Yao et al.. Primary paper on interleaved reasoning and actions.

  2. 2. Model Context Protocol specification

    Model Context Protocol. Current authoritative protocol specification at publication.

  3. 3. LLM06:2025 Excessive Agency

    OWASP GenAI Security Project. Current risk description and mitigation guidance.

Continue through the graph

Glossary: agent · tool · state machine · idempotency · approval gate · MCP · excessive agency