Varför många agentbaserade system fallerar i produktion — och hur du designar pålitliga agenter med tillståndsmaskiner, tydliga verktygskontrakt, omförsök och djup observabilitet.

Agentbaserade system är applikationer där en LLM inte bara svarar på en prompt, utan avgör vad som ska göras härnäst: vilka verktyg som ska anropas, vilken data som ska hämtas, vilka steg som ska köras och när den är "klar." De kombinerar en modell, en uppsättning verktyg (API:er, databaser, tjänster), en planerings-/exekveringsloop och infrastruktur som binder ihop allt.
I en demo ser detta magiskt ut: en agent kommer fram till en plan, anropar några verktyg och returnerar ett perfekt resultat. Den lyckade vägen är kort, latensen är låg och inget fallerar samtidigt.
Under verklig belastning utsätts samma agent för situationer demo-miljön aldrig såg:
Resultatet: fladdrigt beteende som är svårt att reproducera, tyst datakorruption och användarflöden som ibland fastnar eller loopar för evigt.
Ostabila agenter skadar mer än bara "upplevelse." De:
Den här texten handlar om ingenjörsmönster, inte "bättre prompts." Vi tittar på tillståndsmaskiner, explicita verktygskontrakt, retry- och felhanteringsstrategier, minnes‑ och samtidighetskontroll samt observabilitetsmönster som gör agentbaserade system förutsägbara under belastning — inte bara imponerande på scen.
De flesta agent‑system ser bra ut i ett enda happy‑path‑demo. De fallerar när trafik, verktyg och edge‑fall slår ihop sig.
Naiv orkestrering förutsätter att modellen "gör rätt" på ett eller två anrop. Under verklig användning ser du återkommande mönster:
Utan explicita tillstånd och slutvillkor är dessa beteenden oundvikliga.
LLM‑sampling, variabel latens och verktygs‑timing skapar dold icke‑determinism. Samma indata kan ta olika vägar, anropa olika verktyg eller tolka verktygsresultat olika.
I skala dominerar verktygsproblem:
Var och en av dessa leder till spökloopar, omförsök eller felaktiga slutliga svar.
Vad som sällan bryter vid 10 RPS kommer att gå sönder konstant vid 1 000 RPS. Samtidighet avslöjar:
Produktteam förväntar sig ofta deterministiska arbetsflöden, tydliga SLA:er och auditmöjligheter. Agenter, om de lämnas ostrukturerade, erbjuder probabilistiskt, best‑effort‑beteende med svaga garantier.
När arkitekturer ignorerar denna mismatch — genom att behandla agenter som traditionella tjänster istället för stokastiska planerare — beter sig systemen oförutsägbart just när tillförlitlighet betyder mest.
Produktionsredo agenter handlar mindre om "smarta prompts" och mer om disciplinerad systemdesign. Ett användbart sätt att tänka på dem är som små, förutsägbara maskiner som ibland kallar en LLM, inte som mystiska LLM‑klumpar som ibland rör dina system.
Fyra egenskaper spelar störst roll:
Du får inte dessa egenskaper bara från prompts. Du får dem från struktur.
Standardmönstret många team börjar med är: "while not done, call the model, let it think, maybe call a tool, repeat". Det är lätt att prototypa och svårt att drifta.
Ett säkrare mönster är att representera agenten som ett explicit arbetsflöde:
COLLECTING_INPUT, PLANNING, EXECUTING_STEP, WAITING_ON_HUMAN, DONE).Detta omvandlar agenten till en tillståndsmaskin där varje steg är inspekterbart, testbart och återskapbart. Fri‑form‑loopar känns flexibla, men explicita arbetsflöden är vad som gör incidenter felsökbara och beteende auditerbart.
Monolitiska agenter som "gör allt" är lockande, men de skapar tät koppling mellan orelaterade ansvarsområden: planering, retrieval, affärslogik, UI‑orkestration med mera.
I stället, komponera små, välavgränsade agenter eller skills:
Varje skill kan ha sin egen tillståndsmaskin, verktyg och säkerhetsregler. Komponeringslogiken blir då ett högre nivåarbetsflöde, inte en ständigt växande prompt inuti en enda agent.
Denna modularitet håller varje agent tillräckligt enkel för att resonera om och låter dig vidareutveckla en kapacitet utan att destabilisera resten.
En användbar mental modell är att dela en agent i tre lager:
Beslutspolicy (LLM‑prompts + modell)
Innesluter hur agenten väljer nästa åtgärd, tolkad under strikta begränsningar. Du ska kunna byta modell, justera temperatur eller förfina prompts utan att röra systemets kopplingar.
Tillståndsmaskin / workflow‑motor
Äger var du befinner dig i processen, vilka övergångar som är möjliga och hur man persisterar framsteg. Policyn föreslår ett drag; tillståndsmaskinen validerar och applicerar det.
Verktygsskikt
Implementerar vad som faktiskt kan hända i världen: API:er, databaser, köer, externa tjänster. Verktyg exponerar smala, vältypade kontrakt och upprätthåller auktorisation, rate limits och indata‑validering.
Genom att upprätthålla denna separation undviker du fällan att gömma affärslogik i prompts eller verktygsbeskrivningar. LLM blir en beslutskomponent inuti ett tydligt, deterministiskt hölje — inte höljet självt.
De mest pålitliga agentbaserade systemen är inte de mest imponerande demona — det är de vars beteende du kan förklara på en whiteboard.
Konkreta råd:
Denna förkärlek för små, komponerbara och väldefinierade agenter är vad som låter system växa utan att kollapsa under sin egen komplexitet.
De flesta agent‑implementationer börjar som en loop av "tänk, handla, observera" runt ett LLM‑anrop. Det är okej för demos, men det blir snabbt ogenomskinligt och sprött. Ett bättre angreppssätt är att behandla agenten som en explicit tillståndsmaskin: en ändlig uppsättning tillstånd med väl definierade övergångar som triggas av händelser.
Istället för att låta modellen implicit avgöra vad som ska göras härnäst, definiera ett litet tillståndsdiagram:
Övergångar mellan dessa tillstånd triggas av typade händelser såsom UserRequestReceived, ToolCallSucceeded, ToolValidationFailed, TimeoutExceeded eller HumanOverride. Varje händelse, plus det aktuella tillståndet, bestämmer nästa tillstånd och åtgärder.
Detta gör omförsök och timeouter okomplicerade: du fäster policyer på individuella tillstånd (t.ex. CALL_TOOL får omförsök 3 gånger med exponentiell backoff, PLAN kanske inte får omförsök alls) istället för att sprida retry‑logik över hela kodbasen.
Persistiera det aktuella tillståndet och minimal kontext i en extern lagring (databas, kö eller workflow‑motor). Agenten blir då en ren funktion:
next_state, actions = transition(current_state, event, context)
Detta möjliggör:
Med en tillståndsmaskin är varje steg i agentens beteende explicit: vilket tillstånd den var i, vilken händelse som inträffade, vilken övergång som triggades och vilka sidoeffekter som producerades. Den klarheten gör felsökning snabbare, förenklar incidentutredningar och skapar ett naturligt revisionsspår för compliance‑granskningar. Du kan bevisa, från loggar och tillståndshistorik, att vissa riskfyllda åtgärder enbart tas från specifika tillstånd och under definierade förutsättningar.
Agenter beter sig mycket mer förutsägbart när verktyg ser mindre ut som "API:er gömda i prosa" och mer som väldesignade gränssnitt med explicita garantier.
Varje verktyg bör ha ett kontrakt som täcker:
InvalidInput, NotFound, RateLimited, TransientFailure) med klar semantik.Exponera detta kontrakt för modellen som strukturerad dokumentation, inte som en lång textmassa. Agentens planner bör veta vilka fel som är omförsökningsbara, vilka som kräver mänsklig intervention och vilka som ska stoppa arbetsflödet.
Behandla verktygs I/O som vilket annat produktions‑API som helst:
Detta låter dig förenkla prompts: istället för långa instruktioner, förlita dig på schema‑driven vägledning. Tydliga begränsningar minskar hallucinationer och osammanhängande verktygskedjor.
Verktyg utvecklas; agenter bör inte gå sönder varje gång det sker.
v1, v1.1, v2) och peka agenter mot en version.Planeringslogik kan då tryggt kombinera agenter och verktyg i olika mognadsnivåer.
Designa kontrakt med partiella fel i åtanke:
Agenten kan då anpassa sig: fortsätta arbetsflödet med reducerad funktionalitet, be användaren om bekräftelse eller byta till ett fallback‑verktyg.
Verktygskontrakt är en naturlig plats att koda säkerhetsgränser:
confirm: true).Kombinera detta med server‑side‑kontroller; lita aldrig enbart på modellen att "bete sig".
När verktyg har klara, validerade, versionerade kontrakt kan prompts bli kortare, orkestreringslogik enklare och felsökning mycket lättare. Du flyttar komplexitet från bräckliga naturliga språk‑instruktioner till deterministiska scheman och policys, vilket minskar hallucinerade verktygsanrop och oväntade sidoeffekter.
Pålitliga agentbaserade system antar att allt förr eller senare kommer att misslyckas: modeller, verktyg, nätverk eller till och med din egen koordinationslogik. Målet är inte att undvika fel, utan att göra dem billiga och säkra.
Idempotens betyder: att upprepa samma begäran ger samma externt synliga effekt som att göra den en gång. Detta är kritiskt för LLM‑agenter som ofta skickar om verktygsanrop efter partiella fel eller otydliga svar.
Gör verktyg idempotenta från början:
request_id. Verktyget lagrar detta och returnerar samma resultat om det ser samma ID igen.Använd strukturerade omförsök för övergående fel (timeouts, rate limits, 5xx): exponentiell backoff, jitter för att undvika thundering herds och strikt maxantal försök. Logga varje försök med korrelations‑ID så du kan spåra agentbeteende.
För permanenta fel (4xx, valideringsfel, affärsregelavsteg) omförsökas inte. Presentera ett strukturerat fel för agentens policy så den kan revidera planen, fråga användaren eller välja ett annat verktyg.
Implementera circuit breakers både på agent‑ och verktygsnivå: efter upprepade fel blockera anrop till det verktyget tillfälligt och fail‑fast. Kombinera detta med väl definierade fallback‑lägen: degraderade svar, cacheade data eller alternativa verktyg.
Undvik blinda omförsök i agentloopen. Utan idempotenta verktyg och tydliga felklasser multiplicerar du bara sidoeffekter, latens och kostnad.
Pålitliga agenter börjar med klarhet kring vad som är tillstånd och var det bor.
Behandla en agent som en tjänst som hanterar en förfrågan:
Att blanda dessa leder till förvirring och buggar. Till exempel gör det att sätta flyktiga verktygsresultat i "minnet" att agenter återanvänder föråldrad kontext i framtida samtal.
Du har tre huvudalternativ:
En bra regel: LLM är en stateless funktion över ett explicit tillståndsobjekt. Persistiera det objektet utanför modellen och återskapa prompts från det.
Ett vanligt fel är att använda konversationsloggar, spår eller råa prompts som memory.
Problem:
Definiera i stället strukturerade minnesscheman: user_profile, project, task_history osv. Härled loggar från tillstånd, inte tvärtom.
När flera verktyg eller agenter uppdaterar samma entiteter (t.ex. ett CRM‑record eller en uppgiftsstatus) behöver du grundläggande konsistenskontroller:
För högt värde‑operationer, logga en beslutslogg separat från konversationsloggen: vad ändrades, varför och baserat på vilka inputs.
För att överleva krascher, deploys och rate limiting bör arbetsflöden vara återupptagbara:
Detta möjliggör också time travel‑felsökning: du kan inspektera och återköra exakt det tillstånd som ledde till ett dåligt beslut.
Minne är lika mycket en risk som en tillgång. För produktionsagenter:
Behandla minne som en produktfunktion: designad, versionerad och styrd — inte bara en ständigt växande textdump fäst vid din agent.
Agenter ser sekventiella ut på whiteboarden men beter sig som distribuerade system under verklig belastning. Så fort du har många samtidiga användare, verktyg och bakgrundsjobb jonglerar du race conditions, dubbla körningar och ordningsproblem.
Vanliga fel:
Du mildrar dessa med idempotenta verktygskontrakt, explicit arbetsflödestillstånd och optimistisk eller pessimistisk låsning i datalagret.
Synkrona request–response‑flöden är enkla men sköra: varje beroende måste vara uppe, inom rate limits och snabbt. När agenter sprider ut sig till många verktyg eller parallella deluppgifter, flytta långkörande eller sidoeffektiva steg bakom en kö.
Köbaserad orkestrering låter dig:
Agenter träffar typiskt tre slags begränsningar:
Du behöver ett explicit rate‑limit‑lager med per‑användare, per‑tenant och globala throttles. Använd token buckets eller leaky buckets för att upprätthålla policyer, och exponera tydliga feltyper (t.ex. RATE_LIMIT_SOFT, RATE_LIMIT_HARD) så agenter kan backa av graciöst.
Backpressure är hur systemet skyddar sig själv under stress. Strategier inkluderar:
Monitorera mättnadssignaler: ködjup, worker‑utnyttjande, modell/verktygs‑felräntor och latenser percentiler. Stigande ködjup kombinerat med ökande latens eller 429/503 är tidiga varningar om att agenter överbelastar sin miljö.
Du kan inte göra en agent pålitlig om du inte snabbt kan besvara två frågor: vad gjorde den? och varför gjorde den så? Observabilitet för agentbaserade system handlar om att göra de svaren billiga och precisa.
Designa observabilitet så att en enskild task har ett trace som löper igenom:
I det spåret bifogar du strukturerade loggar för viktiga beslut (routningsval, planrevisioner, guardrail‑triggers) och mätvärden för volym och hälsa.
Ett användbart trace innehåller vanligtvis:
Logga prompts, verktygsin‑ och utdata i strukturerad form, men låt dem passera genom ett redaction‑lager först:
Behåll rått innehåll bakom feature‑flaggor i lägre miljöer; produktion bör som standard visa redigerade vyer.
Minst bör du spåra:
När incidenter händer låter bra traces och mätvärden dig gå från "agenten känns ostadig" till en exakt formulering som: "P95‑tasks misslyckas i ToolSelection efter 2 omförsök på grund av nytt schema i billing_service," vilket kortar diagnostid från timmar till minuter och ger konkreta handtag för åtgärd.
Att testa agenter betyder att testa både verktygen de kallar och flödena som binder ihop allt. Behandla det som distribuerade system‑tester, inte bara prompt‑tinkering.
Börja med enhetstester vid verktygsgränsen:
Dessa tester beror aldrig på LLM. Du kallar verktyget direkt med syntetiska inputs och assertar exakt utdata eller felkontrakt.
Integrationstester testar agentens arbetsflöde end‑to‑end: LLM + verktyg + orkestration.
Modellera dem som scenario‑baserade tester:
Dessa tester asserterar tillståndsövergångar och verktygsanrop, inte varje token i LLM:s text. Kolla: vilka verktyg anropades, med vilka argument, i vilken ordning och vilket slutligt tillstånd/resultat agenten nådde.
För att hålla tester repeterbara, fixture:a både LLM‑svar och verktygsutdata.
Ett typiskt mönster:
with mocked_llm(fixtures_dir="fixtures/llm"), mocked_tools():
result = run_agent_scenario(input_case)
assert result.state == "COMPLETED"
Varje prompt‑ eller schemaändring bör trigga en icke‑förhandlingsbar regressionskörning:
Schema‑evolution (lägga till fält, snäva typer) får egna regressionsfall för att fånga agenter eller verktyg som fortfarande antar gammalt kontrakt.
Skicka aldrig ny modell, policy eller routing‑strategi direkt till produktions‑trafik.
I stället:
Först efter att ha passerat offline‑grindar bör en ny variant nå produktion, helst bakom feature flags och gradvis rollout.
Agentloggar innehåller ofta känslig användardata. Testning måste respektera det.
Kodifiera dessa regler i din CI‑pipeline så inget testartifact kan genereras eller sparas utan anonymiseringskontroller.
Att drifta agenter i produktion liknar mer att köra ett distribuerat system än att leverera en statisk modell. Du behöver kontroller för rollout, tydliga tillförlitlighetsmål och disciplinär förändringshantering.
Inför nya agenter eller beteenden gradvis:
Stöd allt detta med feature flags och konfigurationsstyrda policyer: routningsregler, aktiverade verktyg, temperatur, säkerhetsinställningar. Ändringar bör vara konfigurerbara, inte kodändringar, och omedelbart återställbara.
Definiera SLO:er som speglar både systemhälsa och användarvärde:
Koppla dessa till larm och hantera incidenter som för andra produktions‑tjänster: tydligt ansvar, runbooks för triage och standardiserade mildringssteg (rollback‑flagga, trafikdränering, safe‑mode‑beteende).
Använd loggar, spår och konversationstranskript för att förfina prompts, verktyg och policys. Behandla varje ändring som en versionerad artefakt med granskning, godkännande och rollback‑kapacitet.
Undvik tysta prompt‑ eller verktygsändringar. Utan förändringskontroll kan du inte korrelera regressioner till specifika ändringar, och incidentrespons blir gissningslek istället för ingenjörsarbete.
Ett produktionsredo agentsystem gynnas av tydlig separation av ansvar. Målet är att hålla agenten smart i beslut, men dum i infrastruktur.
1. Gateway / API‑edge
En enda ingångspunkt för klienter (appar, tjänster, UI). Den hanterar:
2. Orkestrator
Orkestratorn är "hjärnstammen", inte hjärnan. Den koordinerar:
LLM(s) lever bakom orkestratorn, använda av planner och av specifika verktyg som behöver språkförståelse.
3. Verktyg och lagringslager
Affärslogik stannar i befintliga mikrotjänster, köer och datasystem. Verktyg är tunna wrappers runt:
Orkestratorn anropar verktyg via strikta kontrakt, medan lagringssystemen förblir sanningskällan.
Upprätthåll auth och kvoter i gateway; upprätthåll säkerhet, dataåtkomst och policy i orkestratorn. Alla anrop (LLM och verktyg) emitterar strukturerad telemetri till en pipeline som matar:
En enklare arkitektur (gateway → single orchestrator → verktyg) är lättare att drifta; att lägga till separata planners, policy‑motorer och modellgateways ökar flexibilitet på bekostnad av mer koordination, latens och driftkomplexitet.
Du har nu kärningredienserna för agenter som beter sig förutsägbart under verklig belastning: explicita tillståndsmaskiner, tydliga verktygskontrakt, disciplinerade omförsök och djup observabilitet. Sista steget är att göra dessa idéer till en repeterbar praxis i ditt team.
Tänk på varje agent som ett tillståndsfullt arbetsflöde:
När dessa delar linjerar får du system som degraderar graciöst istället för att kollapsa vid edge‑fall.
Innan du skickar en prototypagent till riktiga användare, bekräfta:
Om något saknas är ni fortfarande i prototyp‑läge.
En hållbar uppsättning skiljer ofta:
Detta låter produktteam röra sig snabbt medan plattforms‑team säkerställer tillförlitlighet, säkerhet och kostnadskontroll.
När du har stabil grund kan du utforska:
Gör framsteg inkrementellt: introducera nya lärandekomponenter bakom feature‑flags, med offline‑utvärdering och starka guardrails.
Temat genom allt detta är detsamma: designa för fel, prioritera tydlighet framför finess, och iterera där du kan observera och rulla tillbaka säkert. Med dessa begränsningar på plats slutar agentbaserade system vara skrämmande prototyper och blir infrastruktur din organisation kan lita på.
Ett agentbaserat system är en applikation där en LLM inte bara svarar på ett enda prompt utan avgör vad som ska göras härnäst: vilka verktyg som ska anropas, vilken data som ska hämtas, vilket steg i ett arbetsflöde som ska köras och när det ska stoppas.
Till skillnad från en enkel chattkomplettering kombinerar ett agentbaserat system:
I produktion blir LLM en av flera beslutskomponenter inuti ett större, deterministiskt skal—inte hela systemet.
Demo-miljöer kör oftast en enda "happy path": en användare, idealiskt beteende från verktyg, inga timeouts, ingen schema-drift och korta konversationer. I produktion möter agenter:
Utan explicita arbetsflöden, kontrakt och felhantering uppstår loopar, fastkörningar, ofullständigt arbete och tysta fel som aldrig syns i demos.
Få LLM:s bete sig i ett klart ramverk istället för i en fri loop:
Modellera agenten som ett arbetsflöde med namngivna tillstånd och typade händelser istället för while not done: call LLM.
Typiska tillstånd kan vara:
Designa verktyg som riktiga produktions-API:er, inte som löst formulerade beskrivningar i prompts. Varje verktyg bör ha:
Anta att varje extern anrop ibland kommer att misslyckas och designa därefter.
Viktiga mönster:
Separera korttids‑tillstånd från långtidsminne, och håll LLM:en stateless.
Undvik att använda råa loggar eller full konversationshistorik som "minne"; härled istället kompakta, strukturerade poster med tydliga retentions- och sekretessregler.
Tänk på ditt agentsystem som ett distribuerat system under belastning, även om varje flöde verkar sekventiellt.
För att vara tillförlitlig:
Du behöver kunna svara på "vad gjorde agenten?" och "varför gjorde den så?" för vilken uppgift som helst.
Praktiska krav:
Behandla agenter som utvecklande tjänster, inte statiska prompts, och hantera dem med samma disciplin som andra produktionssystem.
Rekommenderade rutiner:
Detta låter dig förklara, testa och felsöka beteende steg för steg i stället för att jaga opaka "agenttankar".
PLAN – tolka förfrågan och skapa en steg-för-steg-planCALL_TOOL – anropa ett specifikt verktyg eller en batch verktygVERIFY – kontrollera utdata mot enkla invariantar eller sekundära modellkontrollerRECOVER – hantera fel genom omförsök, fallback eller eskaleringDONE / FAILED – terminala utfallHändelser (t.ex. ToolCallSucceeded, TimeoutExceeded) tillsammans med det aktuella tillståndet bestämmer nästa tillstånd. Det gör omförsök, timeouter och felhantering explcita istället för dolda i prompts eller limkod.
InvalidInput, NotFound, RateLimited, TransientFailureValidera indata innan anropet och utdata efteråt. Versionera verktygskontrakt och peka agenter mot en specifik version så schemaändringar inte bryter flöden tyst.
request_id eller affärsnyckel och returnerar samma resultat om de ser samma ID igen.Detta håller tillförlitligheten hög utan att orsaka runaway-loopar, dubbla sidoeffekter eller okontrollerade kostnader.
Övervaka ködjup, latenser och andel 429/503 för att fånga överbelastning innan det blir ett driftstopp.
Med detta förflyttas incidenttriage från "agenten känns ostadig" till att peka på exakt tillstånd, verktyg och förändring som orsakade regressionen.
Detta låter dig förbättra agenter kontinuerligt samtidigt som fel hålls begränsade, diagnostiserbara och återskapbara.