<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0" xmlns:atom="http://www.w3.org/2005/Atom" xmlns:dc="http://purl.org/dc/elements/1.1/">
  <channel>
    <title>DEV Community: Austin Vance</title>
    <description>The latest articles on DEV Community by Austin Vance (@austinbv).</description>
    <link>https://dev.to/austinbv</link>
    <image>
      <url>https://media2.dev.to/dynamic/image/width=90,height=90,fit=cover,gravity=auto,format=auto/https:%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Fuser%2Fprofile_image%2F305023%2Fc978f899-9fa5-4b1e-9ad9-e3f60313fd65.jpeg</url>
      <title>DEV Community: Austin Vance</title>
      <link>https://dev.to/austinbv</link>
    </image>
    <atom:link rel="self" type="application/rss+xml" href="https://dev.to/feed/austinbv"/>
    <language>en</language>
    <item>
      <title>AI Agent Evaluation Steers the Harness | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Wed, 03 Jun 2026 15:24:58 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/ai-agent-evaluation-steers-the-harness-focused-labs-3c9k</link>
      <guid>https://dev.to/focused_dot_io/ai-agent-evaluation-steers-the-harness-focused-labs-3c9k</guid>
      <description>&lt;p&gt;Agent evaluation is being conflated with scoring agent performance. Such scoring is useful, but what one gets from such scoring are edits to the harness.&lt;/p&gt;

&lt;p&gt;If an evaluation fails to affect the harness after the fact, the team was simply left with a dashboard written up in better language. LangChain puts the sharper version in its Deep Agents writeup, where &lt;a href="https://www.langchain.com/blog/how-we-build-evals-for-deep-agents" rel="noopener noreferrer"&gt;every evaluation is a vector that shifts the behavior of the agentic system&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;That sentence carries the argument.&lt;/p&gt;

&lt;p&gt;An eval suite is part of the system. The eval suite is driving the agent to behave in one way and not another. A sloppy eval is cheap to run. A broad benchmark is a good thing to include in a review. But a broad benchmark does not push the system to perform well on the task distribution actual users encounter.&lt;/p&gt;

&lt;p&gt;I see people treat evaluation of AI agents similarly to how they score the performance of agents. Yes, that matters. But what does the score from that evaluation buy? Edits to the harness. That one failing trace gave the team something valuable. Insight into the structure of the harness.&lt;/p&gt;

&lt;h2&gt;
  
  
  The harness is where the lesson lands
&lt;/h2&gt;

&lt;p&gt;An agent harness is the stuff around the model: tools, tool descriptions, prompts, routing rules, memory, retrieval, runtime policy, state shape, and all the weird connective tissue that decides what the model can actually do. We have written about this in the context of &lt;a href="https://focused.io/lab/developing-ai-agency" rel="noopener noreferrer"&gt;developing AI agency&lt;/a&gt;, because model swaps get too much credit and harness changes get too little ownership.&lt;/p&gt;

&lt;p&gt;Agent evaluation belongs there.&lt;/p&gt;

&lt;p&gt;LangChain's Better-Harness writeup makes the loop explicit: &lt;a href="https://www.langchain.com/blog/better-harness-a-recipe-for-harness-hill-climbing-with-evals" rel="noopener noreferrer"&gt;evals create the learning signal for iteratively improving prompts, tools, tool descriptions, instructions, and runtime scaffolding&lt;/a&gt;. To recap the useful part: design evals, run evals, get learning signal from evals, then use that learning signal to improve the components around the model. The evals are training data for the harness.&lt;/p&gt;

&lt;p&gt;This might happen because of a weakly worded instruction, or a tool set up with incorrect parameters, or a retrieval component that sends the agent on a wild goose chase through a swamp of useless information, or a routing rule that gives the cheap model a go first even though that model is likely to take patience to get to the right answer, or because the agent's state is disappearing at exactly the wrong moment as the agent is trying to recover from something.&lt;/p&gt;

&lt;p&gt;The score does not fix these problems. The score only earns the right to edit the harness.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1p75ciwkejhk1zwhlvan.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1p75ciwkejhk1zwhlvan.png" alt="Circular flow showing production traces turning into eval datasets, scores, harness edits, holdout gates, and release." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The eval loop is only useful when it changes the harness and then protects the next release.&lt;/p&gt;

&lt;h2&gt;
  
  
  Production traces are the raw material
&lt;/h2&gt;

&lt;p&gt;The best eval cases come from the system embarrassing itself.&lt;/p&gt;

&lt;p&gt;Here is the refund agent case. The customer asks for a refund and the agent fails to check eligibility. For the research agent example, the agent reads the first file in a series of linked files but fails to open the rest. It then confidently and incorrectly summarizes the material for the user. For the coding agent, the agent changes the implementation but fails to update the tests. The agent then reports success because the patch compiled in the agent's head.&lt;/p&gt;

&lt;p&gt;LangChain's readiness checklist says the first move is to &lt;a href="https://www.langchain.com/blog/agent-evaluation-readiness-checklist" rel="noopener noreferrer"&gt;manually review 20 to 50 real agent traces before building eval infrastructure&lt;/a&gt;. The fact that a team would be willing to read 50 real traces is what makes this refreshingly boring and, more important, it saves months while the team avoids building an eval suite from vibes, guesses, and the latest loud failure.&lt;/p&gt;

&lt;p&gt;There is a distinction between capability evals and regression evals. The ability of the system to do new things will naturally have a low pass rate at first because the team is hill climbing. Once the system is able to do something, it should continue to do that thing in the future. Regression evals catch the system falling back to old behavior that the product relies on.&lt;/p&gt;

&lt;h2&gt;
  
  
  Evaluate the path when the path is the product
&lt;/h2&gt;

&lt;p&gt;Another simplistic assumption for agent evaluations: just grade the final answer.&lt;/p&gt;

&lt;p&gt;For a variety of reasons, grading the final answer simply does not work for task classes where the path is part of the product surface. The refund agent rejects a refund request because it skipped a check against company policy. The data agent in a meeting creates a chart by issuing a full table scan in production. The support agent solves the ticket by leaking internal notes to the customer in a conversation.&lt;/p&gt;

&lt;p&gt;Google's Agent Development Kit docs make the split cleanly: agent evaluation should assess &lt;a href="https://adk.dev/evaluate/" rel="noopener noreferrer"&gt;both final output quality and trajectory, meaning the sequence of steps, tools, and reasoning the agent used&lt;/a&gt;. Their ADK codelab turns that into a testing workflow with &lt;a href="https://codelabs.developers.google.com/adk-eval/instructions" rel="noopener noreferrer"&gt;golden datasets that preserve user query, trajectory, and final response&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;The release gate has to know what to test for, which behaviors rely on an acceptable path and which behaviors rely only on the output of the agent for a given input. Otherwise the team either blocks good changes with brittle tests or ships dangerous changes because the final answer looked right.&lt;/p&gt;

&lt;h2&gt;
  
  
  System, trace, and node evals answer different questions
&lt;/h2&gt;

&lt;p&gt;The name Agentic CLEAR serves to identify the different levels at which a team can review and assess the ability of an agent to complete complex tasks. The paper describes an evaluation framework that produces insights at &lt;a href="https://arxiv.org/abs/2605.22608" rel="noopener noreferrer"&gt;system, trace, and node levels of granularity&lt;/a&gt;. IBM's project page expands that into an open-source package that evaluates traces across &lt;a href="https://ibm.github.io/CLEAR/" rel="noopener noreferrer"&gt;system-wide issues, node or component analysis, and trace-level inspection&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Those levels map to different harness changes.&lt;/p&gt;

&lt;p&gt;A system-level eval asks whether the workflow produced the outcome the product cares about. Did the claims agent resolve the case? Did the analyst agent produce a grounded answer? Did the coding agent land a patch that passed the intended checks? System-level failures point to architecture: routing, ownership, data access, memory, deployment boundary, or business process fit.&lt;/p&gt;

&lt;p&gt;Trace-level evaluations assess whether an agent follows a task through to a coherent end. They look at whether an agent searches for the appropriate information prior to writing, whether an agent uses the correct tool to send a package, whether an agent sends off work that can be completed in parallel, and whether an agent follows through on a task that has no end point. Trace-level failures suggest problems with planning, tool use, interrupt handling, retry policy, and multi-agent orchestration. This is where &lt;a href="https://focused.io/lab/multi-agent-orchestration-in-langgraph-supervisor-vs-swarm-tradeoffs-and-architecture" rel="noopener noreferrer"&gt;multi-agent orchestration&lt;/a&gt; stops being a diagram and starts being an eval surface.&lt;/p&gt;

&lt;p&gt;Node-level evaluations examine individual behaviors produced by an agent as it goes through a task. Did a retrieval node produce the correct documents? Does a summarizer preserve constraints? Did a tool call include the tenant ID? Did a model produce the correct function for the job? Node-level failures can be addressed by changing local parts of the harness, including a tool schema, prompt wording, retrieval filters, model choice, and guardrail placement.&lt;/p&gt;

&lt;p&gt;One pass rate does not cut it for this type of evaluation. A single number will not highlight the repair surface to the agent developer.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fajt2m2dswnphrwdt22uo.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fajt2m2dswnphrwdt22uo.png" alt="Layered stack showing system, trace, and node levels of AI agent evaluation feeding harness changes." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;System, trace, and node evals answer different questions, so they should change different parts of the harness.&lt;/p&gt;

&lt;h2&gt;
  
  
  Observability feeds evaluation, then evaluation changes behavior
&lt;/h2&gt;

&lt;p&gt;Agent evaluation without traces becomes example-driven theater in which teams argue about a few examples, write up synthetic test cases, and then do a qualitative evaluation of behavior that nobody has actually seen triggered in real life.&lt;/p&gt;

&lt;p&gt;Observability without evaluation is storage. I like traces. I like spans. As wonderful as these things are, the operational data the system is running on is also a receipt for how the system got to that point. That is what can become evaluation data.&lt;/p&gt;

&lt;p&gt;Honeycomb's AI-era observability piece spells out how agentic workflows depend on operational data of high cardinality, queried quickly, because agents query production context iteratively on a case-by-case basis. In their words, agentic workflows depend on &lt;a href="https://www.honeycomb.io/blog/evaluating-observability-tools-for-the-ai-era" rel="noopener noreferrer"&gt;fast, queryable, high-cardinality operational data because agents ask iterative questions against raw production context, not just dashboards&lt;/a&gt;. The easiest way to compromise an evaluation dataset is for production traces to stop including tenant ID, tool arguments, retrieval sources, policy decisions, model versions, prompt versions, and release versions.&lt;/p&gt;

&lt;p&gt;The eval dataset should be downstream of observability and upstream of the harness.&lt;/p&gt;

&lt;p&gt;As such, &lt;a href="https://focused.io/lab/agent-monitoring-is-an-infrastructure-workload" rel="noopener noreferrer"&gt;Agent Monitoring Is an Infrastructure Workload&lt;/a&gt;. Monitoring, log collection, metrics collection, and tracing must be treated as workloads and run as services. Otherwise they are screenshots in a vendor console. The trace proves the agent failed. Then it dies in storage.&lt;/p&gt;

&lt;h2&gt;
  
  
  The release gate is the boring power move
&lt;/h2&gt;

&lt;p&gt;A good release shape is a pull request that includes the modified harness, with all changes visible in the diff, plus the relevant evaluations that identified the change. The diff states that trace 481 failed and that the failed trace and its evaluation were used to modify the tool description. Or that a retrieval filter changed to avoid tenant leakage found by a node eval. Or that a route now uses a stronger model because a holdout set found cheap-model failures. The release is blocked by a regression test suite that found a path violation in the payment-approval case.&lt;/p&gt;

&lt;p&gt;That is boring in the correct way.&lt;/p&gt;

&lt;p&gt;LangChain's readiness checklist describes a CI/CD flow where &lt;a href="https://www.langchain.com/blog/agent-evaluation-readiness-checklist" rel="noopener noreferrer"&gt;code or prompt changes trigger offline evals, preview deployments, online evals, and promotion only after quality gates pass&lt;/a&gt;. Better-Harness then covers how &lt;a href="https://www.langchain.com/blog/better-harness-a-recipe-for-harness-hill-climbing-with-evals" rel="noopener noreferrer"&gt;optimization examples can guide improvement, while holdout evals and human review protect against overfitting the harness to visible cases&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Without that owner, AI agent evaluation becomes a pile of numbers. With that owner, evals become a steering wheel.&lt;/p&gt;

&lt;h2&gt;
  
  
  The first useful eval stack is small
&lt;/h2&gt;

&lt;p&gt;The practical stack does not have to start fancy.&lt;/p&gt;

&lt;p&gt;We should start by recording real usage traces, and then the failures in there as well, with corresponding success criteria that any reasonable human could check. Distinguish between the capability hills that the evaluation is trying to climb, and the regressions that it is trying to prevent. Tag evaluations by behavior. Holdouts should not be part of the agent's optimization loop. Log the part of the harness that changed for each failed eval. Run regression evals in CI before the agent gets another production release.&lt;/p&gt;

&lt;p&gt;Note the granularity of agent evaluation is about a system workflow and thus System-level evaluations about the entire system workflow as a whole. Also note that trace-level evaluations verify the acceptability of the path an agent took to arrive at a conclusion. Finally, note that node-level evaluations verify the local step an agent took through a given node was correct.&lt;/p&gt;

&lt;p&gt;Even good AI will sometimes fail to reach its desired outcome, and that is where the dataset comes from.&lt;/p&gt;

&lt;p&gt;Every meaningful failure of the AI system should become evidence which a human can reuse. Thus a trace of AI system failure through human interactions becomes an eval of an AI program. An eval of an AI program becomes a harness edit. A harness edit goes through the holdout gate for that AI system. The next production run of the AI system produces more evidence.&lt;/p&gt;

&lt;p&gt;In the end, AI agent evaluation is engineering.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
      <category>langchain</category>
    </item>
    <item>
      <title>Agent Skills Are a Software Supply Chain Surface | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Thu, 28 May 2026 22:09:15 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agent-skills-are-a-software-supply-chain-surface-focused-labs-3k46</link>
      <guid>https://dev.to/focused_dot_io/agent-skills-are-a-software-supply-chain-surface-focused-labs-3k46</guid>
      <description>&lt;p&gt;Agent skills, designed to serve as instructional features for developers building applications using agentic AI, are increasingly becoming supply-chain features that developers can download and execute. Agent skills packaged as code and distributed through marketplaces are becoming what I refer to as “executable supply-chain artifacts”. Like any other software feature, these artifacts can have code shaped power wrapped in a friendly-looking markdown jacket.&lt;/p&gt;

&lt;p&gt;As AI agent skills are distributed through marketplaces and enterprise tools, the security world has to examine them as executable artifacts. A new paper, “An Empirical Study on Malicious AI Agent Skills in Marketplaces,” found that 76 of 3,984 total AI agent skills in marketplaces contained malicious payloads for credential theft, backdoor installation, and data exfiltration. The authors also found that 13.4% contained at least one critical issue after manual review. They confirmed that eight malicious skills were still available in one of the marketplaces they studied at publication time (&lt;a href="https://arxiv.org/abs/2605.28588v1" rel="noopener noreferrer"&gt;arXiv, 2026&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;That changes the conversation around agentic AI security.&lt;/p&gt;

&lt;p&gt;The skill file has become a package boundary.&lt;/p&gt;

&lt;h2&gt;
  
  
  Skills are becoming packages
&lt;/h2&gt;

&lt;p&gt;About a year ago we would show a skill file that was essentially a repository of an application, next to a set of rules written by a developer for a model such as Claude Code, Cursor, an agent, or workflow assistant. That repository of rules would give the model additional context or habits for how to process a query or workflow, such as being able to extract information from a complex table or generate supporting text for a given prompt.&lt;/p&gt;

&lt;p&gt;Now the pattern has grown teeth.&lt;/p&gt;

&lt;p&gt;The problem is that shortcuts cross trust boundaries.&lt;/p&gt;

&lt;p&gt;A skill package has to answer plain questions: Who was the owner of the skill, what did it do, where did it get executed, what credentials were in use, what tools were used, what was the configuration of the tool’s sandbox, what were the results of the evaluations for the skill, what traces were produced by the skill, what user action started it, how rollback works for that user.&lt;/p&gt;

&lt;p&gt;Honeycomb announced Agent Skills in the form of eight skills, two agents, and workflows that encode the observability expertise required to instrument, observe, and debug OpenTelemetry-enabled production services and migrate from distributed tracing systems into observability stacks (&lt;a href="https://www.honeycomb.io/blog/accelerate-opentelemetry-migrations-honeycomb-agent-skills" rel="noopener noreferrer"&gt;Honeycomb, 2026&lt;/a&gt;). Lyft built a self-serve platform with LangGraph and LangSmith for domain experts to define custom agents, while the platform manages the underlying graph, tools, safety, state, tracing, dashboards, and LLM-as-a-judge evaluation (&lt;a href="https://www.langchain.com/blog/lyft-built-a-self-serve-ai-agent-platform-for-customer-support-with-langgraph-and-langsmith" rel="noopener noreferrer"&gt;LangChain, 2026&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;That is the right direction for adoption.&lt;/p&gt;

&lt;p&gt;Governance has to move with that power.&lt;/p&gt;

&lt;p&gt;This is directly related to &lt;a href="https://focused.io/lab/agent-monitoring-is-an-infrastructure-workload" rel="noopener noreferrer"&gt;agent monitoring as an infrastructure workload&lt;/a&gt;. That note cautioned against monitoring individual model calls. For skills, monitoring has to track the installed artifact, runtime permissions, traces, user actions, and recovery process.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzgw6fxa67ne8vbcv4iqp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzgw6fxa67ne8vbcv4iqp.png" alt="Architecture diagram showing marketplace, self-serve editor, and optimizer inputs producing a skill package that passes provenance, permission, sandbox, runtime, credential, tool, data, and trace checks." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The skill package is where untrusted instructions become executable production behavior.&lt;/p&gt;

&lt;p&gt;Incident review then starts with ‘how did we feel’ instead of examining the facts of the incident.&lt;/p&gt;

&lt;h2&gt;
  
  
  The optimizer makes the boundary harder
&lt;/h2&gt;

&lt;p&gt;There are also techniques that treat the skill file as external state for a frozen agent and use scored rollouts to inform bounded edits on the skill document. SkillOpt reports wins or ties in 52 out of 52 model, benchmark, or harness comparisons across direct chat, Codex-based chat, and Claude Code-based chat (&lt;a href="https://arxiv.org/abs/2605.23904v2" rel="noopener noreferrer"&gt;SkillOpt, 2026&lt;/a&gt;). SkillGrad treats the skill package as a parameter and uses trajectory-level loss to patch the package over time (&lt;a href="https://arxiv.org/abs/2605.27760v1" rel="noopener noreferrer"&gt;SkillGrad, 2026&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;The manifest of a skill in serious skill systems includes a list of tools that the skill invokes, a list of files that the skill reads and/or writes to, a list of network locations that the skill connects to, a list of secrets that the skill can request, a list of data classes that the skill can read, and a list of human approvals that are needed for a skill to perform an action that could affect data external to the skill.&lt;/p&gt;

&lt;p&gt;Reviews do not make skills safe forever. A reviewed skill can go into production clean, then run through evals, production traces, failed tasks, and large tests. The habits it picks up may be useful. They may also add permission, relax assumptions, or change data handling through a single text edit that looked safe because it passed review and scored high.&lt;/p&gt;

&lt;p&gt;Agyn defines “definition of an agent” in this context as “code through a Terraform provider (e.g., provisioning a function), a signal-driven stateful serverless runtime on Kubernetes (e.g., a Python loop processing events), and a zero-trust, least-privilege security model for agents that hold state and access internal services” (&lt;a href="https://arxiv.org/abs/2605.27575v1" rel="noopener noreferrer"&gt;Agyn, 2026&lt;/a&gt;). In summary, the shape of an agent as a piece of infra to be governed is the intersection of its definition (as code), its runtime (as a serverless process), and the corresponding boundaries on permissions that it must operate within as a state holding, service accessing agent.&lt;/p&gt;

&lt;p&gt;More problems arise because skills are packaged in readable files and can be dropped into workflows quickly. Package managers with no provenance tracking become malware distribution channels. CI/CD pipelines with no scoped credentials become secret leak engines. Folklore around prompts, created through limited reproduction or no change history, enables suboptimal agents to be built and deployed through self-serve platforms.&lt;/p&gt;

&lt;p&gt;If we assign a skill to write out release notes, it will be in a small sandbox. A skill that updates billing / refund information for customers / production data / source code / users’ identities should be in a totally different box and inherit the same spending discipline we previously discussed in &lt;a href="https://focused.io/lab/agentic-payments-move-spending-authority-into-the-runtime" rel="noopener noreferrer"&gt;agentic payments&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Trusted vs. declared runtime behavior.&lt;/p&gt;

&lt;h2&gt;
  
  
  Self-serve agents move governance to the edge
&lt;/h2&gt;

&lt;p&gt;Lyft’s description of customer support work shows the adoption pressure. Account access, damage claims, charge reviews, earnings disputes, and autonomous vehicle support are closer to support domain experts than a central MLE queue. Their old loop took months. The self-serve layer cut that loop to weeks while the platform managed state, tools, safety, and evaluation (&lt;a href="https://www.langchain.com/blog/lyft-built-a-self-serve-ai-agent-platform-for-customer-support-with-langgraph-and-langsmith" rel="noopener noreferrer"&gt;LangChain, 2026&lt;/a&gt;).&lt;/p&gt;

&lt;p&gt;For prompt libraries, the registry only needs to store the text of the prompts. For skill registries, the registry stores signed artifacts together with metadata for the artifacts: the owners, the diffs (if the artifact was created incrementally), validation results for the artifact, failure modes that are known to occur for the artifact, permission manifests for the artifact, sandbox profiles for the artifact, telemetry definitions for the artifact, and deprecation state for the artifact. The registry should enable the system to answer questions about incidents, not questions about content-library usage.&lt;/p&gt;

&lt;p&gt;What changed last night? What skill versions did which agents run last night? What tools did these skills invoke? What eval gate evaluated updates for these skills? What credential scopes were active for these agents? What customer data were read or written by these agents? What is the process for rolling back an agent to a previous skill version? (Re)Installing an agent is presumably not sufficient to “roll back” an agent.)&lt;/p&gt;

&lt;p&gt;Agent platforms are evolving to treat all of an agent’s skills as packages that can be run or installed, in effect treating operating knowledge the same way that a new product or feature would be packaged for distribution by an agent platform.&lt;/p&gt;

&lt;p&gt;The minute something gets packaged, distribution outruns inspection.&lt;/p&gt;

&lt;p&gt;Yes, there is a place for manual review, and it should be limited, though. Skills should pass static checks before they can be installed. Skills should declare what permissions they expect before it can be installed. Skills should run in a sandbox before they are promoted to full-scale task execution. The skill’s evals should be cleared before the skill is promoted to full-scale task execution. Skills should emit trace receipts during their execution. Skills should support a form of rollback after it misbehaves.&lt;/p&gt;

&lt;p&gt;The governance model for skills has to go beyond a document and meeting. The deployment record should name the owner, track versions, show the diff for each change, define permissions, list in-scope credentials, list approved tools, define the sandbox configuration, list required evaluations, show runtime traces, record the user action that deployed the skill, and define a rollback plan.&lt;/p&gt;

&lt;p&gt;The next set of incidents involving agents will be due to the skills executing on them.&lt;/p&gt;

&lt;p&gt;This is directly related to our earlier note on &lt;a href="https://focused.io/lab/agent-monitoring-is-an-infrastructure-workload" rel="noopener noreferrer"&gt;agent monitoring as an infrastructure workload&lt;/a&gt;. Monitoring individual model calls is too narrow. For skills, the system has to monitor the installed artifact, runtime permissions, traces, user actions, and recovery process.&lt;/p&gt;

&lt;p&gt;Then everyone asks who approved the agent.&lt;/p&gt;

&lt;p&gt;This also maps onto our previous observation about &lt;a href="https://focused.io/lab/agent-traces-need-to-cross-the-mcp-boundary" rel="noopener noreferrer"&gt;trace evidence across the MCP boundary&lt;/a&gt;. The trace for a skill cannot simply be a transcript of a model conversation. It has to show the skill’s actions: what capability it requested, what credential it used, what tool calls it made, and what results came back.&lt;/p&gt;

&lt;p&gt;Ask who approved the skill boundary.&lt;/p&gt;

&lt;p&gt;Otherwise the incident review starts with vibes. Bad start.&lt;/p&gt;

&lt;p&gt;We have spent real time on &lt;a href="https://focused.io/lab/developing-ai-agency" rel="noopener noreferrer"&gt;developing AI agency&lt;/a&gt; as if agency lives inside the model. Agency lives in the system: model, tools, runtime, memory, skills, and permission. Skills sit close to human expertise and close to runtime power. That combination is useful and dangerous.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fklw38ypfyduwnv57prsu.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fklw38ypfyduwnv57prsu.png" alt="Governance matrix showing install time, update time, run time, and incident time controls for provenance, permissions, sandbox policy, eval gates, trace evidence, and rollback." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Skill governance only works when the control follows the skill through its lifecycle.&lt;/p&gt;

&lt;p&gt;The skill marketplace is coming. The governance boundary should get there first.&lt;/p&gt;

</description>
      <category>ai</category>
      <category>programming</category>
    </item>
    <item>
      <title>LangChain Interrupt: Agents Moved Into the Runtime | Focused</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Thu, 28 May 2026 04:06:28 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/langchain-interrupt-agents-moved-into-the-runtime-focused-4n3d</link>
      <guid>https://dev.to/focused_dot_io/langchain-interrupt-agents-moved-into-the-runtime-focused-4n3d</guid>
      <description>&lt;p&gt;Interrupt felt different this year.&lt;/p&gt;

&lt;p&gt;Less model worship. More runtime.&lt;/p&gt;

&lt;p&gt;Instead of another round of model worship, the more useful conversations at the conference took a more practical turn. Agents work best when the workflow is built agentically from the start, but as a reality on the ground, many existing enterprise processes are simply wrapped around a model, and then buttons are pressed, forms filled out, and the output of the model is copied and pasted into another field or application. That falls apart after the demo.&lt;/p&gt;

&lt;p&gt;The better way to put agents into workflows is to build the workflow agentically in the first place. The parts that should be deterministic should be surrounded by software. The LLM can then be used for judgment, for synthesis, for planning, for dealing with ambiguity, for making priorities. And the harness and static code should be equipped with tools that have contracts. The harness and static code should be equipped with state. The harness and static code should be equipped with a way for the agent to recover from failures. And the harness and static code should give the agent enough visibility so that when the agent does something weird, someone can actually debug it.&lt;/p&gt;

&lt;p&gt;The release I kept coming back to was &lt;a href="https://www.langchain.com/blog/introducing-langsmith-engine" rel="noopener noreferrer"&gt;LangSmith Engine&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;This is the loop that people have been trying to describe for improvements of agents over time. The new trace engine watches traces of execution of agents. It clusters failures together and turns them into issues. It analyzes the production code of a harness to diagnose the root cause of a problem. It writes PRs for fixes. It proposes online evaluators. It moves failing traces of production runs into offline eval sets for further improvement.&lt;/p&gt;

&lt;p&gt;Production behavior becomes evidence. That evidence becomes an issue for the system to fix. That fix becomes an evaluator watching for the failure to come back.&lt;/p&gt;

&lt;p&gt;That is cool.&lt;/p&gt;

&lt;p&gt;This changes observability. Longstanding views of observability as viewing a trace of an application's execution as merely a receipt of an application's actions are increasingly becoming obsolete as traces within agent systems become sources of new evidence for the next cycle of improvement whether that be harness tuning, updated prompts, additional context, alternative models, the generation of new evaluators or indeed the repair of workflows.&lt;/p&gt;

&lt;p&gt;Storage has a similar point to make, as showcased by &lt;a href="https://www.langchain.com/blog/introducing-smithdb" rel="noopener noreferrer"&gt;SmithDB&lt;/a&gt;. Agent traces have a fundamentally different shape to the traces which teams are accustomed to following through web applications. In agent systems, traces have a different event density, with individual spans taking longer to execute than would be the case for a web trace, and deep, wide span trees, with again, greatly variable timing characteristics. In some cases, individual runs of an agent can include tool calls, context that was retrieved within the run of the agent, model or evaluator output, files which were opened or written to within the run, user provided feedback, or, rarely, even a full research project.&lt;/p&gt;

&lt;p&gt;An agent trace is different from an application trace. Instead of helping to debug why an application is slow or failing, an agent trace helps to understand why an agent decided to take a particular action in the first place.&lt;/p&gt;

&lt;p&gt;That is a different data problem.&lt;/p&gt;

&lt;p&gt;The same theme shows up in &lt;a href="https://www.langchain.com/blog/deep-agents-0-6" rel="noopener noreferrer"&gt;Deep Agents v0.6&lt;/a&gt;. The interesting parts are not flashy: code interpreter, programmatic tool calling, typed streaming, DeltaChannel checkpoint storage, and harness profiles for different models.&lt;/p&gt;

&lt;p&gt;This means lower cost models, e.g. Kimi, will be able to handle routine tool work such as summarization, search, extraction and so on. This type of work should not burn frontier tokens. On the other hand, frontier models will handle the harder reasoning parts of the work, with the ceiling of the model in question being the ultimate determinant. As such, a team might use Kimi here, Qwen there, DeepSeek somewhere else and then reserve Opus or GPT for when the work actually needs it.&lt;/p&gt;

&lt;p&gt;Just because something is in a managed platform and has a model in a box, doesn't mean that changing the model is free. It can have a whole lot of cascading effects on prompts, and how a team prompts, on tool calls, and how the system programmatically calls tools, on typed streaming, and how DeltaChannel checkpointing behaves. Failure modes are introduced in entirely new parts of the system. And cost and latency have entirely different trade spaces. If a team is tweaking the harness or static code to improve an agent, the team wants to know how different tweaks of the harness or static code correlate with changes to the model.&lt;/p&gt;

&lt;p&gt;The question that recurs throughout this conference: what to put in a model, what to put in a harness, what to put in static code, and what to put in runtime?&lt;/p&gt;

&lt;p&gt;And so platforms like &lt;a href="https://www.langchain.com/blog/introducing-managed-deep-agents" rel="noopener noreferrer"&gt;Managed Deep Agents&lt;/a&gt;, &lt;a href="https://www.langchain.com/blog/introducing-context-hub" rel="noopener noreferrer"&gt;Context Hub&lt;/a&gt;, and &lt;a href="https://www.langchain.com/blog/langsmith-sandboxes-generally-available" rel="noopener noreferrer"&gt;Sandboxes&lt;/a&gt; all provide ways to manage such durable threads and other important runtime structure. Files and skills and subagents, and versioned context. Safe code execution and human approval flows. Tracing and checkpoints. And, of course, a memory that lives somewhere other than in the vibes of the person interacting with the system.&lt;/p&gt;

&lt;p&gt;MCP will connect agents to tools that are within an organization's own stack. This is different from A2A, where agents interact with other agents. Some of those will be user agents, and others will be digital employees that have their own permissions, budgets, policy boundaries, and audit trails. This will require different auth models than current approaches, and in many cases, existing agents are essentially useless, or worse, frightfully powerful in their current form.&lt;/p&gt;

&lt;p&gt;For &lt;a href="https://www.langchain.com/blog/introducing-llm-gateway" rel="noopener noreferrer"&gt;LLM Gateway&lt;/a&gt;: spend limits; PII redaction; tracking of policy events, whether spend limits are set, what they are, who updated them; trace continuity, so after a trace is sent to an external tool, the original trace can still be viewed together with the trace generated by the external tool in the same view; and eventually the same type of controls for external tools as for MCP, meaning tool gateway controls.&lt;/p&gt;

&lt;p&gt;My takeaway from Interrupt is that the agent conversation is getting more honest.&lt;/p&gt;

&lt;p&gt;Of course, this is the hard part: putting the LLM in the right place to bear judgment, and surrounding it with code that enables traceability, limits, eval, and improvement.&lt;/p&gt;

&lt;p&gt;That is what made Interrupt feel important.&lt;/p&gt;

&lt;p&gt;The ecosystem is moving in the direction of LLM-powered agents as runtime participants within actual software systems, instead of as magic employees.&lt;/p&gt;

&lt;p&gt;Good. That is where the work is.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>langchain</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agentic Payments Move Spending Authority Into the Runtime | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Thu, 28 May 2026 04:06:26 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agentic-payments-move-spending-authority-into-the-runtime-focused-labs-41i8</link>
      <guid>https://dev.to/focused_dot_io/agentic-payments-move-spending-authority-into-the-runtime-focused-labs-41i8</guid>
      <description>&lt;p&gt;Agentic payments are arriving before payment authority has an owner.&lt;/p&gt;

&lt;p&gt;At LangChain Interrupt there was a constant return to a payment question for agentic AI: what to do with AI agents that need to spend money. &lt;a href="https://x.com/privy_io/status/2057490730558587366" rel="noopener noreferrer"&gt;Privy said the payment question kept coming up&lt;/a&gt;. Harrison Chase &lt;a href="https://x.com/hwchase17/status/2057524656631083124" rel="noopener noreferrer"&gt;pointed at centralized least privilege, audit trails, and dynamic policies&lt;/a&gt; as the path that probably beats static allowlists.&lt;/p&gt;

&lt;p&gt;The wallet signs. The runtime decides.&lt;/p&gt;

&lt;p&gt;So let me just repeat that. The payment question that’s come up for agentic commerce, AI agents making payments, is delegated spend. And spending money, even as a new tool call, is not simply another tool call. It creates liabilities, dispute paths, budget pressure, user trust issues, procurement weirdness, and an audit trail the business needs to defend after the fact.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Spending Bug Has a Perfect UX
&lt;/h2&gt;

&lt;p&gt;In this integrated form, agents can research suppliers, compare offers, reserve resources, pay for APIs or other digital goods and services, issue refunds to customers, or book travel inside systems where humans already work. Thus, as previously noted, &lt;a href="https://focused.io/lab/2026-year-of-the-integrated-agent" rel="noopener noreferrer"&gt;the integrated agent&lt;/a&gt; is far more powerful than AI-powered chat.&lt;/p&gt;

&lt;p&gt;Money exposes the part of the architecture that hand-wavy autonomy hides.&lt;/p&gt;

&lt;p&gt;Note that as soon as the agent stops being able to execute commands in the integrated workflow and instead fills out a human controlled checkout page (e.g. for purchases), then the workflow stops being integrated and turns into purely manual work. And as for spending money on behalf of a user with direct wallet access granted to the agent, the worst part is that the UI will make it look like the money was intentionally spent by the user (with a cool progress bar, for example), until it is revealed weeks later by the finance department that a prompt was entered incorrectly and money was spent by the AI agent.&lt;/p&gt;

&lt;p&gt;Protocols are moving quickly. x402 &lt;a href="https://www.x402.org/" rel="noopener noreferrer"&gt;frames itself as an open payment standard for internet-native payments&lt;/a&gt;. Coinbase describes x402 as &lt;a href="https://docs.cdp.coinbase.com/x402/welcome" rel="noopener noreferrer"&gt;direct programmatic payments over HTTP&lt;/a&gt; for human developers and AI agents, with no account setup and no manual payment flow. Cloudflare’s Agents documentation shows the machine-to-machine flow: &lt;a href="https://developers.cloudflare.com/agents/agentic-payments/x402/" rel="noopener noreferrer"&gt;client requests a paid resource, receives a 402 Payment Required response, retries with a signed payment payload, and gets settlement confirmation&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Good. Interfaces for agents need to be &lt;a href="https://focused.io/lab/mcp-is-packaging-agent-operable-interfaces-are-the-product" rel="noopener noreferrer"&gt;agent-operable interfaces&lt;/a&gt;, including payment interfaces. That’s why human checkout pages are so bad for autonomous work.&lt;/p&gt;

&lt;p&gt;In sum, the hard work in enabling a resource to be paid for over the internet is left to the runtime (i.e. spending policy): what agent requested this spend, what was the purpose of the agent, what is the relevant budget, what merchants/services are in scope, who can retract a delegation of spend, who is the human to approve a spend, where will the settlement receipt of the spend of money be written.&lt;/p&gt;

&lt;h2&gt;
  
  
  Payment Intent Belongs in the Runtime
&lt;/h2&gt;

&lt;p&gt;The core object is payment intent.&lt;/p&gt;

&lt;p&gt;An agent shouldn’t be passing around payment authority, the agent should create a payment intent. The intent would include actor, task, merchant/service, amount, currency, purpose, budget, requested payment method, evidence gathered, and fallbacks for when the main method of payment fails. The runtime policy engine then determines the next steps for the payment intent based on its rules (approve the payment of metered API calls automatically, pay customer refunds to support leads, require approval from procurement for new vendors, reject transactions that were not for the intended task, etc). Those next steps could be yes, no, ask for human approval, or open a ticket.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fcylednsw2a35r4dsjajm.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fcylednsw2a35r4dsjajm.png" alt="Flow diagram showing an agent payment intent passing through a runtime policy engine before a scoped wallet signs and a settlement receipt is written to an audit ledger." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Wallet should be behind the runtime policy not inside the agent loop.&lt;/p&gt;

&lt;p&gt;This sounds boring because money likes boring.&lt;/p&gt;

&lt;p&gt;The runtime spending policy needs a few plain fields:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Amount and currency limits.&lt;/li&gt;
&lt;li&gt;Merchant or service scope.&lt;/li&gt;
&lt;li&gt;Delegated purpose.&lt;/li&gt;
&lt;li&gt;Budget window.&lt;/li&gt;
&lt;li&gt;Approval threshold.&lt;/li&gt;
&lt;li&gt;Wallet or signer scope.&lt;/li&gt;
&lt;li&gt;Revocation owner.&lt;/li&gt;
&lt;li&gt;Receipt destination.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This can be contrasted with the runtime spending policy that is required to be defined by the agent in Privy's x402 writeup here &lt;a href="https://privy.dev/blog/building-agentic-and-programmatic-payments-with-x402-and-privy" rel="noopener noreferrer"&gt;Privy's x402 writeup gets close to this shape&lt;/a&gt; for per-domain spend limits, agent-specific permissions, workflow-level approvals, and even for session signers for offline user workflows.&lt;/p&gt;

&lt;h2&gt;
  
  
  Wallet Ownership Changes the Failure Mode
&lt;/h2&gt;

&lt;p&gt;Wallet architecture still matters. It just answers a much narrower question.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://docs.privy.io/recipes/agent-integrations/agentic-wallets" rel="noopener noreferrer"&gt;Privy's agentic wallet docs describe two control models&lt;/a&gt;: developer-owned wallets controlled by backend authorization keys, and user-owned wallets that grant an agent signer scoped policies while the user keeps ultimate control and revocation.&lt;/p&gt;

&lt;p&gt;A developer-owned wallet for a backend agent paying for infrastructure, such as data enrichment, paid APIs, crawl credits, model calls, or transaction fees. The company owns the budget, the runtime owns the policy, and operational control of the revocation is sufficient (i.e. someone on the team can log into the management interface and cancel an agent).&lt;/p&gt;

&lt;p&gt;User-owned wallets with agent signers also fit into the delegated action model. In these cases, users are delegating others to perform action(s) on their behalf. In these cases, users fund their own workflows, and the agent or signer is granted bounded authority to complete tasks on their behalf. (In these cases, the user should always have the ability to revoke the agent or signer).&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fm20zbexp8vay7q1ahjnp.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fm20zbexp8vay7q1ahjnp.png" alt="Comparison matrix contrasting a developer-owned agent wallet with a user-owned wallet that grants an agent signer scoped policy and revocation." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The control model decides who owns funds, who can revoke access, and where policy gets enforced.&lt;/p&gt;

&lt;p&gt;Both models need runtime policy. A developer-owned wallet with no spend controls turns into a company credit card taped to an agent’s back. A user-owned wallet with no scoped delegation turns into a consent problem just waiting to turn into a customer dispute.&lt;/p&gt;

&lt;h2&gt;
  
  
  Approval UI Is Runtime Infrastructure
&lt;/h2&gt;

&lt;p&gt;Approval is a runtime state transition. The modal is just where a human sees it.&lt;/p&gt;

&lt;p&gt;That is why &lt;a href="https://focused.io/lab/agent-ui-is-runtime-infrastructure" rel="noopener noreferrer"&gt;agent UI belongs in runtime infrastructure&lt;/a&gt;. So when a user approves a spending action, they are approving a proposed transaction with a matched policy. The evidence the agent used, the budget impact, and the scope of authority being granted should all be visible to the user approving the spending. The user should be approving a bounded payment intent, not a vague agent plan.&lt;/p&gt;

&lt;p&gt;That is the part that everyone tries to treat like an SDK integration and therefore payments “work”.&lt;/p&gt;

&lt;h2&gt;
  
  
  Receipts Beat Trust
&lt;/h2&gt;

&lt;p&gt;A payment-capable agent needs a way to have those payments recorded as receipts as first-class data within the agent’s runtime.&lt;/p&gt;

&lt;p&gt;When making payments, the payment response should be written back as evidence to the same stream as the rest of the work done by the agent. Cloudflare’s x402 flow ends with &lt;a href="https://developers.cloudflare.com/agents/agentic-payments/x402/" rel="noopener noreferrer"&gt;a PAYMENT-RESPONSE header that contains settlement confirmation&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;That was also true for tool calls: &lt;a href="https://focused.io/lab/agent-traces-need-to-cross-the-mcp-boundary" rel="noopener noreferrer"&gt;agent traces need to cross the boundary&lt;/a&gt; of work, the side effect of which is that the trace becomes much more valuable. In the case of payments, the side effect is value transfer (i.e. money moving out of or into an account). Therefore, for all but the cheapest of actions, traces of agent work must include payment receipts.&lt;/p&gt;

&lt;p&gt;The ledger doesn’t have to be pretty or shiny. It has to answer the boring set of questions of work done quickly.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;What did the agent intend to buy?&lt;/li&gt;
&lt;li&gt;Which policy allowed it?&lt;/li&gt;
&lt;li&gt;Which signer executed it?&lt;/li&gt;
&lt;li&gt;Which rail settled it?&lt;/li&gt;
&lt;li&gt;Which human approved it, if approval was required.&lt;/li&gt;
&lt;li&gt;Which task, ticket, customer, or account owns the receipt?&lt;/li&gt;
&lt;/ul&gt;

&lt;h2&gt;
  
  
  The Card Networks See the Same Boundary
&lt;/h2&gt;

&lt;p&gt;We should pay attention to how existing payment networks already frame the problem. For example, while &lt;a href="https://corporate.visa.com/en/products/intelligent-commerce.html" rel="noopener noreferrer"&gt;Visa Intelligent Commerce&lt;/a&gt;, enabled by crypto, frames agentic checkout around approved AI “agents” for consumers to manage their card(s) online, for merchants, it frames around similar but additional factors such as fraud/dispute protections, merchant acceptance, and especially “trust in transaction” for each payment context (visa online, in app, etc.), all already handled for them by existing payments networks. PayPal also recently announced integration of Mastercard’s Agent Pay into PayPal wallets &lt;a href="https://newsroom.paypal-corp.com/2025-10-27-Mastercard-and-PayPal-Join-Forces-To-Accelerate-Secure-Global-Agentic-Commerce" rel="noopener noreferrer"&gt;Mastercard Agent Pay will integrate with PayPal's wallet&lt;/a&gt; to enable merchants to accept payments from AI agents acting on behalf of users that have added their payment methods to the wallet.&lt;/p&gt;

&lt;p&gt;The runtime layer has to own the authority model before this becomes the normal pattern.&lt;/p&gt;

&lt;h2&gt;
  
  
  Build the Spending Policy First
&lt;/h2&gt;

&lt;p&gt;Define the payment intent schema. Include purpose, merchant scope, amount, budget, evidence required, approval required, signer scope and receipt destination. Treat as an object from day one. Use for backend logic as well as for generating form fields for human fill-in-the-blanks approval actions.&lt;/p&gt;

&lt;p&gt;A path for runtime control of payments above and beyond enterprise wallet offerings is to first implement a policy engine, write policies as simple rules which Finance and Security can understand, and test against various scenarios. Service allowlists are only a first input, but purpose, budget window, task owner, customer account, and approval state all impact payments.&lt;/p&gt;

&lt;p&gt;Make approval a runtime event: The approval should pause the payment intent, show the policy match, capture a bounded decision, and then resume or reject the workflow. In other words, do not make “approve agent action” a button.&lt;/p&gt;

&lt;p&gt;Test out denial paths. If all a payment system can test for is successful settlement, the team is asking for a weird Friday afternoon. Denied payment, expired approval, revoked signer, duplicate retry, failed settlement, disputed transaction, and exhausted budget all need first-class paths.&lt;/p&gt;

&lt;p&gt;Agentic payments are going to make agents feel useful since they are able to buy data, pay for API calls, issue credits, book services… for companies within specified policy. That is real work.&lt;/p&gt;

&lt;p&gt;The agent runtime becomes a spending control plane.&lt;/p&gt;

&lt;p&gt;Companies will get agentic payments right by starting from a different vantage point than existing payment ‘solutions’ and beginning with a plain set of questions for every transaction: who is delegating the spend; what policy will be enforced on that spend; where is the approval for the spend delegated; and what receipt will prove that the transaction was for the business.&lt;/p&gt;

&lt;p&gt;Then the wallet can sign.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>langchain</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agent UI Is Runtime Infrastructure | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Thu, 28 May 2026 04:05:53 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agent-ui-is-runtime-infrastructure-focused-labs-59jo</link>
      <guid>https://dev.to/focused_dot_io/agent-ui-is-runtime-infrastructure-focused-labs-59jo</guid>
      <description>&lt;p&gt;Agent product spinners tell the truth badly.&lt;/p&gt;

&lt;p&gt;There’s this common pattern in agent UX: a person clicks a button and after a few moments a spinner shows up in the center of the page and the product locks up. The user has no idea what tool is running, what changes are happening in the system, what subagents or agents are involved. Later on the team can go back and read through a long transcript to figure out what happened. It’s better than nothing, but ultimately useless for a human doing real work with real deadlines.&lt;/p&gt;

&lt;p&gt;Token streaming solves the model-call UX problem and makes the answer feel more alive as the model writes out the answer. But agent products have a wider problem: the work of an agent to produce output happens across tools, subagents, checkpoints in a workflow, patches of state, approval gates, background jobs, reconnectable sessions, and different applications that a person is staring at to see the results of the agent’s work.&lt;/p&gt;

&lt;p&gt;This problem has been named by LangChain in its post &lt;a href="https://www.langchain.com/blog/token-streams-to-agent-streams" rel="noopener noreferrer"&gt;"From Token Streams to Agent Streams"&lt;/a&gt;. Generative UI cannot be a pretty wrapper around a transcript. The UI/runtime boundary needs a contract.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qvi98fim2dwcrexu9w6.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F9qvi98fim2dwcrexu9w6.png" alt="Side-by-side diagram comparing flat token streaming with a typed agent event stream feeding multiple UI projections." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The stream stopped being a text pipe. It became the UI contract.&lt;/p&gt;

&lt;h2&gt;
  
  
  A transcript can render text. An agent product has to render work.
&lt;/h2&gt;

&lt;p&gt;Old chat UI worked because a user posted a message and waited for assistant text. During generation, tokens appended to the current thread until the assistant finished.&lt;/p&gt;

&lt;p&gt;The easy chat app shape gets destroyed as soon as work gets added to the agent.&lt;/p&gt;

&lt;p&gt;A support agent looks up account info, checks SSO configuration, opens a ticket, asks for approval to change a plan, adds a note to Salesforce, and waits for billing API to return info. Agent text output during that time is a small fraction of the work done by product to service that request. What matters is the entire path through product taken by that request: billing call, approval card, changed account info, ticket ID, and then finally the response to the agent’s question. A spinner with a blank text input and a dribble of tokens is poor UI for that experience.&lt;/p&gt;

&lt;p&gt;This problem is already apparent in latency-prone chat agents, which are implemented as single-threaded bots that process requests one at a time. Even if the final response is correct, &lt;a href="https://focused.io/lab/your-customer-service-bot-is-slow-because-its-single-threaded" rel="noopener noreferrer"&gt;single-threaded support bots&lt;/a&gt; are an architecture smell, and event streams are just the UI version of the same problem: the frontend needs to see the product surface evolve in real time as the agent processes events in parallel, not after the fact as a single log entry.&lt;/p&gt;

&lt;p&gt;This becomes clearer reading LangChain’s event streaming docs, as they outline this API boundary for new application and frontend work. &lt;a href="https://docs.langchain.com/oss/python/langchain/event-streaming" rel="noopener noreferrer"&gt;LangChain recommends &lt;code&gt;stream_events(..., version="v3")&lt;/code&gt;&lt;/a&gt;, which returns typed projections for messages, tool calls, state values, subgraphs, custom projections, and final output. The application then renders the projection it has been given to display to the user, instead of parsing through the individual chunks of the run and branching based on different text blocks.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;
&lt;span class="n"&gt;stream&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;agent&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;stream_events&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="p"&gt;{&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;messages&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="p"&gt;[{&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;role&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;user&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;content&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;Check the renewal risk for Acme&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;}]},&lt;/span&gt;
    &lt;span class="n"&gt;version&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;v3&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;item&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;stream&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;interleave&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;messages&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;tool_calls&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;values&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="k"&gt;if&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;messages&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="nf"&gt;render_assistant_text&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="nf"&gt;str&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="p"&gt;))&lt;/span&gt;
    &lt;span class="k"&gt;elif&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;tool_calls&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="nf"&gt;render_tool_card&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;tool_name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nb"&gt;input&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;output&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;error&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="k"&gt;elif&lt;/span&gt; &lt;span class="n"&gt;name&lt;/span&gt; &lt;span class="o"&gt;==&lt;/span&gt; &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;values&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
        &lt;span class="nf"&gt;update_state_panel&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;item&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;final_state&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;stream&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="n"&gt;output&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;This lets the front end promise something different than text streaming to a transcript. The transcript can be updated with text in real time. Tool calls can be surfaced as cards with progress and failure states. The latest state of the application can be rendered in real time. Errors can be surfaced with controls to retry. Final output can close the loop.&lt;/p&gt;

&lt;p&gt;The code shape matters because instead of a frontend parsing logs, it subscribes to product nouns.&lt;/p&gt;

&lt;h2&gt;
  
  
  The event stream needs nouns.
&lt;/h2&gt;

&lt;p&gt;A useful agent stream would contain information about the lifecycle of the agent, text messages, tool calls, state, activity, reasoning behind decisions, custom events, and errors. AG-UI, the Agent-User Interaction Protocol, is the cleanest current example of this vocabulary. Its docs describe &lt;a href="https://docs.ag-ui.com/concepts/events" rel="noopener noreferrer"&gt;event-based architecture where events are the fundamental communication units between agents and frontends&lt;/a&gt;, with lifecycle events, text message events, tool call events, state management events, activity events, reasoning events, special events, and draft extensions that are still under construction.&lt;/p&gt;

&lt;p&gt;Again, the lifecycle portion of the events is more important than it may initially seem. A run can start. Steps start and end. Text chunks attach to a message ID. Tool calls start, finish, error, or disappear. State lands as deltas against the user-facing model of the world. A run can end, interrupt, or fail. The UI can behave like software instead of a chat window watching smoke signals.&lt;/p&gt;

&lt;p&gt;AG-UI did not show up by accident. CopilotKit introduced it as a protocol for streaming &lt;a href="https://www.copilotkit.ai/blog/introducing-ag-ui-the-protocol-where-agents-meet-users" rel="noopener noreferrer"&gt;a single JSON event sequence over standard HTTP or an optional binary channel&lt;/a&gt;, carrying messages, tool calls, state patches, and lifecycle events generated during an agent run. The protocol is also supported by &lt;a href="https://learn.microsoft.com/en-us/agent-framework/integrations/ag-ui/" rel="noopener noreferrer"&gt;Microsoft’s Agent Framework&lt;/a&gt; for remote agent hosting. The framework supports real-time streaming over SSE, session and state management, human-in-the-loop approvals, shared state, predictive state updates and tool-based generative UI.&lt;/p&gt;

&lt;p&gt;There is also an enterprise adoption signal here. Agent frameworks are being judged by the event contract that their authors expose to application developers, not by the React widgets they use to build a demo application.&lt;/p&gt;

&lt;h2&gt;
  
  
  Generative UI makes the frontend part of the runtime boundary.
&lt;/h2&gt;

&lt;p&gt;The term “generative UI” is abused because people believe that the model is painting components in front of them. But the useful part is the boring part. How does work happen in the frontend vs. the backend? How does approval work? How does writing state work? And what can be retried here?&lt;/p&gt;

&lt;p&gt;AG-UI’s tool model gives the frontend a way to define client-side tools and let the agent request them through a structured lifecycle. The &lt;a href="https://docs.ag-ui.com/concepts/tools" rel="noopener noreferrer"&gt;AG-UI tool docs&lt;/a&gt; describe tool schemas, tool calls, and frontend-defined tools that let the application keep sensitive operations under product control while the agent reasons over the interaction.&lt;/p&gt;

&lt;p&gt;That boundary is significant. The calendar component exposing “propose meeting times” doesn’t grant the agent write access to the calendar. The billing page for plans exposing “prepare plan change” requires a human approval event before commit. The data table with rows and columns for accounts in a given timeframe can expose “filter this segment” as a UI operation, as opposed to a backend mutation that changes the underlying data, and have the agent ask for it and the product decide to allow it and have the resulting events recorded in the stream of events.&lt;/p&gt;

&lt;p&gt;Once the run context is known, the screen can reflect state, permissions, intermediate artifacts, and interaction history. This is where &lt;a href="https://focused.io/lab/context-will-replace-your-design" rel="noopener noreferrer"&gt;context starts replacing static design&lt;/a&gt;. The UI cannot be drawn once and left alone. It has to change in response to each step of the run and the events generated by those steps.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F8o0l5cj89h9nkhb7v7zy.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F8o0l5cj89h9nkhb7v7zy.png" alt="Layer diagram showing an agent runtime connected to tools and user-facing application components through a typed event stream." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Protocols matter because the UI is now part of the runtime boundary.&lt;/p&gt;

&lt;h2&gt;
  
  
  Subagents make transcript thinking collapse.
&lt;/h2&gt;

&lt;p&gt;The transcript model gets messier with subagents in the product.&lt;/p&gt;

&lt;p&gt;A supervisor might define a task to research a problem, look up a policy, analyze an account, and then plan a series of remediations. The tradeoffs for &lt;a href="https://focused.io/lab/multi-agent-orchestration-in-langgraph-supervisor-vs-swarm-tradeoffs-and-architecture" rel="noopener noreferrer"&gt;multi-agent orchestration with LangGraph&lt;/a&gt; were laid out in a recent architecture piece. The problem for the UI of such a task is similar to that of a chat transcript. When work is delegated to subagents, the work can be flattened into a single transcript, but this flattening obscures important information about the hierarchy of tasks, which are currently blocked, which have completed, and what results were generated by which child run.&lt;/p&gt;

&lt;p&gt;Deep Agents can handle the UI problem that arises when work is split off to subagents by treating the stream of each subagent as a separate first-class projection. The docs say &lt;a href="https://docs.langchain.com/oss/python/deepagents/event-streaming" rel="noopener noreferrer"&gt;&lt;code&gt;stream.subagents&lt;/code&gt; exposes one stream handle per delegated task&lt;/a&gt;, with scoped messages, tool calls, values, nested subagents, output, path, and lifecycle status. This means a UI could show the effect of the supervising agent’s work, then show off the work that the various child agents did as separate cards, and then drill down into any subagent’s stream without subscribing to the stream of every other subagent as well.&lt;/p&gt;

&lt;h2&gt;
  
  
  Reconnects and traces belong in the same design conversation.
&lt;/h2&gt;

&lt;p&gt;Agent runs continue after a browser tab has been closed, run into problems with flaky API connections, have a human manually intervene at a particular point, and continue after a product update has been deployed. They can fail partially in the course of completing a write. So too the stream of UI events corresponding to a given agent run must also be resumable, corresponding to the fact that runs are themselves resumable.&lt;/p&gt;

&lt;p&gt;This is where the event contract turns into production infrastructure. To follow runtime work, the contract has to map run IDs, thread IDs, parent run IDs, and step names. Ordered value deltas, tool calls, outputs, and results have to be tracked so the frontend does not duplicate side effects. When the UI generates a customer-visible action, it should trace back to the run, using the same identifiers that appeared in the tool card showing the “billing API failed” error.&lt;/p&gt;

&lt;p&gt;Honeycomb’s agent work points in the same direction. Its &lt;a href="https://www.honeycomb.io/blog/agent-timeline-flight-recorder-for-your-ai-agents" rel="noopener noreferrer"&gt;Agent Timeline product frames agent debugging as a flight recorder&lt;/a&gt;. The same information used to present active work in the UI can be displayed in a review of an incident that involved that agent. If the UI showed a step title and the “billing API failed” tool card, these same run, step and tool identifiers are necessary in the trace for the subsequent steps to accurately present the work done by the agent.&lt;/p&gt;

&lt;p&gt;Integrated agents raise the bar here. In &lt;a href="https://focused.io/lab/2026-year-of-the-integrated-agent" rel="noopener noreferrer"&gt;the integrated-agent piece&lt;/a&gt;, the point was that agents deliver value when they operate within existing enterprise systems and workflows. Processing work through a UI is not enough. The tool’s event stream has to integrate with the product, the platform, and the observability system. They need the same event contract.&lt;/p&gt;

&lt;h2&gt;
  
  
  What to demand from an AI agent framework.
&lt;/h2&gt;

&lt;p&gt;The buying checklist is getting sharper.&lt;/p&gt;

&lt;p&gt;Can the framework stream messages, tool calls, state patches, subagent progress, approvals, errors, custom domain events, and final output as typed projections?&lt;/p&gt;

&lt;p&gt;Can a product subscribe to a subagent, tool call, or state channel without draining the entire run, then reconnect later with the correct run IDs, state, and pending interrupts?&lt;/p&gt;

&lt;p&gt;Can frontend tools stay under application control while the agent requests them through a documented schema?&lt;/p&gt;

&lt;p&gt;Can event identifiers map cleanly into traces, logs, eval records, and incident tickets?&lt;/p&gt;

&lt;p&gt;Does the frontend UI produce useful UI for product work even for partial completion of work by an AI agent?&lt;/p&gt;

&lt;p&gt;A token stream makes things look active. An agent event stream gives a product handles.&lt;/p&gt;

&lt;p&gt;Generative UI needs these handles: lifecycle events for run boundaries, tool events for actions performed through tools, state events for shared context, subagent events for delegated work, approval events for control, error events for recovery, and observability hooks for the receipts.&lt;/p&gt;

&lt;p&gt;A chatbox is okay. People know how to use a chatbox. But a chatbox cannot be the UI for an agent-based product.&lt;/p&gt;

&lt;p&gt;Make the stream a contract. Then build the UI on purpose.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agent Monitoring Is an Infrastructure Workload | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Thu, 28 May 2026 04:05:50 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agent-monitoring-is-an-infrastructure-workload-focused-labs-4lda</link>
      <guid>https://dev.to/focused_dot_io/agent-monitoring-is-an-infrastructure-workload-focused-labs-4lda</guid>
      <description>&lt;p&gt;I added agent monitoring to the list of reporting work that has crossed over into SRE production infrastructure, which is annoying but real enough. The trace used to explain a single request. Now it has to carry the agent run through tool calls, subagents, sandboxes, services, approvals, retries, and side effects. It has to support SREs reading the trace a week or so after it happened, when no one remembers the details. The trace must support rollback and the other production troubleshooting work SREs do. And it must be understandable by an SRE who has not already read through the full raw event log for the agent run.&lt;/p&gt;

&lt;p&gt;First off, Sarah Cat made the core point that &lt;a href="https://x.com/sarahcat21/status/2057866945408721206" rel="noopener noreferrer"&gt;managing and monitoring agents requires rethinking infrastructure because existing systems were not designed for agent scale&lt;/a&gt;. Then Harrison Chase added that the same point applies on the monitoring side. Charity Majors made the observability version sharper: there is a huge problem tracking long-running async AI sessions with the &lt;a href="https://x.com/mipsytipsy/status/2054099969427312933" rel="noopener noreferrer"&gt;usual transaction and trace building blocks&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Observability for long-running agent sessions is turning into the storage, identity, retention, correlation and control-plane for the behavior of AI agents.&lt;/p&gt;

&lt;p&gt;Fine. Call it monitoring if the label helps. Just don’t staff it like reporting.&lt;/p&gt;

&lt;h2&gt;
  
  
  The trace is carrying a bigger object
&lt;/h2&gt;

&lt;p&gt;A web request goes in through a handler, calls a database (maybe a queue), and then returns a response to the person who made the request. This is the shape of a transaction and this is what people have built their observability tools around. This is the world of spans, of logs, of metrics, of viewing individual exemplars, of looking at a service map, of building a dashboard.&lt;/p&gt;

&lt;p&gt;LangChain’s observability docs say agents require visibility into &lt;a href="https://docs.langchain.com/oss/python/langchain/observability" rel="noopener noreferrer"&gt;tools, prompts, decisions, tool calls, model interactions, and decision points&lt;/a&gt;. LangSmith’s dashboard docs turn that surface into operating metrics: &lt;a href="https://docs.langchain.com/langsmith/dashboards" rel="noopener noreferrer"&gt;trace count, latency, error rates, token usage, cost, tool run counts, tool errors, tool latency, run types, and feedback scores&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;Read that list slowly. The list describes the beginning of an agent control plane.&lt;/p&gt;

&lt;p&gt;I like traces. I like dashboards. I do not like pretending raw logs are the record.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fm9p66dsms3pt1cjxj4nv.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fm9p66dsms3pt1cjxj4nv.png" alt="Data-flow diagram showing an agent run emitting telemetry from model calls, tools, subagents, sandboxes, downstream services, and human approvals into monitoring and SRE loops." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The trace has to follow both the decision and the side effect.&lt;/p&gt;

&lt;p&gt;For a single agent run, the logs from that run are fine to read as logs. However, for monitoring a production system where logs become evidence for SREs or security investigators later, the trace following the commands in the log also has to follow decisions and side effects across the boundaries the agent crosses: tool boundaries, MCP boundaries, sandbox boundaries, and other runtime boundaries. Again, &lt;a href="https://focused.io/lab/agent-traces-need-to-cross-the-mcp-boundary" rel="noopener noreferrer"&gt;Agent Traces Need to Cross the MCP Boundary&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Long-running sessions break request-shaped thinking
&lt;/h2&gt;

&lt;p&gt;A transaction trace is too small for a long-running agent session.&lt;/p&gt;

&lt;p&gt;Honeycomb is running its 2026 Innovation Week around &lt;a href="https://www.honeycomb.io/go/innovation-week-2026" rel="noopener noreferrer"&gt;understanding, debugging, and improving AI systems in production&lt;/a&gt;. Its agent observability launch focuses on tracing agent activity, reconstructing decision paths, and debugging failures &lt;a href="https://siliconangle.com/2026/05/12/honeycomb-introduces-agent-observability-features-keep-eye-production/" rel="noopener noreferrer"&gt;without manual log dives&lt;/a&gt;. The manual log diving is where immature agent systems die.&lt;/p&gt;

&lt;p&gt;Without a session id across the systems, incident review degenerates into archaeology with search bars. Someone opens LangSmith to trace the model calls. Someone opens Honeycomb to trace the service operations. Someone checks the workflow queues. Someone reads application logs. Someone asks whether the sandbox still exists. Someone searches Slack for approvals. Then the team starts piecing together guesses.&lt;/p&gt;

&lt;p&gt;That is archaeology with search bars.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3che0co9p9z1w2mygy9z.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3che0co9p9z1w2mygy9z.png" alt="Timeline showing a short request trace losing context while a long-running agent session continues through retries, subagents, human interrupts, checkpoint, rollback, cost, evaluation, and final action." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;A transaction trace is too small for a long-running agent session.&lt;/p&gt;

&lt;p&gt;Stateful agents raise the pressure again. The DeltaBox paper frames AI agents as systems that perform high-frequency state exploration, relying on checkpoint and rollback of complete sandbox state, including files and process state. With change-based sandbox state, the paper reports &lt;a href="https://arxiv.org/abs/2605.22781" rel="noopener noreferrer"&gt;14 ms checkpoint and 5 ms rollback&lt;/a&gt;. Prior approaches copy the full state to roll back, adding hundreds of milliseconds to seconds of latency during evaluation. The resulting system enables high-frequency state exploration, and supports a wide range of applications.&lt;/p&gt;

&lt;p&gt;This also shows on the UI side. In &lt;a href="https://focused.io/lab/agent-ui-is-runtime-infrastructure" rel="noopener noreferrer"&gt;Agent UI Is Runtime Infrastructure&lt;/a&gt; we noted that the agent event stream contains state that a user can act on. Monitoring has to share those identifiers. The backend trace and user-visible event belong to the same run.&lt;/p&gt;

&lt;h2&gt;
  
  
  AI SRE starts before the incident prompt
&lt;/h2&gt;

&lt;p&gt;The term “AI SRE” is likely to be abused in 2026, but the useful meaning is mundane: an AI agent helps run software, and that software provides enough structure so the agent does not blow the incident budget interpreting things.&lt;/p&gt;

&lt;p&gt;The Causely paper presents hard numbers around AI in SRE. In their paper, the authors describe how workflows using AI derive the environment state from raw telemetry, paying for it in tokens, latency, and interpretation errors. In a 24-microservice OpenTelemetry demo application with injected faults, causal grounding reduced mean time to diagnosis by &lt;a href="https://arxiv.org/abs/2605.18327" rel="noopener noreferrer"&gt;63 percent, token consumption by 60 percent, tool calls by 78 percent, and improved root-cause accuracy from 75 percent to 100 percent&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;AI SRE is going to get abused, but the useful frame is simple: an agent helps operate software, and the software gives that agent enough structure to avoid burning the incident budget on interpretation.&lt;/p&gt;

&lt;p&gt;Monitoring an agent means building production monitoring for the service that runs the agent. That work is data modeling, retention, identity propagation, correlation, storage, schema, and permissions. Boring work. That is why no one wants to do it. That is also why it matters, as long as the work stays boring and does not turn into AI SRE snake oil.&lt;/p&gt;

&lt;p&gt;It also has to close the loop from signal to issue. The signal should open a ticket and attach evidence to that ticket, and then continue to update the evaluator or release gate based on what the human does with that work. We wrote about how agent failures should open tickets in &lt;a href="https://focused.io/lab/agent-failures-should-open-tickets" rel="noopener noreferrer"&gt;Agent Failures Should Open Tickets&lt;/a&gt;.&lt;/p&gt;

&lt;h2&gt;
  
  
  Ownership belongs below the dashboard
&lt;/h2&gt;

&lt;p&gt;Agent monitoring fails when ownership only exists inside the dashboard.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://arxiv.org/abs/2605.16035" rel="noopener noreferrer"&gt;Who Owns This Agent?&lt;/a&gt; observes an attribution gap in which the agent’s behavior is visible to affected parties, but the responsible operator or account is not identifiable. The enterprise version is obvious enough. A finance agent updates a customer record. A security agent modifies a ticket. A coding agent opens a pull request. A support agent sends an email. In each case, the record should say: system, account, policy, and operator.&lt;/p&gt;

&lt;p&gt;The answer cannot be "check the logs." Come on.&lt;/p&gt;

&lt;p&gt;Agent attribution forms part of monitoring, along with the permission state, session identity, and the rollback context of the deployment. The user-visible event and the backend action that caused it need a shared record. Supervisor and swarm systems spread decisions across agents with different responsibilities, which is why &lt;a href="https://focused.io/lab/multi-agent-orchestration-in-langgraph-supervisor-vs-swarm-tradeoffs-and-architecture" rel="noopener noreferrer"&gt;multi-agent orchestration has to be an architecture choice, not a vibe&lt;/a&gt;.&lt;/p&gt;

&lt;p&gt;A production record has to survive outside the dashboard. I want a ledger that can answer boring questions without detective work: which run, which owner, which permission, which tool, which checkpoint, which evaluator, which side effect. The dashboard can stay a view. The record has to be the substrate.&lt;/p&gt;

&lt;h2&gt;
  
  
  Build the monitoring substrate before the agent fleet arrives
&lt;/h2&gt;

&lt;p&gt;Monitoring an AI agent is a platform capability, with its own ownership, budget, and failure modes. Treating it that way eventually makes vendor comparisons useful. The steering deck can wait.&lt;/p&gt;

&lt;p&gt;For incident tracking and monitoring to work, the evidence needs structure. As we argued in &lt;a href="https://focused.io/lab/agent-failures-should-open-tickets" rel="noopener noreferrer"&gt;Agent Failures Should Open Tickets&lt;/a&gt;, the entire prompt may not be safe to store, and raw logs are not enough. Store the fields that make incident response possible: tool called, rejected alternatives, human policy decision, permissions, session cost, retry reason, checkpoint pointer, evaluator result, and final side effect. Govern the sensitive information. Keep the operational information queryable.&lt;/p&gt;

&lt;p&gt;Connecting monitoring to repair work matters too. Failed evaluators should create issues. Cost anomalies should page the owner or throttle the workflow. Repetitive tool errors should open a repair loop. A rollback must attach the checkpoint, diff, and human decision path. A human approval to modify customer data should attach to the trace, not to a screenshot in Slack.&lt;/p&gt;

&lt;p&gt;This is the unglamorous part of the AI agent infrastructure. But it is also where production agents become manageable. The agent can be clever. The runtime cannot be casual.&lt;/p&gt;

&lt;p&gt;Monitoring an AI agent is an infrastructure workload. The agent is a running system with memory, side effects, cost, ownership, state, and judgment loops. A dashboard may report the smoke. The monitoring substrate has to explain the fire.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agent Failures Should Open Tickets | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Thu, 21 May 2026 09:29:57 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agent-failures-should-open-tickets-focused-labs-2ni0</link>
      <guid>https://dev.to/focused_dot_io/agent-failures-should-open-tickets-focused-labs-2ni0</guid>
      <description>&lt;p&gt;Agent traces should create work.&lt;/p&gt;

&lt;p&gt;An AI agent workflow can fail twice. So, if it does fail twice, it should create a ticket with an owner and linked evidence and have that be something that the team can check for regression down the line. Instead, tracing an AI’s processes and reviewing its outputs can be pretty and searchable but still be essentially worthless as something that can be used for anything other than replaying the series of mistakes over and over. It’s what I’ve begun to call “replayable regret,” expensive, and painful to behold.&lt;/p&gt;

&lt;p&gt;LangChain this week identified a critical gap in tooling: traces of AI agent work can be traced and reviewed, but the error identification and corresponding merged fix are still &lt;a href="https://x.com/LangChain/status/2056743982542020992" rel="noopener noreferrer"&gt;manual and slow&lt;/a&gt;. Harrison Chase called this out this week too and noted that LangChain is building out an &lt;a href="https://x.com/hwchase17/status/2056804025904013653" rel="noopener noreferrer"&gt;“issue bench”&lt;/a&gt;, already using it internally, but still early for this class of tooling.&lt;/p&gt;

&lt;p&gt;That phrase matters because the unit of work changes. The trace stops being the artifact everyone stares at after the failure. The recurring failure becomes the artifact the team improves against.&lt;/p&gt;

&lt;h2&gt;
  
  
  Traces should not die in Slack
&lt;/h2&gt;

&lt;p&gt;The common failure loop is quite dumb.&lt;/p&gt;

&lt;p&gt;Step 1 for handling the common failure loop: an agent fails in a workflow, someone opens up the trace from that work item, and the team can see the failure in the trace steps. The tool call timed out. The planner picked a weird branch. Retrieval pulled stale context. The evaluator fired. A user left negative feedback. All of that fails when a trace link is added to Slack with the word “interesting” on top of it. In a word, that’s vibes, not work.&lt;/p&gt;

&lt;p&gt;Traces are good! I recently wrote about why traces from agent workflows should cross &lt;a href="https://focused.io/lab/agent-traces-need-to-cross-the-mcp-boundary" rel="noopener noreferrer"&gt;the MCP boundary&lt;/a&gt;. And making traces visible is the first half of work here. Traces are good because their visibility says this happened. But that trace, or set of traces, must also say this failure family is owned, fixed, covered, and blocked from coming back.&lt;/p&gt;

&lt;p&gt;That second half is the AI agent workflow people keep skipping.&lt;/p&gt;

&lt;p&gt;In the recent Engine thread, the team at LangChain identified the right inputs into the AI agent workflow: &lt;a href="https://x.com/LangChain/status/2056743984483926211" rel="noopener noreferrer"&gt;tool call failures and timeouts, online eval failures, trace anomalies, negative feedback, and unusual behavior&lt;/a&gt;. Today those inputs are treated as interesting patterns to watch as dashboard widgets. Instead, they should be treated as signals for a queue of work, where each is eligible to become a named issue with severity, linked traces, suspected boundary, and release condition.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwb820bt5102utr4m72r5.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fwb820bt5102utr4m72r5.png" alt="Closed issue-loop flow showing trace anomalies becoming clustered issues, fixes, evaluators, release gates, and reopened regressions." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The trace is evidence. The issue loop turns it into engineering work.&lt;/p&gt;

&lt;p&gt;The good version is pretty straightforward and mechanical: a trace anomaly turns into an issue, new traces get clustered with it, and it gets an owner. Said owner then makes a change which in turn adds a new evaluator or updates an existing one. The change is then released through a particular release gate, which in turn runs that new evaluator. And if it introduces any regressions, said issue reopens.&lt;/p&gt;

&lt;p&gt;No ceremony. Just a loop.&lt;/p&gt;

&lt;h2&gt;
  
  
  The ticket needs a shape
&lt;/h2&gt;

&lt;p&gt;An agent issue is not a Jira card with “LLM flaky” in the title. That card should be illegal (morally, at least). The issue needs the same hard edges as a production defect.&lt;/p&gt;

&lt;p&gt;An agent issue has to have the same characteristics of a production defect issue:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Failure name: “refund flow calls payment API before policy check”&lt;/li&gt;
&lt;li&gt;Workflow: refund, plan upgrade, incident triage, research synthesis&lt;/li&gt;
&lt;li&gt;Severity: customer impact, data risk, financial risk, operational drag&lt;/li&gt;
&lt;li&gt;Evidence: linked traces, failed eval runs, user feedback, tool responses&lt;/li&gt;
&lt;li&gt;Boundary: prompt, tool contract, context source, model route, permission, downstream API&lt;/li&gt;
&lt;li&gt;Owner: team or service owner, not “AI”&lt;/li&gt;
&lt;li&gt;Fix status: proposed, merged, reverted, blocked&lt;/li&gt;
&lt;li&gt;Regression coverage: benchmark eval, coverage eval, release gate&lt;/li&gt;
&lt;li&gt;Reopen rule: the exact signal that opens it up again and puts it back in the queue&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Agent failures are hard to test because they manifest differently based on the input, the branch under test, and the tools the agent touched before it failed. Without an issue name, every failure trace becomes a new issue to debug rather than another data point in the failure family that production tests are supposed to remove.&lt;/p&gt;

&lt;p&gt;If LangSmith Engine emits &lt;a href="https://docs.langchain.com/langsmith/engine-webhooks" rel="noopener noreferrer"&gt;&lt;code&gt;issue.created&lt;/code&gt; and &lt;code&gt;issue.trace.added&lt;/code&gt; events&lt;/a&gt;, then stable event IDs can handle dedupe, severity can travel with the event, and the shared request ID can group deliveries from the same upstream action. That’s all that’s required for this. No need for a religion. Use the existing webhook shape to get failures into queues, boards, and CI jobs.&lt;/p&gt;

&lt;p&gt;The boring webhook handler should do four things:&lt;/p&gt;

&lt;ol&gt;
&lt;li&gt;Dedupe on event ID.&lt;/li&gt;
&lt;li&gt;Group related deliveries by request ID.&lt;/li&gt;
&lt;li&gt;Attach trace evidence to the existing issue when the cluster already exists.&lt;/li&gt;
&lt;li&gt;Trigger the right owner workflow for the right reasons, meaning severity and recurrence justify the cost of that workflow.&lt;/li&gt;
&lt;/ol&gt;

&lt;p&gt;This is a small piece of work. It is also how agent quality work avoids getting lost on Tuesday.&lt;/p&gt;

&lt;h2&gt;
  
  
  Benchmarks are pointing at the same problem
&lt;/h2&gt;

&lt;p&gt;Long-horizon agent work fails in similar ways to engineering work. Rather than one incorrect result, the failure is a series of small errors that creep up over time, leaving a final result that is less than useful.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://arxiv.org/abs/2605.15846" rel="noopener noreferrer"&gt;RoadmapBench&lt;/a&gt; exists to evaluate long-horizon software development tasks: 115 tasks spread across 17 repositories and 5 languages. The median task modified 3,700 lines of code in 51 files. For tasks at that size, the best model resolved 39.1% of them. The useful analysis is where the generated plan went wrong, which files inside the task became riskier, and which requirements got orphaned.&lt;/p&gt;

&lt;p&gt;The CLI project pipeline for &lt;a href="https://arxiv.org/abs/2602.14337" rel="noopener noreferrer"&gt;LongCLI-Bench&lt;/a&gt; uses the same kind of scoring to compare tool performance on long-horizon programming tasks: fail-to-pass, pass-to-pass, and step-level progress. It reports pass rates below 20% for state-of-the-art agents. In terms of stalls, there is a big difference between a late red X for failing to hit the ultimate task goal and an early red X that points to a tool loop, the wrong files, or a pass-to-fail regression.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://arxiv.org/abs/2605.15226" rel="noopener noreferrer"&gt;Phoenix-bench&lt;/a&gt;: Locating the oracle for file-level actions on hardware tasks added only 1.4% to resolution. A single round of feedback from testbench logs increased the resolved rate from 42% to 45%. It turns out that pointing to the right general area for a human to improve long-horizon programming tasks is of limited value. Providing actionable feedback that improves the task under consideration is valuable.&lt;/p&gt;

&lt;p&gt;This is the issue-loop argument dressed up in benchmark clothing. Better testing of AI agents requires more than a simple test suite. It requires a workflow that can expose issues, allow them to be fixed, and verify the fix inside the same workflow.&lt;/p&gt;

&lt;h2&gt;
  
  
  The eval suite should grow from resolved issues
&lt;/h2&gt;

&lt;p&gt;Closed issues should feed the test suite.&lt;/p&gt;

&lt;p&gt;LangSmith describes evaluators as &lt;a href="https://docs.langchain.com/langsmith/evaluators#manage-evaluators" rel="noopener noreferrer"&gt;workspace-level resources&lt;/a&gt; that can be attached to tracing projects and data sets in the same workspace. They can be suggested by Engine for detected issues where custom evaluators could be developed and then added as trace evidence for the closed clusters that caused the issue in the first place.&lt;/p&gt;

&lt;p&gt;Brace Sproul’s distinction between &lt;a href="https://x.com/BraceSproul/status/2056823612938850402" rel="noopener noreferrer"&gt;benchmark evals and coverage evals&lt;/a&gt; maps onto this. One set of evaluators for fast benchmarks on known workflows. A second, more exhaustive set of evaluators for longer paths, product commitments, and stranger trajectories. Trying to use one suite for both ends turns evals into the tax nobody wants to pay.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1bk2dm45g62ytr6z347f.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F1bk2dm45g62ytr6z347f.png" alt="Side-by-side matrix comparing fast benchmark evals with deeper coverage evals for AI agent workflows." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Resolved issues should feed the right suite, not one giant eval blob.&lt;/p&gt;

&lt;p&gt;Severity-0 resolved issues, like refund errors in critical workflows, should be evaluated with the fast benchmarks. A rare edge case in a long multi-hop research workflow is probably better served by the broader coverage suite, high cost and long run time included. Severity-0 policy violations may belong in both suites.&lt;/p&gt;

&lt;p&gt;However it gets cut, this is work. Every workflow change can introduce failure modes the system has not seen before. The test that proves a fix worked is different from the test that guards the same problem against a later regression. And then there is the matter of the gate.&lt;/p&gt;

&lt;h2&gt;
  
  
  The queue is where agency gets real
&lt;/h2&gt;

&lt;p&gt;The harder discipline is developing agents so they improve. That is much harder to demonstrate than the capabilities an agent can apply to tasks and workflows.&lt;/p&gt;

&lt;p&gt;A harder thing to demo is building AI agency into an agent. &lt;a href="https://focused.io/lab/developing-ai-agency" rel="noopener noreferrer"&gt;Developing AI agency&lt;/a&gt; was always about that discipline. It shows up in a particular way: when something fails, the team can explain what happened next.&lt;/p&gt;

&lt;p&gt;A good issue queue for a development team debugging a failure answers these questions. The team cannot get all this information from a single trace.&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Is this failure new or recurring?&lt;/li&gt;
&lt;li&gt;Which workflow owns it?&lt;/li&gt;
&lt;li&gt;Which traces point at the same root cause?&lt;/li&gt;
&lt;li&gt;Did the fix land?&lt;/li&gt;
&lt;li&gt;Which evaluator covers it now?&lt;/li&gt;
&lt;li&gt;Which release gate blocks a regression?&lt;/li&gt;
&lt;li&gt;Who gets paged if the issue comes back?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Again, this is normal software development, complicated by workflows that fail through complex, probabilistic, variable paths. Same defect, different costumes.&lt;/p&gt;

&lt;p&gt;The LangChain survey of production AI agents found that &lt;a href="https://www.langchain.com/state-of-agent-engineering" rel="noopener noreferrer"&gt;57.3% of respondents already have agents in production&lt;/a&gt;. The number one production blocker cited by respondents was quality, at 32%. This sits next to 89% observability adoption for production agents, far ahead of offline evaluation at 52.4% and online evaluation at 37.3%. There is already a sea of visibility for production agents. The work to convert that visibility into closed quality issues is still barely underway.&lt;/p&gt;

&lt;p&gt;Honeycomb’s new investigation features for agent observability start to address the same problem, with Agent Timeline built to reconstruct &lt;a href="https://www.honeycomb.io/blog/honeycomb-launches-agent-observability-full-visibility-agentic-workflows" rel="noopener noreferrer"&gt;complex multi-agent, multi-trace workflows&lt;/a&gt;. But reconnecting that path to specific owned work, and making sure the work is covered, is still the large gap.&lt;/p&gt;

&lt;p&gt;That is where the issue queue comes in.&lt;/p&gt;

&lt;h2&gt;
  
  
  Own the loop
&lt;/h2&gt;

&lt;p&gt;The AI agent workflow I want is not fancy.&lt;/p&gt;

&lt;p&gt;Signal failure -&amp;gt; create issue -&amp;gt; add evidence -&amp;gt; assign owner -&amp;gt; propose fix -&amp;gt; add evaluator -&amp;gt; run release gate -&amp;gt; reopen regression.&lt;/p&gt;

&lt;p&gt;This workflow looks less interesting week to week than announcing a new AI model. But to the buyer with an agent touching refunds, support tickets, infrastructure changes, or account data, this is the kind of work that matters week to week. Last week’s failure needs to become this week’s guardrail.&lt;/p&gt;

&lt;p&gt;Agent failures should open tickets.&lt;/p&gt;

&lt;p&gt;The ticket is where the trace becomes work. The work is where the system gets better.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agent Traces Need to Cross the MCP Boundary | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Tue, 19 May 2026 21:23:21 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agent-traces-need-to-cross-the-mcp-boundary-focused-labs-5f2l</link>
      <guid>https://dev.to/focused_dot_io/agent-traces-need-to-cross-the-mcp-boundary-focused-labs-5f2l</guid>
      <description>&lt;p&gt;Observability for AI agents running through MCP has a new failure point: the MCP tool call.&lt;/p&gt;

&lt;p&gt;Good. The broad version of this conversation has already been beaten to death. Agents need traces. Agents need evals. Agents need feedback loops. Fine. The sharper production question is what happens when the agent leaves the planner and crosses into a tool server owned by another team, another vendor, another runtime, or another cloud account.&lt;/p&gt;

&lt;p&gt;That boundary is where the trace disappears.&lt;/p&gt;

&lt;p&gt;Honeycomb is running &lt;a href="https://www.honeycomb.io/blog/honeycomb-announces-o11ycon-2026-bring-together-engineering-teams-building-agent-era" rel="noopener noreferrer"&gt;O11yCon in San Francisco this week&lt;/a&gt;. Christine Yen's line in the announcement gets at the issue: agents are writing code, agents are triaging incidents, agents are running production through orchestration, and engineering has little visibility into what the agents did, let alone whether they added value. The visibility gap for these agents is along the path between the model's decision, the tool server, and the downstream services affected by the action.&lt;/p&gt;

&lt;p&gt;The production shape is distributed tracing with a model in the loop.&lt;/p&gt;

&lt;p&gt;A planner says "tool failed." An MCP server just sees an unrelated &lt;code&gt;tools/call&lt;/code&gt;. A database sees a single query. A payment API sees a single request. The observability backend sees all these individual pieces and, operationally, has no idea what to do with them. Nobody can say whether the model chose the wrong tool, the planner's MCP client lost context somewhere along the line, the server failed to accept the call, or the downstream service simply timed out.&lt;/p&gt;

&lt;p&gt;Logs within a given service are comfortable to view because the local nature of the stream makes them easy to interpret. However, as soon as an incident affects multiple services or tools, that comfortable stream of logs disappears.&lt;/p&gt;

&lt;p&gt;MCP made tool integration portable. It did not magically make tool behavior observable. Focused has been pushing this shape for a while. In &lt;a href="https://focused.io/lab/developing-ai-agency" rel="noopener noreferrer"&gt;Developing AI Agency&lt;/a&gt;, the point was that useful agents need real engineering systems around them. In &lt;a href="https://focused.io/lab/streaming-agent-state-with-langgraph" rel="noopener noreferrer"&gt;Streaming agent state with LangGraph&lt;/a&gt;, the point was that intermediate state matters while long-running work is happening. MCP adds a protocol boundary to that same production story. If the trace cannot cross it, the agent becomes opaque at the exact moment it starts doing useful work.&lt;/p&gt;

&lt;h2&gt;
  
  
  MCP gave us the carrier
&lt;/h2&gt;

&lt;p&gt;MCP made tool integration for production tool calls easier. Making the behavior of those calls observable is a different job.&lt;/p&gt;

&lt;p&gt;This brings us to a simple and useful place: &lt;a href="https://modelcontextprotocol.io/seps/414-request-meta" rel="noopener noreferrer"&gt;SEP-414 reserves the W3C trace keys&lt;/a&gt; for W3C trace context propagation through MCP. So the MCP &lt;code&gt;tools/call&lt;/code&gt; request can include trace context as part of &lt;code&gt;params._meta&lt;/code&gt;, next to the tool name and arguments.&lt;/p&gt;

&lt;p&gt;MCP typically wants &lt;code&gt;_meta&lt;/code&gt; keys that start with a DNS-prefixed name. SEP-414 makes an exception for the three W3C trace keys so existing OpenTelemetry propagation can work without creating twelve slightly different names for the same thing. &lt;code&gt;traceparent&lt;/code&gt; stays &lt;code&gt;traceparent&lt;/code&gt;, &lt;code&gt;tracestate&lt;/code&gt; stays &lt;code&gt;tracestate&lt;/code&gt;, and &lt;code&gt;baggage&lt;/code&gt; stays &lt;code&gt;baggage&lt;/code&gt;.&lt;/p&gt;

&lt;p&gt;Tiny standardization, huge operational consequence.&lt;/p&gt;

&lt;p&gt;A universal set of properties for W3C trace context is a small thing to request. Without SEP-414, every agent stack invents its own set of properties in params: &lt;code&gt;io.modelcontextprotocol.traceparent&lt;/code&gt;, &lt;code&gt;otel_trace_parent&lt;/code&gt;, correlation IDs encoded in a vendor envelope, plus the special shape required by a proprietary monitoring stack. The resulting observability swamp would be indistinguishable from what exists today with services and their HTTP traces.&lt;/p&gt;

&lt;p&gt;First, the agent runtime starts a new span or continues an existing one. Then the MCP client for that runtime injects W3C trace context into &lt;code&gt;params._meta&lt;/code&gt; for the call. When the MCP server processes the call, it extracts the W3C trace context from &lt;code&gt;params._meta&lt;/code&gt;. Then the server creates a new server span. Tool code invoked by that server, including API calls to databases, queues, workflow engines, and other services, runs under the same trace context.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fkw0adpa9jk82yi0kj66q.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fkw0adpa9jk82yi0kj66q.png" alt="Agent runtime sends traceparent through MCP into downstream spans." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The tool boundary is where agent observability either survives or dies.&lt;/p&gt;

&lt;h2&gt;
  
  
  HTTP spans will not save the agent loop
&lt;/h2&gt;

&lt;p&gt;A tempting shortcut is to assume the transport already has tracing. The MCP server runs over HTTP. The ingress span exists. The collector sees requests. Done.&lt;/p&gt;

&lt;p&gt;Nope.&lt;/p&gt;

&lt;p&gt;That is why &lt;a href="https://opentelemetry.io/docs/specs/semconv/gen-ai/mcp/" rel="noopener noreferrer"&gt;OpenTelemetry's MCP semantic conventions&lt;/a&gt; matter: HTTP spans only contain information about transport. Streamable MCP transports can contain more than one request, and one MCP operation can spread across retries and transports. The transport context and MCP context are related, but different.&lt;/p&gt;

&lt;p&gt;A streamable HTTP request can sit under multiple MCP messages. A retry can create multiple transport-level attempts for one logical operation. Stdio has no HTTP request to hang a trace on at all. If instrumentation stops at the transport layer, the team is just looking at plumbing. The production question lives one layer up: what MCP method was called, what tool was called, what session was involved, what error type was returned, and which downstream spans received the trace context.&lt;/p&gt;

&lt;p&gt;A trace is useful when it follows the boundary. In the simplest case, a single trace starts with a span created by the agent runtime. The span name should be boring and low-cardinality, with names like &lt;code&gt;tools/call get_weather&lt;/code&gt;, &lt;code&gt;tools/call query_customer&lt;/code&gt;, or &lt;code&gt;tools/call create_ticket&lt;/code&gt;. The attributes carry the information that matters in production: &lt;code&gt;mcp.method.name&lt;/code&gt;, &lt;code&gt;gen_ai.tool.name&lt;/code&gt;, &lt;code&gt;mcp.session.id&lt;/code&gt;, &lt;code&gt;mcp.protocol.version&lt;/code&gt;, &lt;code&gt;network.transport&lt;/code&gt;, and &lt;code&gt;error.type&lt;/code&gt;. OpenTelemetry warns against adding high-cardinality resource URIs to span names by default. That creates backend cardinality problems for no benefit.&lt;/p&gt;

&lt;p&gt;The same thing is true for baggage. Baggage is useful for correlation. It is also an attractive nuisance. A tenant hint here, a route class there, an evaluation cohort for a particular set of runs. Fine. But prompts, secrets, user emails, access tokens, and customer data do not belong in baggage because trace context is supposed to cross service boundaries.&lt;/p&gt;

&lt;p&gt;Google's Cloud Trace documentation treats tracing through remote MCP request metadata as an implementation detail. A remote server can accept &lt;a href="https://docs.cloud.google.com/mcp/monitor-mcp-tool-use-with-cloud-trace" rel="noopener noreferrer"&gt;&lt;code&gt;traceparent&lt;/code&gt; in headers or &lt;code&gt;_meta&lt;/code&gt;&lt;/a&gt;. Once that tracing information is accepted and the trace is sampled, the server emits spans for the requested operation, including failures caused by the agent or by the tool, and latency caused by the client, network, or server processing.&lt;/p&gt;

&lt;p&gt;Sampling policy becomes relevant for observability of the agent's tool work. If the agent's tool work is not sampled, the tool's work cannot be reconstructed later by whoever wired up the chat UI.&lt;/p&gt;

&lt;h2&gt;
  
  
  Fragmented truth still loses the incident
&lt;/h2&gt;

&lt;p&gt;Separate traces can be valid. A vendor-operated MCP server may want a clean service boundary. A client team may not own the server. Langfuse's docs make that distinction directly: &lt;a href="https://langfuse.com/docs/observability/features/mcp-tracing" rel="noopener noreferrer"&gt;Langfuse's MCP tracing docs&lt;/a&gt;. But default separation is awful for incident management when the agent itself is causing a user-visible problem.&lt;/p&gt;

&lt;p&gt;The agent chooses a tool. The MCP server executes the request. The database locks. The tool returns a timeout. The planner retries with slightly different arguments. The user waits. Each system can tell the truth from inside its own box. The operator still has to stitch together causality by timestamps, request IDs, Slack screenshots, and vibes (the official fourth pillar, apparently).&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fq6lsdam77gqaoxv1mh0u.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fq6lsdam77gqaoxv1mh0u.png" alt="Fragmented traces versus one linked trace across planner, MCP server, and database." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Without propagation, every system tells the truth in isolation.&lt;/p&gt;

&lt;p&gt;In production flow, agent traces should form a chain that represents both the decision process for a request and the execution process carried out by services. The tool spans from an agent trace should link to the corresponding service spans. Having the agent's processing stages with nothing from subsequent services is model theater. Service spans without the corresponding tool decision are classic APM with no agent-specific information.&lt;/p&gt;

&lt;p&gt;Honeycomb has been going down a similar route. Their Innovation Week writeup describes agent workflows that branch, retry, call tools, hand off, and trigger services. They frame &lt;a href="https://www.honeycomb.io/blog/innovation-week-day-2-observability-for-ai-observability-with-ai" rel="noopener noreferrer"&gt;Agent Timeline&lt;/a&gt;. The resulting view places the agent's work inside the incident loop and shows the causal chain behind a prompt log.&lt;/p&gt;

&lt;h2&gt;
  
  
  The implementation surface is small
&lt;/h2&gt;

&lt;p&gt;Here is a concise specification for adding distributed tracing to an agent-enabled workflow:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;inject &lt;code&gt;traceparent&lt;/code&gt; into MCP &lt;code&gt;params._meta&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;extract it on the MCP server&lt;/li&gt;
&lt;li&gt;name spans by MCP method plus stable tool or prompt name&lt;/li&gt;
&lt;li&gt;attach MCP and GenAI attributes with low cardinality&lt;/li&gt;
&lt;li&gt;propagate trace context to following API and database calls&lt;/li&gt;
&lt;li&gt;keep sensitive data out of &lt;code&gt;baggage&lt;/code&gt;
&lt;/li&gt;
&lt;li&gt;send the result to a backend that can show agent and service work together&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The ecosystem around the MCP contract already does a decent amount of the heavy lifting. &lt;a href="https://grafana.com/docs/grafana/latest/developer-resources/mcp/developer/observability-metrics-and-tracing/" rel="noopener noreferrer"&gt;Grafana's MCP server docs&lt;/a&gt; include attributes such as &lt;code&gt;gen_ai.tool.name&lt;/code&gt;, &lt;code&gt;mcp.method.name&lt;/code&gt;, and &lt;code&gt;mcp.session.id&lt;/code&gt;, with W3C trace context propagation from &lt;code&gt;_meta&lt;/code&gt;. &lt;a href="https://mcp-toolbox.dev/documentation/monitoring/telemetry/" rel="noopener noreferrer"&gt;MCP Toolbox telemetry docs&lt;/a&gt; cover attributes for MCP method, transport, protocol, toolset, tool name, and error type. &lt;a href="https://docs.langchain.com/langsmith/trace-with-opentelemetry" rel="noopener noreferrer"&gt;LangSmith accepts OpenTelemetry ingestion&lt;/a&gt;, which means MCP spans do not have to sit in an observability island away from LangChain or LangGraph applications.&lt;/p&gt;

&lt;p&gt;In practice, agent systems run across different runtimes, including planners, graphs, model gateways, tool registries, MCP clients and servers, legacy APIs, databases, queues, approval steps, and eval jobs. Evidence of proper orchestration cannot scatter across architecture components and still be reviewable by team members from AI, platform, service, and business functions. We discussed the tradeoffs in &lt;a href="https://focused.io/lab/multi-agent-orchestration-in-langgraph-supervisor-vs-swarm-tradeoffs-and-architecture" rel="noopener noreferrer"&gt;Multi-Agent Orchestration in LangGraph&lt;/a&gt;. For trace propagation, the same reasoning applies. Architecture can be decomposed into modular components. Evidence for correct runtime behavior cannot.&lt;/p&gt;

&lt;p&gt;A decent review checklist is simple:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Can an operator start from a failed agent run and find the corresponding MCP &lt;code&gt;tools/call&lt;/code&gt; span for the tool that failed?&lt;/li&gt;
&lt;li&gt;Can they see the exact tool name without exploding cardinality?&lt;/li&gt;
&lt;li&gt;Can they jump from the client span to the server span?&lt;/li&gt;
&lt;li&gt;Can they see the downstream API, database, or queue work under the same trace?&lt;/li&gt;
&lt;li&gt;Can they distinguish model/tool selection failure from tool/server failure?&lt;/li&gt;
&lt;li&gt;Can they see &lt;code&gt;error.type&lt;/code&gt;, latency, tokens, and quality signals near the same workflow?&lt;/li&gt;
&lt;li&gt;Can they prove no secrets or PII are leaking through baggage or span attributes?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;Call it what it is: a pull request.&lt;/p&gt;

&lt;h2&gt;
  
  
  The owner is the team that owns the boundary
&lt;/h2&gt;

&lt;p&gt;The trick keeping observability in agent systems stuck is assigning MCP observability to the AI team, or to the MCP tools team, or to the database platform team, while claiming the boundary is too hard for any one team to own.&lt;/p&gt;

&lt;p&gt;There are four parties involved here: the vendor of the tool, the platform team, the AI team, and the service team. The vendor exposes spans. The platform team runs a collector to gather those spans. The AI team creates a planner span that is passed as context to tools. The service team instruments downstream API and database calls made by tools within an agent run. Someone has to own the boundary between those groups.&lt;/p&gt;

&lt;p&gt;Own the boundary.&lt;/p&gt;

&lt;p&gt;For an internal MCP server, trace propagation belongs in the server template for all calls. It should not be left to individual tools. For vendor-provided MCP servers, test the contract by sending &lt;code&gt;traceparent&lt;/code&gt; in &lt;code&gt;params._meta&lt;/code&gt; and verifying that the backend receives the linked span. Test trace propagation from the agent runtime for every tool call after context injection, without needing to chase separate dashboards. Baggage should have a clear policy before developers discover it as a convenient place to add sensitive information.&lt;/p&gt;

&lt;p&gt;AI agent observability will continue to sound mysterious when production monitoring means staring at transcripts of model dialogs. A transcript is one artifact. It will never show the intent behind a command, the tools used to execute it, the side effects, the latency, the errors, or the downstream work required by systems that had to deal with the output of those tools.&lt;/p&gt;

&lt;p&gt;MCP made tools portable. SEP-414 and the OpenTelemetry MCP conventions make the tool boundary traceable. The work is wonderfully unglamorous: pass the context, name the spans, control the attributes to keep cardinality low, protect baggage from sensitive information, and then follow the tool calls as the trace crosses the same boundary as the agent.&lt;/p&gt;

&lt;p&gt;Follow the trace, follow the agent.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>observability</category>
      <category>ai</category>
    </item>
    <item>
      <title>AI Agent Orchestration Needs Receipts | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Sun, 17 May 2026 21:13:49 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/ai-agent-orchestration-needs-receipts-focused-labs-2ho</link>
      <guid>https://dev.to/focused_dot_io/ai-agent-orchestration-needs-receipts-focused-labs-2ho</guid>
      <description>&lt;p&gt;Orchestrating AI agents breaks in the boring place of all: between issuing a tool call and the tool call having its intended side effect.&lt;/p&gt;

&lt;p&gt;As tool calls transition from being client tools executed by application code to server tools executed by models, there is a point in the system where the language and the abstraction used to describe the tool use breaks down. A tool call becomes a runtime transaction. The work done by a tool affects databases, makes payments, sends emails, creates tickets, etc. A retry storm, or even a simple retry, now has significant production consequences.&lt;/p&gt;

&lt;p&gt;Agent tools need receipts.&lt;/p&gt;

&lt;h2&gt;
  
  
  Tool Calls Are Side Effects With Better Marketing
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://platform.claude.com/docs/en/agents-and-tools/tool-use/overview" rel="noopener noreferrer"&gt;Anthropic's tool-use docs split server tools from client tools&lt;/a&gt;. A client tool is executed by application code, and then the application sends &lt;code&gt;tool_result&lt;/code&gt; back to the model. This is where language ends and production begins. Databases get mutated. Payments get made. Emails get sent. Tickets get updated. Credentials get used.&lt;/p&gt;

&lt;p&gt;I see this boundary get described as a function call. Better: side-effect boundary. These systems do not have a durable receipt right now.&lt;/p&gt;

&lt;p&gt;What proves the side effect in an agent runtime? The request IDs from external vendors, the changed rows in the business system, and the receipt the runtime saved before the model moved on. It takes human eyes reading through three different systems (and writing glue code along the way) to answer questions like "Did this exact tool intent already cause this exact side effect?" if the runtime cannot track the side effects caused by tool calls inside the model loop.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Old Backend Pattern Still Applies
&lt;/h2&gt;

&lt;p&gt;Normal API work has already figured this out. For example, &lt;a href="https://docs.stripe.com/api/idempotent_requests" rel="noopener noreferrer"&gt;Stripe supports idempotent requests for POST&lt;/a&gt;, so a caller can retry after a network failure without charging the customer twice. It tracks the original parameters for a given idempotency key, so if the key is reused with different parameters, it will not be treated as the same operation.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://docs.aws.amazon.com/powertools/python/latest/utilities/idempotency/" rel="noopener noreferrer"&gt;AWS Lambda Powertools describes idempotency records&lt;/a&gt; with INPROGRESS and COMPLETE states, payload hashes, stored responses and an expiration for the record. This is a tiny state machine around a side effect. That's all that's required for an agent runtime to safely handle model-intent-to-change-the-world calls.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://docs.aws.amazon.com/prescriptive-guidance/latest/cloud-design-patterns/transactional-outbox.html" rel="noopener noreferrer"&gt;transactional outbox pattern&lt;/a&gt;: write the business state and the outbound message in one database transaction, then deliver from the outbox. AWS writes about the duplicate-message problem for this style of delivery and recommends idempotent consumers that track processed message IDs.&lt;/p&gt;

&lt;p&gt;The deterministic backend, for example a Java or Python service, calls a service endpoint with fixed intent semantics. Booking a hotel room is boring in exactly the right way. An agent tool call is produced by a model loop that can re-plan, retry, branch, summarize state, and call the same tool again. The runtime has to record the intent before the side effect is produced.&lt;/p&gt;

&lt;h2&gt;
  
  
  What the Ledger Has to Know
&lt;/h2&gt;

&lt;p&gt;Tool Ledger. Side-Effect Journal. Orchestration Transaction Table. The name is unimportant. It is a table with a specific shape.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5f8qrxylenw05rlpay8t.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F5f8qrxylenw05rlpay8t.png" alt="Architecture diagram showing an agent runtime routing mutating tool calls through a side-effect ledger with idempotency keys and receipts." width="800" height="467"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The side-effect ledger is the boundary between model intent and production side effects.&lt;/p&gt;

&lt;p&gt;A side-effecting tool call needs a record before execution:&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;
&lt;span class="n"&gt;create&lt;/span&gt; &lt;span class="n"&gt;table&lt;/span&gt; &lt;span class="nf"&gt;agent_tool_ledger &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
  &lt;span class="nb"&gt;id&lt;/span&gt; &lt;span class="n"&gt;uuid&lt;/span&gt; &lt;span class="n"&gt;primary&lt;/span&gt; &lt;span class="n"&gt;key&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;run_id&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;step_id&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;tool_name&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;input_hash&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;operation_key&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt; &lt;span class="nf"&gt;check &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;status&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="p"&gt;(&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;planned&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;in_progress&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;succeeded&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;failed&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;compensating&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;'&lt;/span&gt;&lt;span class="s"&gt;compensated&lt;/span&gt;&lt;span class="sh"&gt;'&lt;/span&gt;
  &lt;span class="p"&gt;)),&lt;/span&gt;
  &lt;span class="n"&gt;receipt&lt;/span&gt; &lt;span class="n"&gt;jsonb&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;compensation&lt;/span&gt; &lt;span class="n"&gt;jsonb&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;error&lt;/span&gt; &lt;span class="n"&gt;jsonb&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;run_trace_id&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;owner_service&lt;/span&gt; &lt;span class="n"&gt;text&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
  &lt;span class="n"&gt;created_at&lt;/span&gt; &lt;span class="n"&gt;timestamptz&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt; &lt;span class="n"&gt;default&lt;/span&gt; &lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;
  &lt;span class="n"&gt;updated_at&lt;/span&gt; &lt;span class="n"&gt;timestamptz&lt;/span&gt; &lt;span class="ow"&gt;not&lt;/span&gt; &lt;span class="n"&gt;null&lt;/span&gt; &lt;span class="n"&gt;default&lt;/span&gt; &lt;span class="nf"&gt;now&lt;/span&gt;&lt;span class="p"&gt;(),&lt;/span&gt;
  &lt;span class="nf"&gt;unique &lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;tool_name&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;operation_key&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
&lt;span class="p"&gt;);&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;That unique constraint is the point.&lt;/p&gt;

&lt;p&gt;The record would hold: tool name, normalized input hash, run ID, graph step, owner service, run trace ID, status, receipt, and compensation metadata. On conflict, the application checks the stored &lt;code&gt;input_hash&lt;/code&gt; against the new &lt;code&gt;input_hash&lt;/code&gt;. Same key with different input is a bug. The receipt is the external fact: Stripe charge ID, Zendesk ticket ID, GitHub comment URL, invoice number, database primary key, email provider message ID.&lt;/p&gt;

&lt;p&gt;No receipt, no production claim.&lt;/p&gt;

&lt;h2&gt;
  
  
  Retry Safety Has to Be Designed Before the Retry
&lt;/h2&gt;

&lt;p&gt;A retry policy is essentially a duplicate side-effect generator wearing a reliability costume.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzr995om0l6r4xovbtj4j.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fzr995om0l6r4xovbtj4j.png" alt="Timeline comparing an unsafe agent retry that duplicates a side effect with a safe retry that checks a side-effect ledger and returns an existing receipt." width="800" height="444"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Retries become safe only after the runtime has a durable place to check intent and receipts.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://docs.temporal.io/activity-definition" rel="noopener noreferrer"&gt;Temporal's Activity documentation recommends idempotent Activities&lt;/a&gt; because they can be retried. A non-idempotent Activity can corrupt application state even when the distributed system is functioning correctly. The runtime's retry policy does not make the agent reliable by itself.&lt;/p&gt;

&lt;p&gt;This is where agent systems get uncomfortable. Because we've instrumented our system to retry on transport failure, we can easily believe that we're retrying on transport failure, when in reality we're just retrying on a model of the world that observes a timeout and decides to go down a different path. So, for example, after refunding a customer the model may decide to create a support note, and then the model may decide to refund the customer again in a summary step, losing the receipt from the first attempt. The model may ask a human for confirmation in the meantime and then resume with stale tool context. The model may even run a background subagent that decides to go down a different path in order to arrive at the same conclusion.&lt;/p&gt;

&lt;p&gt;This intent cannot be raw JSON. Models produce irrelevant differences. Field order changes. Natural-language notes shift. A good operation key comes from the business operation. The model's token stream is too noisy. refund:{tenant_id}:{payment_id}:{reason_code} beats a hash of the entire prompt. comment:{repo}:{pull_request}:{review_run_id} beats a blob of generated markdown.&lt;/p&gt;

&lt;p&gt;That ownership boundary corresponds to the ownership of the credentials for the tool. In agent systems, the authentication of the agent to the external system should start with the workload identity. In &lt;a href="https://focused.io/lab/ai-agent-authentication-workload-identity" rel="noopener noreferrer"&gt;AI Agent Authentication Starts With Workload Identity&lt;/a&gt;, we discussed the reasons why the secrets should not be passed around like party favors. This same principle applies here. The runtime should not make up the side-effect semantics for a tool that is not owned by the runtime.&lt;/p&gt;

&lt;h2&gt;
  
  
  Observability Without the Receipt Is Theater
&lt;/h2&gt;

&lt;p&gt;But traces do not, by default, create a business-level uniqueness boundary.&lt;/p&gt;

&lt;p&gt;Joining traces to ledger entries changes what agent observability can do. The trace explains the path after the incident. The ledger table can drive behavior during the incident: suppress the duplicate, resume from a receipt, trigger compensation, alert the owning team, or block the next step until a human approves the ambiguous side effect.&lt;/p&gt;

&lt;p&gt;That is the difference between a dashboard and a control surface. The trace is evidence. The ledger is state.&lt;/p&gt;

&lt;p&gt;Evaluations also get a lot better. In place of "the model called the refund tool", the useful check is one planned refund, one succeeded ledger entry, one receipt, zero duplicate external effects after a simulated timeout. In &lt;a href="https://focused.io/lab/everybody-tests" rel="noopener noreferrer"&gt;Everybody Tests&lt;/a&gt;, we recognized that people are already testing with the feedback loops they have today. The transcript is too thin to capture all the detail.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Tool Interface Should Expose the Contract
&lt;/h2&gt;

&lt;p&gt;The contract for a side-effecting tool should be defined near the definition of the tool itself. That contract should describe the operational facts that the runtime can enforce for that tool. A side-effecting tool contract should answer:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;Is the tool read-only or mutating?&lt;/li&gt;
&lt;li&gt;Who owns the tool?&lt;/li&gt;
&lt;li&gt;Which fields form the operation key?&lt;/li&gt;
&lt;li&gt;Which external receipt proves success?&lt;/li&gt;
&lt;li&gt;What status means the side effect is safe to retry?&lt;/li&gt;
&lt;li&gt;What compensation path exists when the effect is wrong?&lt;/li&gt;
&lt;li&gt;How long does the ledger entry live?&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;This is where &lt;a href="https://focused.io/lab/mcp-is-packaging-agent-operable-interfaces-are-the-product" rel="noopener noreferrer"&gt;MCP and other tool packaging efforts&lt;/a&gt; need to "grow up" to support packaging of tools for agents to use in production. Such interfaces are not just "packaging" and must be agent-operable - typed, permissioned, inspectable, retryable, and owned by a service. This is the real product, and it is a far cry from a mere interface for the agent to discover and call a tool.&lt;/p&gt;

&lt;p&gt;A tool registry that simply says a tool exists is table stakes. A registry that says a write tool mutates customer billing, requires workload identity, lists the operation-key fields, emits a specific external receipt, and pages the service owner on ambiguous completion starts to look like production infrastructure.&lt;/p&gt;

&lt;p&gt;Boring. Also useful.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Runtime Should Refuse Unsafe Writes
&lt;/h2&gt;

&lt;p&gt;Ledger policies for mutating tools run the show.&lt;/p&gt;

&lt;p&gt;Read-only search tools remain lightweight, (retrieval, ranking, summarization, classification). Write tools charge cards or email customers. Write tools have their own set of problems but follow a different set of rules. For write tools the runtime should require a ledger policy before registration. The tool owner supplies the operation-key builder, receipt parser, retry rules, and compensation metadata. The runtime supplies the reservation, status transitions, trace joining, and audit events. The rest of the orchestration layer checks the side-effect ledger before running the tool and after it fails. The eval harness tests the duplicate paths for the tool. The on-call team can see stuck &lt;code&gt;in_progress&lt;/code&gt; rows before the customers do.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://focused.io/lab/langgraph-agent-error-handling-production" rel="noopener noreferrer"&gt;LangGraph Agent Error Handling in Production&lt;/a&gt;. Here, handling errors in tools called by an agent is more than simply handling exceptions that occur when the tool is called. The side effects that occur before the error is surfaced, especially around a timeout, are the real problem the error handling has to address. The ledger is where the system goes looking for evidence.&lt;/p&gt;

&lt;p&gt;That last point matters. Agents can keep going after an error has occurred. But in production, continuing can be reckless.&lt;/p&gt;

&lt;h2&gt;
  
  
  Own the Receipt
&lt;/h2&gt;

&lt;p&gt;The gold rush version of AI agent orchestration wants better planners, bigger context windows, and more tools. Fine. Those help.&lt;/p&gt;

&lt;p&gt;The production version needs a boring table that answers whether a tool call already did the thing.&lt;/p&gt;

&lt;p&gt;That table won't demo well. Nobody cheers for a simple unique index on &lt;code&gt;(tool_name, operation_key)&lt;/code&gt;. But that's exactly what this table is. And it will save a team from having to refund, email, provision, delete and apologize (for the mysterious model) twice.&lt;/p&gt;

&lt;p&gt;The model can be probabilistic. The side-effect boundary cannot.&lt;/p&gt;

&lt;p&gt;Own the receipt.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agentic AI Implementation Runs Through Change Control | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Sun, 17 May 2026 21:13:16 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agentic-ai-implementation-runs-through-change-control-focused-labs-37pi</link>
      <guid>https://dev.to/focused_dot_io/agentic-ai-implementation-runs-through-change-control-focused-labs-37pi</guid>
      <description>&lt;p&gt;There’s been a big mis-selling in Agentic AI implementation. People compare its implementation to software enablement. But this breaks when the agent can change a workflow.&lt;/p&gt;

&lt;p&gt;The agent approves a refund, opens an incident, updates a customer record, begins onboarding for a new customer, or escalates a support ticket. At that point a training calendar and a Slack message are not enough for a rollout plan.&lt;/p&gt;

&lt;p&gt;It needs a change record.&lt;/p&gt;

&lt;p&gt;Enterprise AI adoption has a naming problem. Work ‘adoption’ gets viewed through the same lens as software ‘usage’. Thus work is framed in terms of seats, office hours, examples of how to properly format a prompt, and wait for it to kick in. But then the work actually gets executed out through an agent that in turn changes a workflow.&lt;/p&gt;

&lt;p&gt;The system has entered the process.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.microsoft.com/en-us/worklab/work-trend-index/agents-human-agency-and-the-opportunity-for-every-organization" rel="noopener noreferrer"&gt;Microsoft's 2026 Work Trend Index&lt;/a&gt; frames this shift as an operating-model problem. WorkLab analysis finds that employees may be ready for AI, while the systems around work are not. Agent approvals, open incidents, and changed customer records create a different implementation roadmap.&lt;/p&gt;

&lt;p&gt;That changes the implementation roadmap.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Rollout Surface Changed
&lt;/h2&gt;

&lt;p&gt;Agents behave differently from a chat tool. An agent is released through a system.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://newsroom.servicenow.com/press-releases/details/2026/ServiceNow-opens-its-full-system-of-action-to-every-AI-Agent-in-the-enterprise/default.aspx" rel="noopener noreferrer"&gt;ServiceNow announced Action Fabric at Knowledge 2026&lt;/a&gt;, explicitly opening its governed system of action to agents. The MCP Server gives agents access to workflows, playbooks, approvals, catalog requests, and business rules. All of which run through identity verification, granted permissions, and audit trails.&lt;/p&gt;

&lt;p&gt;Within an enterprise the enterprise agent problem manifests itself when an agent has moved from the edge of a process, creating a summary of work done, to inside the process, making a move.&lt;/p&gt;

&lt;p&gt;The first key question that comes to the surface for the enterprise is no longer "who should have access to this tool" and rather "what change is this tool going to drive for the business, and who is going to own that change (ie: the teams that run the production systems, compliance to regulations, promises to customers, incident response, and the overall economics of the workflows that this will insert into)".&lt;/p&gt;

&lt;p&gt;The reality of the enterprise is well captured in a preview for LangChain's Interrupt 2026: the initial excitement to have agents proving work in production will quickly give way to questions about the team, tooling and infrastructure required to support agents that are no longer ‘proof-of-concept’ work (LangChain Interrupt 2026 preview &lt;a href="https://www.langchain.com/blog/previewing-interrupt-2026-agents-at-enterprise-scale" rel="noopener noreferrer"&gt;LangChain Interrupt 2026 preview&lt;/a&gt;). My experience with clients has been the same: there is initial excitement with the first useful agent, overlap of work with the second and finally ownership problems with the third.&lt;/p&gt;

&lt;p&gt;Fine. That is the good version.&lt;/p&gt;

&lt;p&gt;The bad version of this is quiet. A team enables an agent with a service account, an admin token, a dashboard that nobody looks at. It looks good during the demo, and then a change in a source system happens (e.g. a field name changes), a policy document drifts, an approval queue gets renamed, a customer edge case gets found out, and the agent keeps moving. Nobody owns the change because nobody treated the agent as a change.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjm67oni2b700t3f1emvd.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fjm67oni2b700t3f1emvd.png" alt="Agent rollout path from prototype to change record, sandbox, canary, and production" width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The rollout path gets safer when every promotion carries evidence, scope, and a rollback owner.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Change Record Is the Agent Spec
&lt;/h2&gt;

&lt;p&gt;&lt;a href="https://www.atlassian.com/itsm/change-management" rel="noopener noreferrer"&gt;Atlassian describes IT change management&lt;/a&gt; as planning, reviewing, approving, and deploying changes to services with as little disruption as possible. Boring. Also the right object.&lt;/p&gt;

&lt;p&gt;Agentic AI needs the same boring object.&lt;/p&gt;

&lt;p&gt;A change record should specify which human role loses or gains work, which systems the agent can interact with, which actions require approval, which actions are forbidden, which metrics define harm, which traces prove behavior, and which owner can roll back changes made by the agent when something goes wrong.&lt;/p&gt;

&lt;p&gt;Rather than going straight to a typical roadmap of discovery, pilot, platform choice, training, and rollout, I would put a change-control spine through each step of that typical roadmap.&lt;/p&gt;

&lt;p&gt;By discovering the workflows instead of thinking of all the cool things an AI can do, we can categorize “Summarize account notes” and “renew an enterprise contract” for example into different risk classes. For example, pilot work should run in a sandbox that is production-like in terms of data and failure handling. Limited rollout of an agent should in the first place constrain the authority of the agent before it’s given to more people. And production should have a clear owner, and the agent and all its traces should be kept for a defined amount of time, after which they can be evaluated for performance, and in case of an incident there should be a clear path to resolve it.&lt;/p&gt;

&lt;p&gt;This keeps the agent’s actual permissions from being discovered during an incident review.&lt;/p&gt;

&lt;p&gt;By embedding service ownership into an organization’s way of working, these implementation dangers can be mitigated by establishing contracts between teams, a sandboxed deployment, and an appropriate rollout sequence. The AI team can be left to own the things they know best, i.e. the evaluation harness, the evals, model routing, and deployment mechanics. The business process owner must own the workflow semantics. Security, operations, and the relevant parts of legal or compliance must own the permission envelope, production response, and the consequences of non-compliance (respectively).&lt;/p&gt;

&lt;p&gt;Shared ownership is annoying. So is production.&lt;/p&gt;

&lt;p&gt;This is why I keep harping on service ownership for agent work. &lt;a href="https://focused.io/lab/langgraph-enterprise-agent-development" rel="noopener noreferrer"&gt;LangGraph for enterprise agent development&lt;/a&gt; made the runtime version of this point. Production agents have operational contracts. A clever graph is not enough. It can fall apart after the first model swap, policy change, or integration outage.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fre0n2yfo5djf2k3juxli.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2Fre0n2yfo5djf2k3juxli.png" alt="Change record connecting workflow owner, permission envelope, eval gate, telemetry, and rollback path" width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The change record is the handoff object between business process, agent runtime, security, and operations.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Metrics Already Exist
&lt;/h2&gt;

&lt;p&gt;No need for another exotic agent scorecard. The software delivery world already has the basic bones. &lt;a href="https://dora.dev/guides/dora-metrics/" rel="noopener noreferrer"&gt;DORA's software delivery metrics&lt;/a&gt; track change lead time, deployment frequency, failed deployment recovery time, change fail rate, and deployment rework rate.&lt;/p&gt;

&lt;p&gt;Change lead time: time from proposing agent behavior to approving production behavior. Deployment frequency: rate of safe promoting of an agent to production, such as adding an agent to a tool registry, policy pack, an organization’s memory schema, retrieval index, or a workflow. Failed deployment recovery time: time to reverse an action of an agent, such as reverting a prompt or policy that was added to production, removing a permission that was granted to an agent, or switching back to a previous workflow. Change fail rate: percentage of changes to agents that require intervention.&lt;/p&gt;

&lt;p&gt;This would all be nice and clean if an agent’s behavior failed in a binary way, like an exception being thrown. But it does not. It produces a technically correct answer that just happens to be wrong in the context of the workflow. Which is why the failure is behavioral, not binary, and is invisible to a deployment platform that only knows how to scream when a process fails to start.&lt;/p&gt;

&lt;p&gt;So the metric needs evidence.&lt;/p&gt;

&lt;p&gt;In the end, the production agent rollout should collect all traces of decisions (tool calls, approval steps etc), rejected actions (e.g. because of insufficient privileges), user corrected mistakes as well as any failures of the eval routine. Business outcomes should also be added to that list of the things changed for a release story and then the team has the evidence for the change board that they’re approving of “stuff” with a slightly nicer UI.&lt;/p&gt;

&lt;p&gt;This is where &lt;a href="https://focused.io/lab/everybody-tests" rel="noopener noreferrer"&gt;Everybody Tests&lt;/a&gt; comes in. Testing cannot be relegated to downstream QA when an agent can affect a live workflow. Product, engineering, operations, security, and enterprise systems teams should be able to run the test. Ideally, they should understand it, too. The eval suite tests behavioral regressions. Traces reveal runtime drift. Approval logs expose authority escalation. Business metrics surface harm the model never sees.&lt;/p&gt;

&lt;p&gt;All of them are part of the change.&lt;/p&gt;

&lt;h2&gt;
  
  
  The Roadmap Is a Promotion Ladder
&lt;/h2&gt;

&lt;p&gt;Start with read-only assistance. The agent assists with summarization, search, templates, classification, and process explanation. That finds workflow fit and failure modes without giving the system authority to act.&lt;/p&gt;

&lt;p&gt;Next, the team gradually grants more permission inside well-defined boundaries. Completing low-dollar refunds, updating internal tickets, sending non-regulated customer messages, changing low-risk account fields, deploying to test environments. The goal is to prove bounded authority before scope expands.&lt;/p&gt;

&lt;p&gt;This promotion path pays for itself by preventing a business process from being secretly screwed by an AI that nobody can explain.&lt;/p&gt;

&lt;p&gt;Make each step on the promotion ladder concrete. Human-in-the-loop needs a named reviewer, a review surface, override power, correction capture, and a rule for when the agent stops asking. Same for guardrails, observability, and governance. Each word should collapse to an owner, system, threshold, and audit trail.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://www.mckinsey.com/capabilities/tech-and-ai/our-insights/tech-forward/state-of-ai-trust-in-2026-shifting-to-the-agentic-era" rel="noopener noreferrer"&gt;McKinsey's 2026 AI trust survey&lt;/a&gt; is useful here because it separates adoption from maturity. Strategy, governance, and controls for agentic AI remain the weak spots. Security and risk concerns remain the main barrier to scaling. Which tracks.&lt;/p&gt;

&lt;p&gt;Boring. Beautiful.&lt;/p&gt;

&lt;h2&gt;
  
  
  Own the Change
&lt;/h2&gt;

&lt;p&gt;So long as an organization treats an enterprise AI agent like another tool intended to spread to more people in the organization with the same amount of enthusiasm, then the AI agent’s implementation will fail shortly after the first collisions with the organization’s permission models, its customers’ reporting structures, its compliance requirements, its process exceptions and its sheer number of customers.&lt;/p&gt;

&lt;p&gt;I have no particular interest in helping to recreate the CAB theater for Enterprise Agents. Meetings with 8 approvers (or more!) for a password reset workflow that they cannot even understand is a huge waste of time and effort. Yes, review is reasonable in regulated paths, but that should be the exception, not the rule. And it should be as trivial and technical as possible, ideally close to where the work is actually being done. (In this case a simple approval in the workflow UI).&lt;/p&gt;

&lt;p&gt;Put the agent change record next to the PR, the eval report, the trace sample, the permission diff, and the rollback plan. Have the workflow owner sign the semantics; security sign the authority; engineering sign the runtime; and operations sign the incident path.&lt;/p&gt;

&lt;p&gt;Then ship.&lt;/p&gt;

&lt;p&gt;That is what an AI implementation roadmap needs now: a promotion path for systems that can act.&lt;/p&gt;

&lt;p&gt;Production always gets weird.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
    </item>
    <item>
      <title>Agent Benchmark Scores Are Measuring the Harness, Not the Model | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Sun, 17 May 2026 21:13:13 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/agent-benchmark-scores-are-measuring-the-harness-not-the-model-focused-labs-145l</link>
      <guid>https://dev.to/focused_dot_io/agent-benchmark-scores-are-measuring-the-harness-not-the-model-focused-labs-145l</guid>
      <description>&lt;p&gt;The difference between the leading agentic coding models is much smaller than the difference between two distinct configurations of a single model on the same benchmark. &lt;a href="https://www.anthropic.com/engineering/infrastructure-noise" rel="noopener noreferrer"&gt;Anthropic just quantified it&lt;/a&gt;: a six-percentage-point gap on Terminal-Bench 2.0 between the most- and least-resourced setups, p &amp;lt; 0.01. Same model. Same task set. Same harness. The only variable was the resource budget given to the pod.&lt;/p&gt;

&lt;p&gt;This is larger than the spread between most frontier models on the public leaderboard.&lt;/p&gt;

&lt;p&gt;The number the enterprise picked as "the best agent model" is mostly the amount of CPU and RAM that the eval team assigned to the pod for the test. Welcome to production.&lt;/p&gt;

&lt;h2&gt;
  
  
  The benchmark is not what the benchmark claims to measure
&lt;/h2&gt;

&lt;p&gt;Static evals score a model's output directly. Agentic coding evals score a model in a runtime, and the runtime itself decides whether a container gets OOM-killed for a transient memory spike, whether a &lt;code&gt;pip install&lt;/code&gt; command finishes, whether a test subprocess ever returns a result. Two agents at different resource budgets will be taking different tests.&lt;/p&gt;

&lt;p&gt;Anthropic ran Terminal-Bench 2.0 across six resource configurations, from strict enforcement of the per-task specs all the way to completely uncapped. They observed 5.8% of tasks failing on pod errors unrelated to model capacity at strict enforcement, compared to 0.5% at uncapped. Success scores at 1x through 3x were largely within noise (p=0.40), since the agent was going to fail those tasks anyway. However, past 3x, success scores climbed faster than infra errors declined. The extra headroom gave the agent room to attempt new approaches that only work when given more generous allocations, such as installing several large packages at once, running memory-hungry test suites, or spawning subprocesses that take extra time to complete.&lt;/p&gt;

&lt;p&gt;The benchmark shifted. Previously it was measuring how capable the model was. Now it is measuring how much budget the harness gives the agent to brute-force the answer.&lt;/p&gt;

&lt;p&gt;This is not a bug in Terminal-Bench. It is the nature of agentic evaluation: the runtime is not a passive container, it is an active part of the problem-solving process.&lt;/p&gt;

&lt;p&gt;When the benchmark does not include the exact hardware and resource configuration, it ships a number that can't be compared to anyone else's number. Nobody is measuring the same thing.&lt;/p&gt;

&lt;h2&gt;
  
  
  The model is mostly plumbing
&lt;/h2&gt;

&lt;p&gt;Harrison Chase has been making a variant of this argument for about a year. The agent is not the model. The agent is the harness, memory, tools, prompts, retries, state machines, guardrails, and context windows, with a model call buried somewhere in there.&lt;/p&gt;

&lt;p&gt;The Anthropic data is the experimental confirmation of the harness sitting at the heart of the agent. Flip the pod resource limits and the "same" agent is a different agent inhabiting a wildly different reality. Flip the sandbox provider and the same leaderboard score means a completely different thing. The vast majority of the decisions that go into building an agent are about tuning the harness.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://x.com/AnnaBernad50664/status/2046626400296174052" rel="noopener noreferrer"&gt;Anna Bernad posted a Twitter thread&lt;/a&gt; last week after looking at 36 production agent harnesses. Her take is far sharper than mine.&lt;/p&gt;

&lt;blockquote&gt;
&lt;p&gt;"Every harness I studied that actually ships does the same underlying move, and guess, it's not separation. It's making the context describe a different room."  &lt;/p&gt;
&lt;/blockquote&gt;

&lt;p&gt;If the context reads as "teammate shipped work, I'm the reviewer, pipeline wants green," the agent soft-approves with a minor note. Not because the model is bad. The agent is trying to fit the response to the context, and soft approval is the only way to complete the pattern.&lt;/p&gt;

&lt;p&gt;The harness is the room. The model is the tenant.&lt;/p&gt;

&lt;h2&gt;
  
  
  What this does to enterprise procurement
&lt;/h2&gt;

&lt;p&gt;Agent performance based on a benchmark consistently deviates from expectations once a client engages with our service. The model selected for the agent's function is sound. The "harness" through which the model is commanded to operate is what impedes the application. The runtime may not give the tools sufficient compute to act effectively. The retry mechanism built to improve throughput actually masks critical errors until it is far too late. The context window is being consumed by boilerplate system prompts the procurement team didn't know existed.&lt;/p&gt;

&lt;p&gt;The enterprise then concludes "AI doesn't work for us" and abandons the effort. The model vendor is blamed. Nobody audits the scaffold.&lt;/p&gt;

&lt;p&gt;Vendor benchmark claims aren't automatically disbelieved, but those claims become purely marketing when translated into an "eval score" meant for buyers to use in evaluating vendors. If the eval score is only reproducible on the vendor's Kubernetes cluster with their sandboxing solution and their machine resources, it's safe to say the score has no procurement value.&lt;/p&gt;

&lt;p&gt;The &lt;a href="https://x.com/LangChain/status/2046303329312227787" rel="noopener noreferrer"&gt;LangSmith Signal report this week&lt;/a&gt; puts billions of agent runs behind the month's trends. Anthropic grew 73% in users, gaining 39% of share. Gemini rose after the release of Gemini 3. OpenAI remained the largest at around 80% of volume but didn't move up or down. Those are usage numbers, not capability numbers. People are moving around based on what actually works in their harness, not based on what a leaderboard says.&lt;/p&gt;

&lt;h2&gt;
  
  
  How to read a benchmark
&lt;/h2&gt;

&lt;p&gt;Three questions, in order.&lt;/p&gt;

&lt;p&gt;The first question is what the harness actually was. If the eval team doesn't publish the scaffold, retry policy, context budget, tool set, and resource configuration tradeoffs, the number is a picture of one run on their box and not comparable to anything.&lt;/p&gt;

&lt;p&gt;Second: what is the infra error rate? Anthropic reported 5.8% of Terminal-Bench 2.0 tasks failing on pod errors at strict enforcement, a 5x margin above the spread between most frontier models. An eval that doesn't separate "model failed" from "container got killed" introduces a lot of noise in the headline number.&lt;/p&gt;

&lt;p&gt;Third: does my production environment resemble the eval environment? If the eval runs uncapped on a data-center GPU cluster, the score is going to have almost no predictive value for me, since my agent runs in a sandboxed environment such as a Lambda function with a 512MB memory cap. An agent can win the competition by brute-forcing the space of &lt;code&gt;scikit-learn&lt;/code&gt; installs and then fail silently at ship time because it consumes too much memory in the production environment. A lean, efficient agent that loses the benchmark will ship just fine.&lt;/p&gt;

&lt;h2&gt;
  
  
  What to do instead
&lt;/h2&gt;

&lt;p&gt;Build the harness first. Run the model last.&lt;/p&gt;

&lt;p&gt;The analysis has to translate to production. Production tools. Production retry budget (or lack thereof). Production memory store. Production prompt scaffolding. Production runtime limits. Wire it up with &lt;a href="https://focused.io/lab/your-customer-service-bot-is-slow-because-its-single-threaded" rel="noopener noreferrer"&gt;observability that traces trajectories through the system, not individual LLM calls&lt;/a&gt;. Then swap different models in and see what changes.&lt;br&gt;
&lt;/p&gt;

&lt;div class="highlight js-code-highlight"&gt;
&lt;pre class="highlight python"&gt;&lt;code&gt;
&lt;span class="c1"&gt;# Shape of an internal model bake-off in 2026.
# LangChain 1.x, LangGraph 1.1.9, LangSmith.
&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;langchain.agents&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;create_agent&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;langsmith&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;Client&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt; &lt;span class="n"&gt;traceable&lt;/span&gt;
&lt;span class="kn"&gt;from&lt;/span&gt; &lt;span class="n"&gt;langsmith.evaluation&lt;/span&gt; &lt;span class="kn"&gt;import&lt;/span&gt; &lt;span class="n"&gt;evaluate&lt;/span&gt;

&lt;span class="n"&gt;CANDIDATES&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="p"&gt;[&lt;/span&gt;
    &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;anthropic:claude-opus-4-7&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;openai:gpt-5.1-pro&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;google:gemini-3-pro&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
&lt;span class="p"&gt;]&lt;/span&gt;

&lt;span class="k"&gt;def&lt;/span&gt; &lt;span class="nf"&gt;build_agent&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="nb"&gt;str&lt;/span&gt;&lt;span class="p"&gt;):&lt;/span&gt;
    &lt;span class="c1"&gt;# Same tools, same prompt, same retry budget, same memory store.
&lt;/span&gt;    &lt;span class="c1"&gt;# The ONLY variable is the model string.
&lt;/span&gt;    &lt;span class="k"&gt;return&lt;/span&gt; &lt;span class="nf"&gt;create_agent&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;model&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;tools&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;PRODUCTION_TOOLS&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;prompt&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;PRODUCTION_SYSTEM_PROMPT&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;middleware&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="nc"&gt;PIIMiddleware&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;config&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;PROD_PII_CONFIG&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
            &lt;span class="nc"&gt;HumanInTheLoopMiddleware&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;escalation_policy&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;PROD_POLICY&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="n"&gt;context_schema&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;ProductionContext&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="n"&gt;client&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nc"&gt;Client&lt;/span&gt;&lt;span class="p"&gt;()&lt;/span&gt;
&lt;span class="n"&gt;dataset&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="n"&gt;client&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;read_dataset&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;dataset_name&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;production-trajectories-q2&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;

&lt;span class="k"&gt;for&lt;/span&gt; &lt;span class="n"&gt;model_id&lt;/span&gt; &lt;span class="ow"&gt;in&lt;/span&gt; &lt;span class="n"&gt;CANDIDATES&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt;
    &lt;span class="n"&gt;agent&lt;/span&gt; &lt;span class="o"&gt;=&lt;/span&gt; &lt;span class="nf"&gt;build_agent&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;model_id&lt;/span&gt;&lt;span class="p"&gt;)&lt;/span&gt;
    &lt;span class="nf"&gt;evaluate&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;
        &lt;span class="k"&gt;lambda&lt;/span&gt; &lt;span class="n"&gt;inputs&lt;/span&gt;&lt;span class="p"&gt;:&lt;/span&gt; &lt;span class="n"&gt;agent&lt;/span&gt;&lt;span class="p"&gt;.&lt;/span&gt;&lt;span class="nf"&gt;invoke&lt;/span&gt;&lt;span class="p"&gt;(&lt;/span&gt;&lt;span class="n"&gt;inputs&lt;/span&gt;&lt;span class="p"&gt;),&lt;/span&gt;
        &lt;span class="n"&gt;data&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="n"&gt;dataset&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;evaluators&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="p"&gt;[&lt;/span&gt;
            &lt;span class="n"&gt;trajectory_match&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;       &lt;span class="c1"&gt;# compares actual tool-call path to reference
&lt;/span&gt;            &lt;span class="n"&gt;tool_call_precision&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;    &lt;span class="c1"&gt;# did the agent use the right tool at the right time
&lt;/span&gt;            &lt;span class="n"&gt;final_output_rubric&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;    &lt;span class="c1"&gt;# LLM-as-judge on the end state
&lt;/span&gt;        &lt;span class="p"&gt;],&lt;/span&gt;
        &lt;span class="n"&gt;experiment_prefix&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="sa"&gt;f&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="s"&gt;harness-bakeoff-&lt;/span&gt;&lt;span class="si"&gt;{&lt;/span&gt;&lt;span class="n"&gt;model_id&lt;/span&gt;&lt;span class="si"&gt;}&lt;/span&gt;&lt;span class="sh"&gt;"&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
        &lt;span class="n"&gt;max_concurrency&lt;/span&gt;&lt;span class="o"&gt;=&lt;/span&gt;&lt;span class="mi"&gt;8&lt;/span&gt;&lt;span class="p"&gt;,&lt;/span&gt;
    &lt;span class="p"&gt;)&lt;/span&gt;
&lt;/code&gt;&lt;/pre&gt;

&lt;/div&gt;



&lt;p&gt;All tests run using the same harness, the same tools, one variable at a time. The goal is to select the model that actually works within the production stack, not the one that earned points on a public leaderboard running on a Kubernetes cluster someone else had tuned.&lt;/p&gt;

&lt;p&gt;This is where the engineering work is. This is also why &lt;a href="https://focused.io/lab/developing-ai-agency" rel="noopener noreferrer"&gt;the agent harness is where the engineering work lives now&lt;/a&gt;, and why a lot of clients call us. The model picker is not the problem. The harness design is the problem. The eval infrastructure is the problem. The trajectory observability is the problem.&lt;/p&gt;

&lt;h2&gt;
  
  
  The harder truth
&lt;/h2&gt;

&lt;p&gt;The methods for finding genuinely good agents tended to favor simplicity and efficiency. The reason is that we were looking for agents that could write efficient code quickly. In contrast, agents that had plenty of resources available tended to do better when there were plenty of resources available. Both types of agents are useful to test for, and both correspond to realistic scenarios. Neither of them can fairly be collapsed into a single number on a leaderboard.&lt;/p&gt;

&lt;p&gt;Many of the agents we deploy to enterprises run on some sort of strict budget for resources such as memory and CPU. Beyond these general limits, there are often specific restrictions on things like subprocess runtime and the number of times an API can be called within a window, largely because of cost. The model that wins with unlimited resources is a different model than the one that wins under strict limits.&lt;/p&gt;

&lt;p&gt;Pick the model that performs in the harness. Own the harness. Measure the trajectory. The benchmark is not the product.&lt;/p&gt;

&lt;p&gt;The harness is the product.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
    </item>
    <item>
      <title>AI Agent Authentication Starts With Workload Identity | Focused Labs</title>
      <dc:creator>Austin Vance</dc:creator>
      <pubDate>Wed, 13 May 2026 14:55:56 +0000</pubDate>
      <link>https://dev.to/focused_dot_io/ai-agent-authentication-starts-with-workload-identity-focused-labs-418</link>
      <guid>https://dev.to/focused_dot_io/ai-agent-authentication-starts-with-workload-identity-focused-labs-418</guid>
      <description>&lt;p&gt;AI agent authentication starts when the system can answer which actor is allowed to make a tool call.&lt;/p&gt;

&lt;p&gt;The model can propose the action. The runtime has to attach authority to it.&lt;/p&gt;

&lt;p&gt;Most teams start with the fastest answer: an API key in an environment variable. The agent reaches Salesforce, GitHub, Jira, Snowflake, Stripe, whatever system makes the first useful proof feel real, and everyone moves on.&lt;/p&gt;

&lt;p&gt;That proof matters. It shows the agent can reach the systems where work actually happens. It also hides the first product decision: who is acting when the tool call leaves the runtime?&lt;/p&gt;

&lt;p&gt;The agent gets memory. The agent runs in the background. The agent forks into subagents. The agent retries failed operations. The agent calls tools after the user has walked away. The agent lands in an enterprise workflow where the work has value, the logs have value, and breaking something has a consequence.&lt;/p&gt;

&lt;p&gt;A shared API key starts as configuration. Then it quietly becomes the identity of the agent.&lt;/p&gt;

&lt;p&gt;An ugly place to stumble into by accident.&lt;/p&gt;

&lt;h2&gt;
  
  
  The secret becomes the actor
&lt;/h2&gt;

&lt;p&gt;Early security models for agents tend toward good vibes with a bearer token. The prompt gives instructions. The tool schema lists calls. Hard-coded secrets in the runtime decide what actually gets done based on the input, the agent, and whatever authority those secrets carry.&lt;/p&gt;

&lt;p&gt;The secret wins.&lt;/p&gt;

&lt;p&gt;The agent has all of those powers if the same key can read every customer record, submit refunds, update tickets, and write to production data. Carefulness in the prompt is theater at that point. The tool description can say those powers apply only when appropriate. The audit log will still show one credential able to perform a pile of different tasks.&lt;/p&gt;

&lt;p&gt;There is already a category for this outside agents: &lt;a href="https://owasp.org/www-project-non-human-identities-top-10/" rel="noopener noreferrer"&gt;OWASP's Non-Human Identities Top 10&lt;/a&gt;. Production applications identify themselves as non-human identities. Agents are adding themselves to that growing list of stranger workloads, running differently than normal services, but still requiring access to systems and data.&lt;/p&gt;

&lt;p&gt;The important step for me is naming the agent as a workload, because the architecture gets less magical and more useful.&lt;/p&gt;

&lt;p&gt;Workloads have identities. Workloads can request scoped credentials for those identities. A workload can be denied a credential. A workload can rotate credentials. A workload can leave an audit trail that survives the model, the prompt, and the v2 or v3 abstraction barrier the team is currently working around.&lt;/p&gt;

&lt;p&gt;Baseline authentication for production AI agents.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3ke2gp8x404se04fz457.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3ke2gp8x404se04fz457.png" alt="A runtime identity boundary showing an agent requesting scoped credentials from an identity broker before calling external systems." width="800" height="533"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;The runtime should issue tool-specific credentials instead of letting the agent carry a shared key everywhere.&lt;/p&gt;

&lt;h2&gt;
  
  
  Workload identity is the boring answer
&lt;/h2&gt;

&lt;p&gt;This part is old. Good.&lt;/p&gt;

&lt;p&gt;Kubernetes already considers service accounts to be identities of processes running in Pods, and the current docs describe &lt;a href="https://kubernetes.io/docs/concepts/security/service-accounts/" rel="noopener noreferrer"&gt;short-lived, automatically rotating ServiceAccount tokens&lt;/a&gt; issued through the TokenRequest API. SPIFFE generalizes that into workload identity documents, including &lt;a href="https://spiffe.io/docs/latest/spiffe-about/spiffe-concepts/" rel="noopener noreferrer"&gt;short-lived X.509 and JWT SVIDs&lt;/a&gt; that a workload can use to authenticate itself to other workloads.&lt;/p&gt;

&lt;p&gt;Cloud platforms are heading in the same general direction. AWS STS can &lt;a href="https://docs.aws.amazon.com/STS/latest/APIReference/API_AssumeRoleWithWebIdentity.html" rel="noopener noreferrer"&gt;issue temporary security credentials&lt;/a&gt; after a workload has identified itself using OpenID Connect. Google Cloud Workload Identity Federation allows external workloads to &lt;a href="https://cloud.google.com/iam/docs/workload-identity-federation" rel="noopener noreferrer"&gt;access Google Cloud resources without service account keys&lt;/a&gt;. Azure managed identity docs describe workload identities as &lt;a href="https://learn.microsoft.com/en-us/entra/identity/managed-identities-azure-resources/overview" rel="noopener noreferrer"&gt;machine and non-human identities&lt;/a&gt; associated with compute resources.&lt;/p&gt;

&lt;p&gt;The industry knows how to keep long-lived secrets out of the hot path. It just keeps giving agents interfaces that make the old mistake easy.&lt;/p&gt;

&lt;p&gt;A developer writes a tool wrapper. The tool wrapper needs credentials. The fastest way to configure it is to add an API key to an environment variable and add a TODO to remove it later. The TODO gets pushed to production because now the agent answers support tickets, reconciles invoices, or looks at CI.&lt;/p&gt;

&lt;p&gt;I've worked with teams who reviewed the model, tuned prompts, drew diagrams for tool selection, created a few secrets in deploy config, and crossed their fingers that the tool descriptions would shore it all up.&lt;/p&gt;

&lt;p&gt;They are not enough.&lt;/p&gt;

&lt;h2&gt;
  
  
  Delegation is the missing primitive
&lt;/h2&gt;

&lt;p&gt;In many applications, the agent should rarely hold the credential it uses to act.&lt;/p&gt;

&lt;p&gt;Put an identity assertion in the flow. This agent. This tenant. This user context if present. This policy version. This tool request. This approval state. That assertion is exchanged for a credential only when the action needs one.&lt;/p&gt;

&lt;p&gt;OAuth was designed to support exactly this shape. &lt;a href="https://www.rfc-editor.org/rfc/rfc8693" rel="noopener noreferrer"&gt;RFC 8693 defines token exchange&lt;/a&gt;, describing how one temporary credential can be exchanged for another temporary credential intended for a different context. In the agent case, the model proposes an action, the runtime checks policy, the broker issues a credential for that action and tool context, the call happens, and the credential dies.&lt;/p&gt;

&lt;p&gt;It does not expire after a quarter. It does not expire after someone remembers to rotate it. It expires because the system puts expiration in the path.&lt;/p&gt;

&lt;p&gt;That changes the damage pattern. A compromised tool wrapper no longer implies broad access to every downstream system. A prompt injection has to cross approval, run, tenant, and policy boundaries. A subagent that escapes its execution boundary cannot reuse credentials after the run, approval, or tenant context has expired.&lt;/p&gt;

&lt;p&gt;The agent is still useful. It just has to query through a production boundary that understands production concerns.&lt;/p&gt;

&lt;p&gt;This is why &lt;a href="https://focused.io/lab/2026-year-of-the-integrated-agent" rel="noopener noreferrer"&gt;integrated agents&lt;/a&gt; are valuable and dangerous at the same time. The valuable integrated agents do not live in a chatbot tab. They integrate with real systems. Once an agent is tied to real systems, authentication becomes product architecture rather than cleanup work hidden in deployment.&lt;/p&gt;

&lt;h2&gt;
  
  
  The runtime owns the identity boundary
&lt;/h2&gt;

&lt;p&gt;A model provider should not own this boundary. A prompt should not own this boundary. A tool schema should not own this boundary.&lt;/p&gt;

&lt;p&gt;The runtime owns it because the runtime follows the whole path.&lt;/p&gt;

&lt;p&gt;It connects agent definitions to threads or runs, tenants, and identity information, including the user who initiated the work, whether the work is backgrounded, whether a human approved a risky step, which tool is being called, and which downstream credential is being requested. It can attach those facts to an identity assertion and make a policy decision before any assertion leaves the process.&lt;/p&gt;

&lt;p&gt;That policy decision can be boring and explicit:&lt;/p&gt;

&lt;ul&gt;
&lt;li&gt;The refund tool can request a payment credential for the current tenant.&lt;/li&gt;
&lt;li&gt;A GitHub tool can request a write credential after CI has produced an eval pass.&lt;/li&gt;
&lt;li&gt;The Snowflake tool can request a read credential for one warehouse, one role, and one time window.&lt;/li&gt;
&lt;li&gt;A subagent can run with a delegated identity, but only with fewer capabilities than the parent run.&lt;/li&gt;
&lt;/ul&gt;

&lt;p&gt;The list is not impressive, which is why it is powerful.&lt;/p&gt;

&lt;p&gt;This is also where &lt;a href="https://focused.io/lab/multi-agent-orchestration-in-langgraph-supervisor-vs-swarm-tradeoffs-and-architecture" rel="noopener noreferrer"&gt;multi-agent orchestration&lt;/a&gt; gets serious. A supervisor handing work to a subagent creates a delegation relationship along with the task description. The child process needs enough authority to perform the work at hand and no more. The audit log must reflect that chain of trust cleanly or troubleshooting becomes an exercise in futility.&lt;/p&gt;

&lt;p&gt;The worst setup is a swarm of agents all sharing the same service account. Simple enough to get going. Terrible when it comes time to debug an incident. Every action has been performed by the same principal, authenticated with the same key, and observed through the same useless blur.&lt;/p&gt;

&lt;p&gt;The incident has no useful actor. Just a shared key with a long memory and no accountability.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3qaovc23fundj7hk9akt.png" class="article-body-image-wrapper"&gt;&lt;img src="https://media2.dev.to/dynamic/image/width=800%2Cheight=%2Cfit=scale-down%2Cgravity=auto%2Cformat=auto/https%3A%2F%2Fdev-to-uploads.s3.amazonaws.com%2Fuploads%2Farticles%2F3qaovc23fundj7hk9akt.png" alt="A token lifecycle showing an agent run creating an identity assertion, exchanging it for a scoped token, calling a tool, writing audit evidence, and expiring the credential." width="800" height="312"&gt;&lt;/a&gt;&lt;/p&gt;

&lt;p&gt;Short-lived delegated credentials make the agent run, policy decision, tool call, and audit trail line up.&lt;/p&gt;

&lt;h2&gt;
  
  
  Audit follows identity
&lt;/h2&gt;

&lt;p&gt;Agent observability without identity is half a story.&lt;/p&gt;

&lt;p&gt;A trace for the agent step called &lt;code&gt;refund_customer&lt;/code&gt; can include latency, tool arguments, model output, retries, all visualized in a convenient span tree. Useful. Then someone asks who had authority to issue that refund, and the trace turns into archaeological excavation.&lt;/p&gt;

&lt;p&gt;The right trace shows the tool call connected to a principal. Not just a service account. A principal with an agent ID, run ID, tenant, user context, policy decision, credential scope, and expiration time.&lt;/p&gt;

&lt;p&gt;This is what allows a team to answer questions after the tool call has done real work.&lt;/p&gt;

&lt;p&gt;Who granted access? What user context did it use? What broker generated the credential? What version of policy allowed it? What downstream resource accepted it? What subagent inherited it? Can that credential be used for something else?&lt;/p&gt;

&lt;p&gt;Those questions determine whether there is a real postmortem or just hand waving about the agent doing something weird.&lt;/p&gt;

&lt;p&gt;The same principle applies to testing. In &lt;a href="https://focused.io/lab/everybody-tests" rel="noopener noreferrer"&gt;Everybody Tests&lt;/a&gt;, I argued that every team already tests whether they admit it or not. Agent identity needs that same honesty. If a runtime can create delegated credentials, tests should verify that the boundary holds. A refund agent should fail against the wrong tenant. A code agent should fail when eval gates are red. A research agent should fail when it asks for write access to a system it only reads.&lt;/p&gt;

&lt;p&gt;Not a single &lt;code&gt;npx this and that&lt;/code&gt; in the whole codebase. Test it in CI.&lt;/p&gt;

&lt;h2&gt;
  
  
  Shared keys hide product decisions
&lt;/h2&gt;

&lt;p&gt;The fastest credential story hides the decisions that matter most.&lt;/p&gt;

&lt;p&gt;A shared key hides tenancy. It hides user context. It hides the identity of the agent performing an action. It hides which subagent inherited authority. It hides whether approval was granted. It hides whether the action matched the original request. It hides rotation until rotation becomes an outage.&lt;/p&gt;

&lt;p&gt;&lt;a href="https://cheatsheetseries.owasp.org/cheatsheets/Secrets_Management_Cheat_Sheet.html" rel="noopener noreferrer"&gt;OWASP's secrets management guidance recommends dynamic secrets where possible&lt;/a&gt; to reduce credential reuse and limit the damage when credentials leak. Agent systems need the same pressure, with the additional constraint that the credential must represent the run instead of only the application.&lt;/p&gt;

&lt;p&gt;A normal backend service is expected to behave predictably and follow a reliable lifecycle. It accepts requests, implements endpoints, and changes through controlled deployments. An agent runtime for integration automation can select different tools per request, execute work in subagents, retry steps, and continue running after initial user interaction has completed.&lt;/p&gt;

&lt;p&gt;So identity has to be more exact.&lt;/p&gt;

&lt;p&gt;The credential loaned to the system should assert what it is currently allowed to do. The operating policy should be visible enough to understand the motivation behind the action. The audit trail must persist long enough for a human to traverse the events as they happened.&lt;/p&gt;

&lt;p&gt;A boundary-based platform does not need a full rewrite. Start with one boundary.&lt;/p&gt;

&lt;p&gt;Put an identity broker between the agent runtime and the first high-risk tool. Give the agent runtime a workload identity. Have the broker exchange that identity for a tool credential. Associate the decision with tenant, run, and operation. Record the policy decision in the trace. Add a CI test that proves the wrong tenant fails. Expire the credential quickly. Make the failure visible when the broker returns no.&lt;/p&gt;

&lt;p&gt;Then move the next tool behind the boundary.&lt;/p&gt;

&lt;h2&gt;
  
  
  The production line
&lt;/h2&gt;

&lt;p&gt;AI agent authentication is the control plane for non-human actors who do work across systems.&lt;/p&gt;

&lt;p&gt;Ownership matters here. Security cannot retroactively add this after the agent and its resources have shipped. Platform cannot stash it in a vault path. Product cannot mark it as a checkbox in consent. Identity, delegation, expiration, and audit have to be inherent in the runtime of the agent and how it executes.&lt;/p&gt;

&lt;p&gt;The agent should actually be able to act. That is, after all, why we are doing &lt;a href="https://focused.io/lab/developing-ai-agency" rel="noopener noreferrer"&gt;AI agency&lt;/a&gt; in the first place. That agency should have a workload identity.&lt;/p&gt;

&lt;p&gt;Production systems have already worked out parts of the problem. Kubernetes, SPIFFE, OAuth token exchange, cloud workload federation, managed identities, dynamic secrets. They exist because static secrets rot and shared principal accounts make bad worse.&lt;/p&gt;

&lt;p&gt;It is a mistake to grant agents an exemption because the interface is conversational.&lt;/p&gt;

&lt;p&gt;The model can decide on the next step. The runtime decides whether that step gets a credential.&lt;/p&gt;

</description>
      <category>programming</category>
      <category>ai</category>
      <category>webdev</category>
    </item>
  </channel>
</rss>
