The Ovalleaf Weeklychevron_rightIssue 008

Building Agentic AI Systems at Scale

From proof-of-concept to production—how to architect multi-agent AI systems that reason, integrate with enterprise APIs, and deliver explainable results.

The Ovalleaf Team3 min read

The Agent Frontier

Twelve months ago, building an AI system meant choosing between two paths: statistical models that were interpretable but brittle, or deep neural networks that worked but remained black boxes. Today, a third path has emerged—agentic systems that combine the reasoning of large language models with the precision of programmatic logic.

But building agents at scale is fundamentally different from running a single chat prompt through an API. Production agentic systems need orchestration, error handling, observability, and integration with legacy enterprise infrastructure. This is where most teams get stuck.

The Architecture Challenge

A production agentic system has three layers:

Layer 1: The Brain — Your LLM (Claude, GPT, open-source). This is not just a chat interface. You're building chains of thought, tool integration trees, and verification loops. Every decision point is an opportunity to validate, correct, or escalate.

Layer 2: The Nervous System — Tool integration. Your agents need to read databases, write to APIs, fetch real-time data, and call other services. This is where your enterprise integration strategy lives. We've seen teams spend 60% of their development time here—not because it's hard in isolation, but because it's hard to do safely at scale.

Layer 3: The Operations — Kubernetes, monitoring, logging, and failure modes. When an agent makes a decision that costs $50,000, you need to know exactly why, step-by-step, including every tool call and verification result.

Multi-Step Reasoning With Safety

Here's a pattern that works:

Agent receives request
  → Break into subtasks
    → For each subtask:
       - LLM proposes action
       - Verify action against policy
       - Execute with timeouts
       - Validate result against schema
       - Log full execution trace
    → Aggregate results
    → Human review (if threshold exceeded)
  → Provide response with reason codes

The key is verification at every step. Claude can draft an email, but your system should verify:

  • The email doesn't contain PII
  • The recipient exists in your directory
  • The content doesn't violate compliance rules
  • The sender has permission to send to that recipient

Only then does it execute. This adds latency (50-200ms per verification), but it eliminates entire categories of production incidents.

Tool Integration Patterns

Don't expose your database directly to the agent. Instead, build a tool layer:

@tool
def query_customer_data(customer_id: str) -> dict:
    """Fetch customer data (read-only)."""
    # Validate input
    if not is_valid_uuid(customer_id):
        raise ValueError("Invalid customer ID")
    
    # Query with row-level security applied
    result = db.query(
        "SELECT * FROM customers WHERE id = %s",
        [customer_id],
        timeout=5  # Always timeout long queries
    )
    
    # Redact sensitive fields
    return {k: v for k, v in result.items() 
            if k not in ['ssn', 'credit_card']}

@tool
def update_customer_notes(customer_id: str, notes: str) -> bool:
    """Add notes to customer record (audit logged)."""
    if len(notes) > 500:
        raise ValueError("Notes too long")
    
    audit_log.record("customer_update", {
        "customer_id": customer_id,
        "timestamp": now(),
        "notes": notes
    })
    
    db.execute(
        "UPDATE customers SET notes = %s WHERE id = %s",
        [notes, customer_id]
    )
    return True

Every tool should:

  • Validate inputs strictly
  • Have timeouts
  • Log every execution
  • Redact sensitive fields
  • Have clear error messages

Observability at Scale

When something goes wrong, you need the full trace:

trace = {
    "request_id": uuid(),
    "timestamp": now(),
    "user_id": user_id,
    "initial_prompt": "...",
    "steps": [
        {
            "type": "reasoning",
            "llm_call": {
                "model": "claude-opus-5",
                "tokens_in": 1200,
                "tokens_out": 450,
                "response": "I should query the customer..."
            }
        },
        {
            "type": "tool_call",
            "tool": "query_customer_data",
            "input": {"customer_id": "abc-123"},
            "result": {"success": true, "data": {...}},
            "duration_ms": 142
        },
        {
            "type": "verification",
            "check": "Does result match expected schema?",
            "passed": true
        },
        ...
    ],
    "final_result": "...",
    "total_duration_ms": 1842
}

Store this in a searchable database. Every executive question ("Why did the agent approve this claim?") should be answerable in seconds.

Handling Failures

Agents will fail. Plan for it:

  • Graceful degradation: If the agent can't verify a decision, fall back to a human queue, don't crash.
  • Retry with backoff: Transient failures happen. Implement exponential backoff with jitter.
  • Circuit breakers: If a downstream API is failing, stop calling it immediately. Route to a fallback.
  • Escalation paths: Define at what confidence thresholds decisions go to humans.
if agent_confidence < 0.7:
    # Low confidence—escalate to human review
    send_to_queue("human_review", {
        "request_id": request_id,
        "agent_reasoning": agent_trace,
        "recommendation": agent_output
    })
    return {"status": "pending_review"}
elif agent_confidence < 0.9:
    # Medium confidence—execute but flag
    execute_decision(agent_output)
    flag_for_audit(request_id)
else:
    # High confidence—execute and move on
    execute_decision(agent_output)

The ROI Equation

A well-built agentic system handles 60-80% of requests without human intervention, while maintaining an audit trail for every decision. For claims processing, this means:

  • Before: 100 claims/day, 2 people, 8 hours, cost = $400/day
  • After: 100 claims/day, 1 person (oversight only), 2 hours, cost = $100/day

The $300/day savings compounds to $109k/year per process. Scale to 5 processes, and you're looking at half a million in annual labor reductions—before accounting for faster settlement times and improved accuracy.

But only if you build it right. Build it wrong, and you're automating mistakes at scale.

Next Steps

Start small. Pick one well-defined process (customer onboarding, claims triage, support escalation). Build the agent, the tool layer, and the verification system for that one process. Get it to production. Measure it. Iterate.

Then replicate the pattern to the next process. The infrastructure you build for process one will be 80% reusable for processes two through ten.

The teams winning at agentic AI aren't the ones with the fanciest prompts. They're the ones with the best operational discipline—verification at every step, observability everywhere, and clear escalation paths when things get uncertain.

Build it right, and agents become a force multiplier for your human teams. Build it wrong, and they become a liability.


Have you deployed agentic systems? What was your toughest operational challenge? Reach out—we'd love to hear your story.

Tech Stack

AnthropicPythonKubernetes

The Ovalleaf Weekly, every week.

What we built, what broke, and what we learned — straight from the engineers doing the work.

One email a week. No spam, unsubscribe any time. See our Privacy Policy.