There's a pattern I've noticed in every serious engineering team that starts building production agentic AI systems.

Week one: excitement. The agent works. It reasons, it calls tools, it produces useful output. The team ships a demo.

Week four: confusion. The agent works but it's slow, expensive, and occasionally does something unexpected. The team starts adding things — a vector store here, a session manager there, some retry logic, a summarization step for long conversations.

Week eight: recognition. An engineer who's been around long enough looks at what they're building and says: "Wait. This is just session management. This is just a workflow engine. This is just an API gateway. We've built all of this before."

They're right.

The engineering required to run agents reliably in production is not new engineering. It is classical software engineering — distributed systems patterns, API infrastructure, identity and access management, observability, fault tolerance — applied to a new workload type with a few specific adaptations.

The industry has been slow to recognize this because the AI framing dominates the conversation. We talk about prompts, models, context windows, and reasoning chains. We treat the harness — everything surrounding the model — as an AI problem. It isn't. It's a software engineering problem. And that's good news, because software engineering already knows how to solve it.

This issue is a full mapping: every component of the agentic harness to its classical engineering equivalent, what's genuinely new, and what's the same problem you've been solving for twenty years.

What Is a Harness?

The term comes from testing. A test harness is the infrastructure around the thing being tested — the setup, the mocking, the assertions, the teardown. The harness doesn't do the work. It creates the conditions for the work to happen safely and observably.

An agentic harness is the same concept applied to production. The agent — the LLM doing the reasoning — is the core. The harness is everything surrounding it: the session management that persists state, the context management that assembles the prompt, the auth infrastructure that gates tool access, the orchestration layer that sequences steps, the observability stack that captures what happened, the isolation environment that contains the blast radius.

The harness doesn't reason. It doesn't call tools. It doesn't generate text. It creates the conditions for the agent to do those things safely, reliably, and observably — and it ensures that when the agent fails, the failure is contained, diagnosed, and recoverable.

Most teams underinvest in the harness because it isn't glamorous. The model is glamorous. The harness is plumbing. But in production, the reliability of your agent system is almost entirely determined by the quality of the harness. The model will fail sometimes. The harness determines whether that failure is an incident or a routine recovery.

The Components, One by One

Let's go through each major harness component — what the classical engineering equivalent is, what the agentic version adds, and what the core problem actually is.

Memory and Session State

Classical equivalent: Session management

Web applications solved this problem in the early 2000s. Users interact with stateless HTTP servers. Between requests, state needs to persist somewhere. The solution: externalize session state to a shared store — Redis, Memcached, a database — keyed by session ID, with TTL-based expiry, serialization, and distributed access.

The agentic version is structurally identical. LLM calls are stateless. Between calls, state needs to persist somewhere. The solution: externalize agent state to a shared store — Redis for hot state, Postgres for durable state — keyed by session ID, with TTL-based expiry, serialization, and distributed access.

What's added: semantic retrieval. A user session store doesn't need to answer the question "what's the most relevant thing I've stored, given this current query?" An agent memory store does. The vector store, the retrieval pipeline, the episodic-to-semantic consolidation — these are additions on top of the classical session management pattern, not replacements for it.

The core problem: managing per-session state across a stateless execution layer. You've been solving this since PHP.

Context Window Management

Classical equivalent: Pagination and buffer management

APIs that return large datasets don't return everything at once. They return bounded result sets with cursors — the client manages where it is in the dataset, requests the next page when needed, and never loads more than it can handle at once. Buffer management in streaming systems works the same way: process what fits, slide the window, drop what's been processed.

Context window management is buffer management for text. The LLM call has a bounded token limit. The agent manages what fits in that limit, what gets compressed when it doesn't fit, and what gets evicted when compression isn't enough. The sliding window, the cursor, the bounded buffer — same concepts, different medium.

What's added: LLM-based compression. Classical buffer management drops old content. Agentic context management can summarize it first — using a model call to distill a long conversation into a compact representation that preserves semantic content. This is genuinely novel. But the problem it's solving — "I have more state than fits in my working memory, how do I manage it?" — is ancient.

The core problem: bounded buffer management with lossy compression. Streaming systems have been doing this since the beginning.

Authentication and Authorization

Classical equivalent: Service-to-service auth and RBAC/ABAC

Microservices authenticate to each other using scoped, short-lived credentials — OAuth client credentials, mTLS certificates, API keys with narrow permissions. The principle of least privilege: each service gets exactly the access it needs for its role, no more. Credentials rotate. Audit trails record every access.

Authorization is handled by policy engines — OPA, AWS IAM, RBAC systems — that evaluate a request against a set of rules: "does this identity have permission to perform this action on this resource?" Policy is centralized, version-controlled, and applied consistently.

Agent identity and JIT tokens are service-to-service auth applied to a new actor type. The agent is a service. It authenticates to tools using scoped, short-lived credentials. The principle of least privilege applies: the agent gets exactly the permissions it needs for the current task, no more. Credentials expire. Audit trails record every access.

What's added: task-context as a policy dimension and HITL approval gates for irreversible actions. Classical RBAC asks "does this service have permission?" Agentic policy asks "does this agent have permission, for this task type, at this scope level?" The policy evaluation is more contextual. The infrastructure — policy engine, credential issuer, audit log — is identical.

The core problem: scoped credential lifecycle management and policy evaluation. IAM solved this. We're extending it to a new actor type.

Orchestration

Classical equivalent: Workflow engines

Airflow, Temporal, Step Functions, Celery — workflow engines define sequences of tasks with dependencies, retry logic, timeout handling, and durable execution. Each step has inputs and outputs. Failure at any step triggers retry or compensation. The entire workflow is checkpointed so that a failure mid-execution doesn't require restarting from the beginning.

Agent orchestration is a workflow engine where some of the routing logic is decided by an LLM rather than statically defined. LangGraph, CrewAI, AutoGen — these are workflow engines with probabilistic edges. The step sequence isn't fully predetermined; the model decides at certain nodes which step to take next based on the current state.

What's added: non-deterministic routing. Classical workflow engines have static DAGs — the flow graph is defined before execution. Agentic orchestrators have dynamic edges — the model decides at runtime. This is the genuinely novel part. But the surrounding infrastructure — step definitions, retry logic, timeout handling, checkpoint-based recovery, dead letter queues for failed tasks — is classical workflow engine design, unchanged.

The core problem: durable execution of a graph of tasks with failure recovery. Temporal has a deep answer to this. Most agentic frameworks are reinventing it from scratch.

Tool Integration

Classical equivalent: RPC and API client patterns

Services call other services via typed interfaces — gRPC, REST clients, service mesh. Request/response contracts are enforced by schemas. The client layer handles retries with exponential backoff, circuit breakers that fast-fail on persistent failures, timeout enforcement, and structured error handling. The service mesh handles service discovery — clients don't need to know where services live, they ask the mesh.

Model Context Protocol is typed RPC with dynamic discovery. The agent calls tools via a standardized protocol with defined schemas. The MCP gateway handles the same retry, circuit breaker, and timeout patterns. The MCP registry handles discovery — the agent can find what tools are available without hardcoding endpoints.

What's added: semantic tool selection. Classical RPC clients call a specific service by name. Agentic tool clients can describe what they need and have the appropriate tool resolved by semantic matching. This is discovery, taken one step further. The client-side reliability patterns are identical.

The core problem: typed remote procedure calls with reliability guarantees. gRPC has a very good answer. MCP is building a domain-specific version for agent tool access.

Fault Tolerance and Recovery

Classical equivalent: Circuit breakers, retry logic, and dead letter queues

Resilience4j, Hystrix, Polly — every distributed systems practitioner knows the patterns. Transient failures are retried with exponential backoff and jitter. Persistent failures trip the circuit breaker, fast-failing requests until the downstream service recovers. Unrecoverable messages route to a dead letter queue for inspection and manual replay.

Agent fault tolerance is the same pattern applied to the agent step loop. Transient tool failures are retried with exponential backoff. Persistent tool failures abort the step and trigger the agent's failure handling logic. Unrecoverable sessions route to the dead letter queue. The only addition is checkpoint-based mid-task resume — because agent tasks can be long-running, a failure at step 40 of a 50-step task should resume from step 40, not restart from step 1.

What's added: checkpoint-based resume for long-running tasks. This is a natural extension of the pattern — distributed systems that run long jobs have always had this requirement. Map-Reduce had it. Spark has it. The agent version is the same concept applied to a reasoning loop rather than a data processing pipeline.

The core problem: graceful failure with a clear recovery path. The patterns exist. The implementations exist. Use them.

Isolation and Sandboxing

Classical equivalent: Container isolation

Kubernetes, Docker, cgroups, seccomp — the container ecosystem provides process isolation, resource limits, syscall filtering, ephemeral filesystems, and network namespacing. Each workload runs in its own isolated environment. A misbehaving container cannot affect adjacent containers or the host.

Agent execution sandboxing is container isolation applied at session granularity rather than service granularity. Each agent session gets its own isolated execution environment with the same resource limits, the same seccomp profiles, the same ephemeral filesystem semantics, the same network namespacing.

What's added: per-session isolation granularity. Traditional containerization isolates services — the payment service runs in a container, the notification service runs in a container. Agentic isolation goes further — each individual session run is its own container, spinning up and tearing down with the task. This is more granular, but the underlying technology and concepts are identical.

The core problem: workload isolation. The container ecosystem solved this comprehensively. We're applying it at a different granularity.

Observability

Classical equivalent: Distributed tracing

OpenTelemetry, Jaeger, Zipkin — distributed traces follow a request through multiple services. Each span captures the service name, operation, duration, inputs/outputs, and errors. Trace context propagates through service calls via headers, maintaining the causal chain across service boundaries.

Agent step tracing is distributed tracing applied to a reasoning loop. Each span is an agent step — the reasoning, the tool call, or the model invocation. Trace context propagates through the agent's state, maintaining the causal chain across steps. The trace reconstructs the full execution path from trigger to completion.

What's added: token cost per span and decision logging. Classical traces capture latency and errors. Agent traces also capture token consumption (the cost metric unique to LLM workloads) and decision points — what options the model considered at each reasoning step. This additional semantic richness is what makes agent observability harder than service observability, but the underlying tracing infrastructure is unchanged.

The core problem: trace context propagation through a multi-step execution. OpenTelemetry is the right foundation. LLM-specific platforms like Langfuse are building the domain-specific layer on top.

Rate Limiting and Resource Budgets

Classical equivalent: API rate limiting

Token bucket, leaky bucket, Redis-backed counters — API gateways enforce per-client request quotas. Excess requests are queued or rejected with structured errors. Burst allowances handle spiky traffic. Per-tenant isolation ensures one customer's traffic doesn't affect another's.

Agent token budgets are resource rate limiting applied to a new resource unit. Instead of requests per minute, the unit is LLM tokens per session and tool calls per step. Instead of an API gateway enforcing quotas at the HTTP layer, the agent orchestration layer enforces quotas at the step level. The underlying mechanics — token bucket, per-tenant isolation, structured rejection — are identical.

What's added: token-denominated quotas. Tokens are a resource type that classical rate limiters weren't designed for, because they didn't exist. But the enforcement mechanism, the per-tenant isolation, and the budget management are pure classical rate limiting, extended to a new resource dimension.

The core problem: per-client resource budgeting with enforcement. API gateways have a robust answer. Apply it to the LLM layer.

Multi-Tenancy

Classical equivalent: Tenant isolation patterns

Row-level security, namespace scoping, VPC isolation, per-tenant resource quotas — multi-tenant SaaS platforms have solved this comprehensively. Each tenant's data, compute, and network access is logically isolated. Shared infrastructure, isolated planes. No tenant can access another's data or consume their resource allocation.

Multi-tenant agent systems require the same isolation applied to agent-specific resources: session state namespaced by tenant, memory stores namespaced by tenant, tool access restricted by tenant policy, token budgets allocated per tenant, audit logs queryable per tenant. The patterns are identical. The namespacing keys are agent-specific, but the isolation model is unchanged.

What's added: memory store namespacing as an additional isolation dimension. Classical multi-tenancy namespaces data stores and compute. Agent multi-tenancy also namespaces memory — the episodic and semantic memory accumulated by one tenant's agents must not be accessible to another tenant's agents. This is an additional namespace, not a new concept.

The core problem: logical tenant isolation on shared infrastructure. SaaS platforms have been solving this for fifteen years.

Human Approval Flows

Classical equivalent: Change management and approval workflows

ITSM systems, GitHub PR reviews, deployment approval gates — high-impact changes to production systems require human approval before execution. The requestor, the approver, the scope of the change, and the decision are all recorded. Approvals expire if not acted on within a window.

Agent HITL gates are change management applied to agent actions. High-impact agent actions — irreversible writes, large-scale modifications, access to sensitive data — require human approval before execution. The same requestor, approver, scope, and decision semantics. The same approval TTL. The same audit record.

What's added: async mobile and messaging channels for approval, and dry-run previews. Classical change management approvals happen in ticketing systems. Agent HITL approvals need to reach a human who may not be at their desk — Slack, push notification, email with one-click approve/deny. And agents can offer something a deployment ticket can't: run the action in dry-run mode first and show the human exactly what would happen before asking for confirmation. Same approval workflow, better interface.

The core problem: structured approval before high-impact irreversible actions. Change management solved this. We're extending it to agent actions.

What's Actually New

After mapping every component to its classical equivalent, it's worth being precise about what is genuinely novel in the agentic harness.

Three things:

Non-deterministic execution paths. Classical workflow engines have static graphs. Agentic orchestration has LLM-decided routing. The same task can follow different execution paths on different runs, based on the model's reasoning about the current state. This requires the harness to handle branching logic it can't fully anticipate, instrument decisions it can't predict, and reason about equivalence across runs that took different paths.

Semantic retrieval on top of state management. Classical session state is retrieved by key. Agent memory is retrieved by relevance — the harness needs to answer "what's the most useful thing I've stored, given this current context?" This requires the vector store, the retrieval pipeline, and the relevance scoring — none of which exist in classical session management.

Token cost as a first-class resource. Classical infrastructure is priced by compute, storage, and bandwidth. Agent infrastructure is priced by all of those, plus LLM tokens — a resource that doesn't map cleanly to anything in classical systems. Token budgeting, cost attribution per session, and cost-aware routing are genuinely new infrastructure requirements.

Everything else is classical engineering, contextually applied. The mistake — and it's an expensive one — is treating the entire harness as novel and building it from scratch rather than recognizing which components are solved problems and applying the existing solutions.

Why This Recognition Matters

The teams that build the best agentic systems in production aren't the ones with the deepest LLM expertise. They're the ones with the deepest infrastructure expertise — engineers who've built distributed systems, managed multi-tenant SaaS platforms, implemented API gateways, and operated high-availability services.

They recognize the patterns. When they need agent memory, they reach for Redis and add a retrieval layer. When they need orchestration, they evaluate Temporal before writing a custom DAG engine. When they need auth, they extend their existing IAM system rather than building a new one. When they need observability, they extend their OpenTelemetry pipeline rather than deploying a parallel stack.

This recognition has practical consequences:

It accelerates timelines. Recognizing that agent session management is Redis with a retrieval layer means you're building on twenty years of Redis operational experience, not reinventing distributed cache eviction from scratch.

It reduces incidents. Classical infrastructure patterns have been battle-tested at scale. Circuit breaker implementations have been tuned across thousands of production deployments. Container isolation has been tested against real attack scenarios. Building on these foundations means inheriting their reliability, not discovering their failure modes from scratch.

It informs hiring. The best people to build agentic infrastructure are not necessarily AI researchers. They're distributed systems engineers who can recognize a workflow engine problem and reach for the right tool, session management engineers who can extend an existing state store rather than building a new one, and security engineers who understand credential lifecycle management and can extend it to a new actor type.

The LLM is the novel part. The harness that makes it production-ready is engineering's greatest hits — applied with precision, extended with restraint, and built on the shoulders of two decades of distributed systems practice.

— Santosh

👀 Also Watching

  • Temporal.io — the workflow engine that gets closest to what agentic orchestration actually needs: durable execution, checkpoint-based recovery, and exactly-once task semantics. If your agentic orchestration layer is getting complex, evaluate this before writing more custom code.

  • OpenTelemetry's semantic conventions for LLMs — the emerging standard for how to instrument model calls within OTEL spans. Building on this from day one avoids a painful migration later.

  • The "boring technology" principle — Dan McKinley's classic piece on choosing boring technology remains the best framing for what this post argues. Build the AI layer with frontier technology. Build the harness with the most battle-tested tools available.

Until next time,

Learn to use AI. Use AI to learn.

If someone forwarded this to you, subscribe at whattheagent.com. If this was useful, forward it to one engineer who needs it.

Keep Reading