Agentes de LangChain: guía técnica completa para 2026

20 de junio de 2026
14 min de lectura

20 de junio de 2026
14 min de lectura
Agentes de LangChainHover to exploreUn LLM que responde preguntas es útil. Un LLM que puede hacer cosas —consultar tu base de datos, enviar un mensaje a Slack, tramitar un reembolso y después contarte qué ha hecho— es un producto. Los agentes de LangChain son la forma estándar de montar ese bucle en 2026. Esta guía recorre todo el camino, del modelo mental al código de producción: el bucle del agente, cómo escribir herramientas, memoria y estado, salida estructurada, streaming, gestión de errores y qué funciona (y qué no) según r/LangChain, r/LocalLLaMA y la comunidad de X.
Esta guía se apoya en la documentación de agentes de LangChain v1, la documentación de LangGraph y en las discusiones recurrentes de r/LangChain y @LangChainAI en X.
Todos los agentes de LangChain ejecutan el mismo bucle, sea cual sea el modelo:
ToolMessage.Eso es todo. La sofisticación está en qué herramientas ofreces y en cómo acotas el bucle, no en ninguna magia interna del framework.
Con create_agent de LangChain v1 apenas hay código repetitivo:
from langchain.agents import create_agent
from langchain.tools import tool
@tool
def search_orders(order_id: str) -> str:
"""Look up an order by ID and return its current status."""
# Replace with your real DB call
return f"Order {order_id}: Shipped, arriving 2026-06-23."
@tool
def issue_refund(order_id: str, reason: str) -> str:
"""Issue a full refund for an order given a reason."""
return f"Refund issued for order {order_id}. Reason: {reason}."
agent = create_agent(
model="anthropic:claude-sonnet-4-6",
tools=[search_orders, issue_refund],
system_prompt=(
"You are a helpful customer support agent. "
"Always look up the order before issuing a refund."
),
)
result = agent.invoke({
"messages": [{"role": "user", "content": "Refund order #4821 — it arrived broken."}]
})
print(result["messages"][-1].content)
Por debajo, el agente llama a search_orders("4821"), lee el resultado, llama a issue_refund("4821", "arrived broken") y devuelve la confirmación al usuario. Todo dentro de una sola llamada a invoke, sin orquestación manual.
Lo que más influye en la calidad de un agente es el diseño de las herramientas, no la elección del modelo. El modelo decide a cuál llamar basándose únicamente en el nombre de la función, el docstring y el esquema de argumentos. Si eso está mal planteado, no hay prompt que lo arregle.
Reglas que se cumplen en la práctica:
search_and_refund() es una trampa: sepárala. El modelo debe poder invocar cada paso por separado."Error: order not found" en lugar de lanzar una excepción: así el agente puede reintentar o explicar el fallo en vez de romperse.from langchain.tools import tool
from pydantic import BaseModel, Field
class SearchInput(BaseModel):
order_id: str = Field(description="The numeric order ID, e.g. '4821'")
include_history: bool = Field(
default=False,
description="Set True to include the full shipment history"
)
@tool(args_schema=SearchInput)
def search_orders(order_id: str, include_history: bool = False) -> str:
"""
Look up an order's current status by order ID.
Call this FIRST before any action that modifies the order.
Returns: status string, or an error message if not found.
"""
try:
order = db.get_order(order_id)
if not order:
return f"Error: order {order_id} not found."
base = f"Order {order_id}: {order.status}, ETA {order.eta}."
if include_history:
base += f" History: {order.shipment_history}"
return base
except Exception as e:
return f"Error fetching order: {str(e)}"
Por defecto, cada llamada a agent.invoke() es sin estado: el agente olvida el turno anterior en cuanto termina. Para conversaciones de varios turnos hay que pasar el estado de forma explícita. LangChain ofrece dos patrones:
Patrón A: checkpointing por hilo con LangGraph (recomendado en producción)
from langchain.agents import create_agent
from langgraph.checkpoint.memory import MemorySaver
# MemorySaver keeps state in RAM; swap for PostgresSaver in production
checkpointer = MemorySaver()
agent = create_agent(
model="anthropic:claude-sonnet-4-6",
tools=[search_orders, issue_refund],
checkpointer=checkpointer,
)
# Same thread_id = same conversation memory
config = {"configurable": {"thread_id": "user-123-session-456"}}
# Turn 1
agent.invoke(
{"messages": [{"role": "user", "content": "What is the status of order 4821?"}]},
config=config,
)
# Turn 2 — agent remembers turn 1
agent.invoke(
{"messages": [{"role": "user", "content": "Go ahead and refund it."}]},
config=config,
)
Patrón B: resumen automático para contextos largos
Cuando un hilo supera la ventana de contexto del modelo, SummarizationMiddleware comprime los mensajes antiguos en un resumen acumulado antes de cada llamada. El agente pierde el histórico literal pero conserva el sentido, suficiente para la mayoría de casos de soporte o asistencia.
A menudo quieres que el agente recopile información y devuelva un objeto validado, no un resumen en texto libre. Pasa un modelo de Pydantic a response_format y el agente emitirá un objeto tipado dentro del mismo bucle, sin ningún paso extra de parseo:
from pydantic import BaseModel
from langchain.agents import create_agent
class SupportTicket(BaseModel):
order_id: str
issue_type: str # "refund" | "late_delivery" | "wrong_item"
recommended_action: str
confidence: float # 0.0 – 1.0
agent = create_agent(
model="anthropic:claude-sonnet-4-6",
tools=[search_orders],
response_format=SupportTicket,
system_prompt=(
"Classify the customer's issue and recommend an action. "
"Always search the order before classifying."
),
)
result = agent.invoke({"messages": [
{"role": "user", "content": "My order 4821 never arrived — it's been 3 weeks."}
]})
ticket: SupportTicket = result["structured_response"]
print(ticket.issue_type) # "late_delivery"
print(ticket.recommended_action) # "escalate to carrier"
print(ticket.confidence) # 0.92
El mayor problema de experiencia de usuario en un agente es la latencia: quien lo usa no ve nada hasta que termina el bucle completo. El streaming lo resuelve mostrando tokens y eventos de herramientas según se producen. LangChain admite dos modos:
# Mode 1 — stream final output tokens only
for chunk in agent.stream(
{"messages": [{"role": "user", "content": "Status of order 4821?"}]},
stream_mode="messages",
):
if chunk[1].get("langgraph_node") == "agent":
print(chunk[0].content, end="", flush=True)
# Mode 2 — stream every event (tool calls, results, tokens)
for event in agent.stream(
{"messages": [{"role": "user", "content": "Status of order 4821?"}]},
stream_mode="updates",
):
kind = list(event.keys())[0]
if kind == "tools":
print(f"[tool] {event['tools']['messages'][0].name}")
elif kind == "agent":
for msg in event["agent"]["messages"]:
print(msg.content, end="", flush=True)
En la práctica, usa stream_mode="updates" en cualquier interfaz con un panel de «pensando» en vivo: permite mostrar qué herramienta está llamando el agente sin esperar a la respuesta final.
Cualquier agente capaz de gastar dinero, enviar un mensaje o escribir en una base de datos necesita una aprobación humana para las acciones irreversibles. LangChain v1 ofrece dos vías: middleware para los casos sencillos e interrupciones de LangGraph cuando necesitas control total.
# Simple approach — middleware
from langchain.agents.middleware import HumanInTheLoopMiddleware
agent = create_agent(
model="anthropic:claude-sonnet-4-6",
tools=[search_orders, issue_refund, send_email],
middleware=[
HumanInTheLoopMiddleware(
interrupt_on={"issue_refund": True, "send_email": True}
)
],
)
# Advanced approach — LangGraph interrupt node
from langgraph.types import interrupt
def human_approval_node(state):
last_tool_call = state["messages"][-1]
# Pause execution and surface the tool call to your UI
decision = interrupt({
"tool": last_tool_call.name,
"args": last_tool_call.tool_input,
"prompt": "Approve this action?",
})
if decision["approved"]:
return state # continue
# Inject a rejection message back into the graph
return {"messages": [ToolMessage(content="Action rejected by user.", ...)]}
El middleware se implementa antes. La interrupción de LangGraph es más flexible: permite modificar los argumentos, no solo aprobar o rechazar. En proyectos con clientes casi siempre empezamos con middleware y solo pasamos a las interrupciones cuando hay que dejar que el usuario edite la llamada antes de ejecutarla.
Esta distinción confunde a mucha gente. En LangChain de 2022–2023, ReAct (Reason + Act) era el patrón principal: se pedía al modelo que escribiera un bloc de notas «Thought / Action / Observation» en texto plano, que LangChain parseaba para saber qué invocar. Funcionaba, pero era frágil: cualquier desviación del formato rompía el parser.
En 2026, create_agent usa tool calling nativo: el modelo emite la llamada estructurada en la respuesta de la API, no en texto libre. Es más fiable, más barato (no hay doble prompt) y está soportado por todos los grandes proveedores. ReAct queda como alternativa para modelos sin tool calling nativo, no como camino por defecto.
| Característica | ReAct (heredado) | Tool calling nativo (por defecto en v1) |
|---|---|---|
| Formato | Bloc de notas en texto libre | Respuesta estructurada de la API |
| Fiabilidad | Sensible al formato | Validado contra esquema |
| Llamadas en paralelo | No | Sí (donde el proveedor lo admite) |
| Ideal para | Modelos locales sin tool calling | Todo lo demás |
LANGSMITH_API_KEY y LANGSMITH_TRACING=true. Cada invoke, cada llamada a herramienta y cada token quedan trazados automáticamente. Lo agradecerás a las dos de la madrugada, cuando algo se rompa en producción.MemorySaver sirve para desarrollo local, pero cámbialo por PostgresSaver o RedisSaver antes de salir a producción: si no, un reinicio del servidor borra todo el estado conversacional.Tras leer meses de hilos en r/LangChain, r/LocalLLaMA y los rincones de ingeniería de IA de X, la opinión de la comunidad se resume en estos temas recurrentes:
langchain / langchain-core / langgraph) sigue despistando a quien empieza». El propio equipo de LangChain lo reconoce. El modelo mental es más limpio en v1, pero la instalación sigue haciendo tropezar la primera vez.«La pregunta en 2026 no es "¿debería usar LangChain?". Es "¿necesito checkpointing, observabilidad y tool calling portable entre proveedores, o tengo un solo proveedor, tres pasos y me basta con una llamada directa?". Ten claro cuál es tu problema antes de elegir framework.»
Los agentes de LangChain son la opción correcta cuando necesitas al menos dos de estas cosas:
Recurre al SDK del proveedor cuando:
Los agentes de LangChain en 2026 ya no son un juguete de tutorial. Con create_agent, tool calling nativo, estado con checkpoints, salida estructurada, streaming y middleware, el framework cubre toda la superficie de lo que necesita un agente en producción. La curva de aprendizaje existe —sobre todo en el diseño de herramientas y en el modelo de checkpoints de LangGraph—, pero a cambio obtienes un agente que puedes observar, pausar, ceder a una persona y migrar a otro modelo sin reescribir el código. Es una base sólida para cualquier MVP con IA.

IdeaToMVP Academy
4-week live cohort for founders. Learn to ship AI agents, scope MVPs, and automate your business — taught by the same team that writes these guides.