Para agentes de IA: hay un índice de documentación disponible en https://www.mongodb.com/es/docs/llms.txt — versiones en markdown de todas las páginas están disponibles agregando .md a cualquier ruta URL.
See how MongoDB 9.0 delivers up to 2x higher throughput.
MongoDB Branding Shape
Register now >
Docs Menu

gráfico de lenguaje del SDK del motor del agente

Un SDK de LangChain para MongoDB Atlas Agent Engine. Proporciona una capa de abstracción ligera específica de LangChain sobre el entorno de ejecución de la plataforma agent-engine-runner-shared.

pip install agent-engine-sdk-langgraph

O en un proyecto UV:

uv add agent-engine-sdk-langgraph
from agent_engine_sdk_langgraph import App
from langgraph.graph import StateGraph, MessagesState
from langgraph.prebuilt import ToolNode
app = App(app_name="my-agent", app_version="1.0.0")
@app.tool()
def lookup(query: str) -> str:
"""Search the knowledge base."""
return "result for " + query
@app.entrypoint
def build_agent():
from langchain_openai import ChatOpenAI
llm = app.llm(ChatOpenAI(model="gpt-5.4"))
tools = app.get_tools()
def call_model(state: MessagesState):
response = llm.invoke(state["messages"])
return {"messages": [response]}
graph = StateGraph(MessagesState)
graph.add_node("agent", call_model)
graph.add_node("tools", ToolNode(tools))
graph.set_entry_point("agent")
graph.add_edge("tools", "agent")
return graph.compile(checkpointer=app.checkpointer())
app.run()

app.memory es la fachada unificada `agent-engine-sdk-memory <../agent-engine-sdk-memory/README.md>`__ Memory (vinculada a la aplicación sobre el entorno de ejecución de la plataforma). La identidad se resuelve por llamada desde el argumento, un contexto vinculado o el contexto de ejecución ambiental.

app = App(app_name="my-agent")
# Save a semantic fact — returns CreateSemanticResult
result = app.memory.save_semantic(
text="User prefers dark mode",
label="pref-theme",
user_id="u1",
metadata={"channel": "web", "priority": "high"}, # optional caller-supplied metadata
)
if result.acknowledged:
...
# Search — returns list[MemoryChunk]
chunks = app.memory.search_semantic(query="user preferences", user_id="u1")
for chunk in chunks:
print(chunk.content)
# Build prompt context — returns ContextResponse
# Default sources are LTM (episodic + semantic); pass
# enabled_sources={"stm", ...} to include recent turns.
context = app.memory.build_context(query="help me", user_id="u1")
prompt_block = context.formatted_context # str (or structured list, depending on format)

build_context_from_sources (modos de recuperación por fuente, filtros y top_k) está disponible en el entorno de ejecución app.memory. Devuelve el ContextResponse completo, por lo que los metadatos por fuente (ranking_strategy, source_outcomes) se conservan; la plataforma registra la tenencia y lleva la respuesta de vuelta a través de la ejecución duradera. session_id solo se requiere cuando se solicita la fuente stm.

from agent_engine_sdk_langgraph import Memory Reexporta la misma clase que agent_engine_sdk_memory.Memory. Construir Memory(api_key=...) / Memory(base_url=...) usted mismo es la ruta HTTP/directa, no está limitada a la aplicación ambiental.

Cuando esto se rompa

Se trata de una modificación drástica: no existe una API dual ni un adaptador de compatibilidad en app.memory. Los agentes de cliente solo fallan al reconstruir una imagen de agente que incluye paquetes wheel basados ​​en el ejecutor con este SDK. La fusión de plataformas o la redistribución de una imagen de agente antigua no modifican el código SDK ya integrado en dicha imagen. No se produce ninguna migración de datos en memoria; solo cambian las formas de retorno del cliente y las convenciones de llamada.

Migrando desde la superficie de la prefachada

  • Tipos de retorno / veracidad / metadatos / ``build_context``: escribe resultados con tipo de retorno (CreateSemanticResult, CreateEpisodicResult, etc.) con acknowledged — no con bool/dicts sin formato. Prefiere if result.acknowledged: (no if result: — los modelos Pydantic siempre son veraces). Las búsquedas de similitud devuelven list[MemoryChunk] (chunk.content, opcional chunk.similarity_score). Los campos sueltos que solían ser claves de diccionario de nivel superior (title, summary, tags, term, definition, related_terms, …) viven bajo chunk.metadata (por ejemplo, ep.metadata.get("title") en lugar de ep.get("title")). build_context devuelve ContextResponse; use context.formatted_context, no el valor de retorno como una cadena.

  • Las funciones auxiliares de escritura solo admiten palabras clave (save_semantic(text=..., label=..., …)). Las llamadas posicionales generan TypeError.

  • Las lecturas con ``visibility="private"`` mantienen el filtro de usuario ambiental (anteriormente, pasar cualquier argumento visibility lo eliminaba): las búsquedas de visibilidad privada ahora devuelven solo los recuerdos del usuario actual a menos que se pase un user_id explícito.

  • ``top_k``: por fuente search_semantic / search_episodes / search_taxonomic por defecto a top_k=50 (era a menudo 10). discover_procedures sigue por defecto a 10. Unificado Memory.search() sigue por defecto a top_k=10. Público build_context no tiene parámetro top_k. Use max_tokens para un presupuesto bruto de construcción de contexto (no un costo de obtención). Después de la recuperación y clasificación, el servidor resta una reserva de formato de token 500, luego selecciona codiciosamente bloques de memoria completos que caben en el resto. Los valores positivos en o por debajo de 500 no dejan presupuesto para memorias. Los valores por encima de 500 aún pueden producir un contexto vacío cuando ningún bloque cabe. Pase un top_k explícito en los ayudantes de búsqueda si necesita el límite anterior.

  • Identidad: los campos obligatorios que no se pueden resolver generan MemoryIdentityError (ya no hay None suave / salto silencioso). save_episode requiere un session_id resoluble (el contexto de invocación ambiental es suficiente; de ​​lo contrario, páselo explícitamente o vincule un MemoryRequestContext). Los valores en blanco no se consideran establecidos.

  • Fidelidad de creación vinculada a la aplicación: el resultado de creación id puede ser "" y has_embedding suele ser False; el éxito de la puerta depende de .acknowledged, no de id. Los detalles de cada operación se encuentran en la matriz de capacidades del paquete de memoria.

  • Obtiene vs búsqueda: get_semantic / get_taxonomic_term / list_episodes siguen devolviendo diccionarios con tipado flexible en la aplicación vinculada. Solo los métodos search* devuelven list[MemoryChunk].

  • Cambios de nombre: si alguien llamó a los nombres de pre-fachada, use la API pública de fachada: create_taxonomic → save_taxonomic; list_taxonomic_domains → list_domains.

Antes / después

# save_semantic: bool → .acknowledged; positional → keyword-only
# before
ok = app.memory.save_semantic("User prefers dark mode", "pref-theme", user_id="u1")
if ok:
...
# after
result = app.memory.save_semantic(
text="User prefers dark mode",
label="pref-theme",
user_id="u1",
)
if result.acknowledged:
...
# save_episode: str|None → CreateEpisodicResult (.acknowledged / .id)
# before
doc_id = app.memory.save_episode(title="Quote chat", content=summary, user_id="u1")
if doc_id:
...
# after
episode = app.memory.save_episode(
title="Quote chat",
content=summary,
user_id="u1",
metadata={"channel": "web", "priority": "high"}, # optional caller-supplied metadata
# session_id from ambient context, or pass explicitly
)
if episode.acknowledged:
print(episode.id) # may be "" on app-bound
# search_episodes: dict.get → MemoryChunk metadata + content; pin top_k if needed
# before
episodes = app.memory.search_episodes(query="policy quote", top_k=10)
for ep in episodes:
print(ep.get("title"), ep.get("content"))
# after
episodes = app.memory.search_episodes(query="policy quote", top_k=10)
for ep in episodes:
print(ep.metadata.get("title"), ep.content)
# build_context: str → ContextResponse.formatted_context
# before
prompt = app.memory.build_context(query="help me", user_id="u1")
# after
context = app.memory.build_context(query="help me", user_id="u1")
prompt = context.formatted_context

Migración de referencia (en el repositorio de ejemplos de Agent Engine):

  • agents/insurance-agent/src/insurance_agent/main.py

Las diferencias de capacidad entre backends y las brechas limitadas a las aplicaciones se documentan en la matriz de capacidades del paquete de memoria. La documentación a nivel de método para la fachada Memory se encuentra en agent-engine-sdk-memory.

Habilite la memoria con features.memory: true en agent.yaml, o con la variable de entorno heredada ENABLE_MEMORY=true cuando se omita esa bandera de característica. Las aplicaciones existentes aún pueden pasar enable_memory=... o enable_tracing=... a App(...), pero esas banderas del constructor están obsoletas: mueva la memoria a agent.yaml y elimine enable_tracing por completo porque el rastreo siempre está activado.

Las habilidades son archivos Markdown (SKILL.md) que el LLM puede cargar bajo demanda mediante divulgación progresiva. Úselos para codificar conocimientos especializados (por ejemplo, reglas de revisión de seguridad, convenciones de codificación) que sobrecargarían el mensaje del sistema si se incluyeran siempre.

my_agent/
skills/
security-checklist/
SKILL.md
style-guide/
SKILL.md

Pasa el directorio padre skills/ a skills=[...]. En tiempo de ejecución, deepagents lista ese directorio a través del backend configurado y descubre cada subdirectorio inmediato que contiene SKILL.md como una habilidad. El descubrimiento es de un solo nivel de profundidad, no recursivo.

---
name: security-checklist
description: Security review rules for Python code, focusing on injection and auth
---
# Security Checklist
## REVIEW-RULE-ID-SEC-1: SQL injection
Never concatenate user input into SQL...
## REVIEW-RULE-ID-SEC-2: Command / path injection
Calls to `subprocess.run`, `os.system`, `shell=True`, and `open()` must not
interpolate untrusted input...

deepagents valida el encabezado de las habilidades en tiempo de ejecución. Omite el encabezado ilegible o no analizable y las habilidades que carecen de name o description. Las infracciones en la nomenclatura de las habilidades del agente o en los nombres de directorio generan advertencias, pero aun así pueden cargarse. El SDK reenvía las rutas declaradas sin inspeccionarlas ni filtrarlas.

Nota

Requisito previo: agent.yaml debe incluir features.deep_agent: true o App.deep_agent() generará RuntimeError en el momento de la construcción:

features:
deep_agent: true
from langchain_openai import ChatOpenAI
from agent_engine_sdk_langgraph import App
app = App(app_name="My Reviewer")
@app.entrypoint
def build_agent():
return app.deep_agent(
llm=ChatOpenAI(model="gpt-5.4"),
system_prompt="You are a code reviewer.",
skills=["skills"],
)
app.run()

Cada entrada skills=[...] es un directorio fuente principal, no un directorio de habilidad hoja ni un archivo SKILL.md. Las rutas son relativas al directorio que contiene agent.yaml, por lo que skills=["skills"] funciona tanto para imágenes de agente único (/app/skills) como para imágenes de monorepo (/app/<agent-subdirectory>/skills). Si sus habilidades se encuentran en otro lugar dentro del árbol de origen del agente, establezca AGENTIC_SKILLS_DIR en ese directorio relativo y haga que skills=[...] sea relativo a él. En tiempo de ejecución, deepagents lee el frontmatter de cada habilidad descubierta y pasa sus metadatos (nombre, descripción y ruta resuelta) al LLM como un bloque del sistema de habilidades en el indicador del sistema.

En el turno 1, el LLM solo ve los metadatos de la habilidad, no los cuerpos. Cuando un usuario pregunta sobre seguridad, el LLM decide read_file("<agent-dir>/skills/security-checklist/SKILL.md"), y el cuerpo completo llega como un ToolMessage en el contexto del turno 2.

Esto mantiene la solicitud básica simple (los metadatos son aproximadamente 50 tokens por habilidad) al tiempo que permite que la experiencia profunda se cargue bajo demanda.

El sistema de archivos escribible y los manejadores de shell de ToolPod siguen usando WORKSPACE_DIR, que por defecto es /tmp/agent-workspace. Mantén ese como espacio temporal.

Las habilidades empaquetadas se tratan como recursos de solo lectura. ToolPod obtiene la raíz de habilidades predeterminada de AGENTIC_AGENT_CONFIG_PATH o AGENTIC_AGENT_WORKDIR: si la configuración de tiempo de ejecución es /app/agent.yaml, la raíz de habilidades es /app/skills; si la configuración de tiempo de ejecución es /app/agents/reviewer/agent.yaml, la raíz de habilidades es /app/agents/reviewer/skills. AGENTIC_SKILLS_DIR anula esa raíz y debe ser relativa a la raíz de origen del agente. Las herramientas de sistema de archivos de solo lectura pueden cargar archivos bajo esa raíz sin establecer WORKSPACE_DIR al directorio de habilidades. Las operaciones de escritura, edición y shell permanecen en el espacio de trabajo escribible. La raíz de habilidades se resuelve al iniciar Tool Pod, no al importar el SDK, por lo que una importación estática normal del SDK funciona; no se necesita ninguna solución alternativa para el orden de importación.

Las habilidades solo son visibles para el agente que las declara. Si tu agente crea subagentes (mediante la herramienta task), estos no heredan las habilidades del agente padre. Pasa skills=[...] a cada especificación de subagente que necesite archivos de habilidades.

El entorno de ejecución deep-agent reserva los nombres de herramientas 9 para las funciones integradas.No registre @app.tool() con ninguno de estos nombres, ya que esto oculta silenciosamente la función integrada y altera el comportamiento de skills/sandbox:

  • read_file, write_file, edit_file, ls, glob, grep (sistema de archivos)

  • execute (caparazón)

  • write_todos (planificación)

  • task (subagent dispatch)

Elegir un nombre que entre en conflicto ocultará silenciosamente el nombre integrado; no habrá ningún error en el momento de la importación.

Objetivo < 200 líneas por cuerpo de SKILL.md. Habilidades más grandes:

  • Consume más contexto cuando se carga (cada read_file es un volcado de cuerpo completo).

  • Riesgo de alcanzar el límite de contexto de mensaje único del LLM en giros complejos

  • Sugiero que la habilidad se divida en varios archivos especializados.

El entorno de ejecución almacena en caché skills_metadata en el estado del agente durante la vida útil de un hilo. Si edita un archivo SKILL.md, los hilos existentes seguirán utilizando los metadatos obsoletos hasta que se reinicien. En desarrollo: elimine el hilo o inicie una nueva sesión. En producción: los cambios en las habilidades deben ir acompañados del lanzamiento de una nueva versión del modelo/mensaje.

Consulte el repositorio de ejemplos de Code Reviewer Agent en Agent Engine para obtener una implementación de referencia:

  • Repositorio de ejemplos de Agent Engine agents/code-reviewer-agent/src/code_reviewer_agent/main.py — cableado

  • Repositorio de ejemplos de Agent Engine agents/code-reviewer-agent/skills/*/SKILL.md — ejemplos de habilidades

LangGraphBaseAgent.stream() produce objetos StreamEvent. Itere con async for para recibir actualizaciones a nivel de token, marcadores del ciclo de vida del subagente y el resultado final.

event
Cuando dispara
data Campos

token

Cada fragmento de token LLM del agente raíz o de cualquier subagente activo.

content: texto del token. source: "" para el agente raíz o el nombre del gráfico del subagente. tool_call_id: task tool_call_id del padre cuando hay uno en ejecución para este subagente (puede ser "" hasta que se ensamble).

subagent_start

Comienza la ejecución de un subagente. Se emite desde una de dos rutas: (1) primaria: se observa la llamada a la herramienta task del agente padre; (2) de reserva sintética: llega un token de origen antes de que se haya ensamblado la llamada a la herramienta padre (proveedores de despacho con búfer). Las dos rutas se desduplican entre sí, de modo que se activa exactamente un inicio por subagente por turno.

source / subagent_name: el nombre del gráfico del subagente. tool_call_id: el task tool_call_id del padre, o "" si el mecanismo de reserva sintético se activó antes de que se ensamblara la llamada a la herramienta. description: el description argumento que el padre pasó a task (vacío cuando se activa primero el mecanismo sintético).

subagent_end

Finaliza la ejecución de un subagente. Ruta principal: el grafo padre observa un cierre Command cuyo tool_call_id coincide con un subagente abierto. Ruta defensiva: el flujo genera errores o finaliza con subagentes pendientes; se emite un subagent_end por cada huérfano para que los consumidores puedan cerrar el estado de su interfaz de usuario.

source / subagent_name: igual que el inicio. tool_call_id: el tool_call_id de cierre, o "" para finales huérfanos de un inicio solo sintético que nunca recibió una llamada a herramienta real. summary: el contenido ToolMessage final del subagente (vacío para finales defensivos).

result

Finalización definitiva del agente raíz.

response Además de la lista completa de mensajes.

suspend

Interrupción HITL: el gráfico se pausa a la espera de revisión humana.

suspend_payload, checkpoint_id.

Notas para los consumidores:

  • subagent_start y subagent_end siempre están emparejados, incluso en caso de terminación anormal. El brazo de limpieza en stream() distingue GeneratorExit (desconexión del consumidor: descarta el estado sin ceder, ya que no queda ningún consumidor) de los errores del lado del proveedor (cede el estado defensivo subagent_end y luego lo vuelve a elevar).

  • Para despachos paralelos del mismo tipo de subagente, cada invocación tiene su propio tool_call_id. Prefiera tool_call_id para los tokens de enrutamiento y recurra a source solo cuando tool_call_id == "".

  • subagent_end.summary es el texto de respuesta final del subagente, la misma cadena que el agente principal verá como valor de retorno de la herramienta task.

Los flujos de trabajo duraderos reproducen la llamada nativa interrupt() de LangGraph y traducen su ID nativo recién generado a la posición de actividad OE registrada previamente. Consulte Interrupción y reanudación de Durable LangGraph para obtener información completa sobre la suspensión, la reproducción y el flujo Command(resume=...), así como sus puntos de llamada de código.

Consulte docs/api.md para ver la superficie App / LangGraph generada automáticamente. Para la fachada Memory (métodos, tipos de retorno, reglas de identidad), consulte agent-engine-sdk-memory y su matriz de capacidades.

Variable de entorno
predeterminado
Descripción

MDB_AGENTIC_STORE_DB

mdb_store

Nombre base para el almacén MongoDB por proyecto utilizado para los puntos de control de LangGraph (solo en modo AER). El alcance/descubrimiento del proyecto se mantiene a menos que se especifique lo contrario a continuación.

CHECKPOINT_DB_NAME

(sin establecer)

Nombre exacto de la base de datos MongoDBSaver cuando se configura. Omite la definición del alcance y el descubrimiento del proyecto. Opción para bases de datos de puntos de control compartidas de doble tiempo de ejecución (configuradas en el entorno del pod AER del agente / SecretRefs).

CHECKPOINTER_SERVER_SELECTION_TIMEOUT

5.0

Segundos para la selección del servidor de punto de control de MongoDB antes de que falle la E/S del punto de control.

CHECKPOINTER_CONNECT_TIMEOUT

5.0

Segundos para el establecimiento de la conexión del punto de control de MongoDB.

CHECKPOINTER_SOCKET_TIMEOUT

15.0

Segundos para lecturas/escrituras de sockets de punto de control de MongoDB.

Por defecto, el punto de control de LangGraph thread_id es session_id:workspace_id. Los agentes pueden sobrescribirlo con @app.resolve_thread_id (valor de retorno utilizado tal cual en el reinicio y la reanudación). Las claves personalizadas son invisibles para las búsquedas de historial de Atlas Agent Engine /query/sessions*, que siguen utilizando únicamente las claves predeterminadas derivadas de la sesión/espacio de trabajo. Los agentes que omiten el ámbito del espacio de trabajo también poseen el aislamiento de colisiones dentro de la base de datos del punto de control.

El viaje en el tiempo de LangGraph parchearía el origen thread_id. En cambio, Atlas Agent Engine crea una nueva sesión. Las sesiones de punto de control nativo copian un punto de control completado en un nuevo hilo; las sesiones de flujo de trabajo duradero se ramifican a partir de un estado validado por OE reconstruido en un espacio temporal aislado. Consulte Bifurcación de sesión frente a viaje en el tiempo de LangGraph.

Documentación de la plataforma (qué es Durable Workflow, primitivas, habilitación, restricciones): Durable Workflow. El modelo de reproducción compartida de Tool y LLM se describe en la identidad de actividad de Durable. Consulte Subgrafos compilados de Durable y delegación de agente profundo de Durable para obtener diagramas de secuencia completos, ejemplos y mapas de sitios de llamadas de código. Solo los efectos enrutados a través de los envoltorios seguros de LLM y Tool de Atlas Agent Engine participan en la grabación/reproducción duradera. Para la reproducción duradera de Tool, ToolCall debe provenir del envoltorio seguro de LLM y ejecutarse a través de una Tool devuelta por app.get_tools().

Los flujos de trabajo duraderos no exponen la ramificación dinámica `Send deLangGraph `__.El punto de control normal de la plataforma rechaza las escrituras Send creadas por la aplicación. Los grafos creados por app.deep_agent() son una excepción opaca porque LangChain usa Send internamente para enrutar ToolCalls; esta compatibilidad privada no hace que Send sea una API de aplicación compatible. En su lugar, use aristas de grafo fijas, subgrafos compilados o delegación de tareas de Deep Agent. Los flujos de trabajo de punto de control nativos no se ven afectados.

Las lecturas son solo para ámbitos. El historial de sesión expande cada Atlas Agent Engine session_id a solo su clave compuesta con ámbito de espacio de trabajo; la clave sin ámbito nunca se consulta una vez que se conoce un ámbito de espacio de trabajo, porque las claves sin ámbito son legibles y escribibles por cada espacio de trabajo en el almacenamiento compartido. Por lo tanto, los puntos de control heredados escritos antes de que existiera el ámbito ya no son atendidos por los puntos finales del historial; no vuelva a agregar el respaldo. Un ámbito vacío es legítimo solo en tiempos de ejecución explícitamente sin ámbito (desarrollo local / pruebas, sin APP_ID). Los AER administrados llevan REQUIRE_PROJECT_SCOPED_DB; si APP_ID falta allí, tanto las lecturas como las escrituras fallan cerradas en lugar de confiar en el espacio de trabajo de la red o usar claves sin ámbito. Los adoptantes de producción de claves personalizadas aún deben tratar la unicidad de la clave de punto de control dentro de una base de datos compartida como propiedad del agente.

  • Python >= 3.11

  • uv

uv sync --extra dev

Para las mismas comprobaciones que ejecuta CI (lint + format + pyright + tests), utilice el ejecutor unificado: ./scripts/test.sh agent-engine-sdk-langgraph desde la raíz del repositorio.

uv run pytest
uv run pyright
make docs
# Check for lint errors
uv run ruff check src
# Auto-fix lint errors
uv run ruff check --fix src
# Format code
uv run ruff format src
Califique esta página