- Inicio
- Documentation
- Configuración
- Arquitectura de almacenamiento de blobs y artefactos
Arquitectura de almacenamiento de blobs y artefactos
Este documento describe cómo coding-agent almacena cargas útiles grandes/binarias fuera del JSONL de sesión, cómo se persisten las salidas truncadas de herramientas y cómo las URLs internas (artifact://, agent://) se resuelven de vuelta a los datos almacenados.
Por qué existen dos sistemas de almacenamiento
Sección titulada «Por qué existen dos sistemas de almacenamiento»El runtime utiliza dos mecanismos de persistencia diferentes para diferentes formas de datos:
- Blobs con direccionamiento por contenido (
blob:sha256:<hash>): almacenamiento global orientado a binarios, utilizado para externalizar cargas útiles grandes de imágenes en base64 de las entradas de sesión persistidas. - Artefactos con alcance de sesión (archivos bajo
<archivoSesión-sin-.jsonl>/): archivos de texto por sesión utilizados para salidas completas de herramientas y salidas de subagentes.
Están separados intencionalmente:
- el almacenamiento de blobs optimiza la deduplicación y las referencias estables mediante hash de contenido,
- el almacenamiento de artefactos optimiza las herramientas de sesión de solo adición y la recuperación por humanos/herramientas mediante IDs locales.
Límites de almacenamiento y disposición en disco
Sección titulada «Límites de almacenamiento y disposición en disco»Límite del almacén de blobs (global)
Sección titulada «Límite del almacén de blobs (global)»SessionManager construye BlobStore(getBlobsDir()), por lo que los archivos de blobs residen en un directorio de blobs global compartido (no en una carpeta de sesión).
Nomenclatura de archivos de blobs:
- ruta del archivo:
<blobsDir>/<sha256-hex> - sin extensión
- cadena de referencia almacenada en las entradas:
blob:sha256:<sha256-hex>
Implicaciones:
- el mismo contenido binario en diferentes sesiones se resuelve al mismo hash/ruta,
- las escrituras son idempotentes a nivel de contenido,
- los blobs pueden sobrevivir a cualquier archivo de sesión individual.
Límite de artefactos (local a la sesión)
Sección titulada «Límite de artefactos (local a la sesión)»ArtifactManager deriva el directorio de artefactos a partir de la ruta del archivo de sesión:
- archivo de sesión:
.../<timestamp>_<sessionId>.jsonl - directorio de artefactos:
.../<timestamp>_<sessionId>/(se elimina.jsonl)
Los tipos de artefactos comparten este directorio:
- archivos de salida truncada de herramientas:
<numericId>.<toolType>.log(paraartifact://) - archivos de salida de subagentes:
<outputId>.md(paraagent://)
Esquemas de asignación de IDs y nombres
Sección titulada «Esquemas de asignación de IDs y nombres»IDs de blobs: hash de contenido
Sección titulada «IDs de blobs: hash de contenido»BlobStore.put() calcula SHA-256 sobre los bytes binarios en bruto y devuelve:
hash: resumen hexadecimal,path:<blobsDir>/<hash>,ref:blob:sha256:<hash>.
No se utiliza ningún contador local de sesión.
IDs de artefactos: entero monotónico local a la sesión
Sección titulada «IDs de artefactos: entero monotónico local a la sesión»ArtifactManager escanea los archivos de artefactos *.log existentes en el primer uso para encontrar el ID numérico máximo existente y establece nextId = max + 1.
Comportamiento de asignación:
- formato de archivo:
{id}.{toolType}.log - los IDs son cadenas secuenciales (
"0","1", …) - la reanudación no sobrescribe artefactos existentes porque el escaneo ocurre antes de la asignación.
Si el directorio de artefactos no existe, el escaneo produce una lista vacía y la asignación comienza desde 0.
IDs de salida de agentes (agent://)
Sección titulada «IDs de salida de agentes (agent://)»AgentOutputManager asigna IDs para las salidas de subagentes como <index>-<requestedId> (opcionalmente anidados bajo un prefijo padre, por ejemplo 0-Parent.1-Child). Escanea los archivos .md existentes durante la inicialización para continuar desde el siguiente índice en la reanudación.
Flujo de datos de persistencia
Sección titulada «Flujo de datos de persistencia»1) Ruta de reescritura de persistencia de entradas de sesión
Sección titulada «1) Ruta de reescritura de persistencia de entradas de sesión»Antes de que las entradas de sesión se escriban (#rewriteFile / persistencia incremental), SessionManager llama a prepareEntryForPersistence() (a través de truncateForPersistence).
Comportamientos clave:
- Truncado de cadenas grandes: las cadenas sobredimensionadas se cortan y se les añade el sufijo
"[Session persistence truncated large content]". - Eliminación de campos transitorios:
partialJsonyjsonlEventsse eliminan de las entradas persistidas. - Externalización de imágenes a blobs:
- solo se aplica a bloques de imagen en arrays
content, - solo cuando
datano es ya una referencia de blob, - solo cuando la longitud del base64 alcanza al menos el umbral (
BLOB_EXTERNALIZE_THRESHOLD = 1024), - reemplaza el base64 en línea con
blob:sha256:<hash>.
- solo se aplica a bloques de imagen en arrays
Esto mantiene el JSONL de sesión compacto mientras preserva la recuperabilidad.
2) Ruta de rehidratación en la carga de sesión
Sección titulada «2) Ruta de rehidratación en la carga de sesión»Al abrir una sesión (setSessionFile), después de las migraciones, SessionManager ejecuta resolveBlobRefsInEntries().
Para cada bloque de imagen de message/custom-message con blob:sha256:<hash>:
- lee los bytes del blob desde el almacén de blobs,
- convierte los bytes de vuelta a base64,
- muta la entrada en memoria para incluir el base64 en línea para los consumidores del runtime.
Si el blob no se encuentra:
resolveImageData()registra una advertencia,- devuelve la cadena de referencia original sin cambios,
- la carga continúa (sin fallo crítico).
3) Ruta de volcado/truncado de salida de herramientas
Sección titulada «3) Ruta de volcado/truncado de salida de herramientas»OutputSink potencia la salida en streaming en bash/python/ssh y ejecutores relacionados.
Comportamiento:
- Cada fragmento se sanitiza y se añade al buffer de cola en memoria.
- Cuando los bytes en memoria exceden el umbral de volcado (
DEFAULT_MAX_BYTES, 50KB), el sink marca la salida como truncada. - Si hay disponible una ruta de artefacto, el sink abre un escritor de archivos y escribe:
- el contenido almacenado en buffer existente una vez,
- todos los fragmentos subsiguientes.
- El buffer en memoria siempre se recorta a la ventana de cola para visualización.
dump()devuelve un resumen que incluyeartifactIdsolo cuando el escritor de archivos se creó exitosamente.
Efecto práctico:
- La UI/retorno de herramienta muestra la cola truncada,
- la salida completa se preserva en el archivo de artefacto y se referencia como
artifact://<id>.
Si la creación del escritor de archivos falla (error de E/S, ruta inexistente, etc.), el sink recurre silenciosamente al truncado solo en memoria; la salida completa no se persiste.
Modelo de acceso por URL
Sección titulada «Modelo de acceso por URL»Referencias blob:
Sección titulada «Referencias blob:»blob:sha256:<hash> es una referencia de persistencia dentro de las cargas útiles de entradas de sesión, no un esquema de URL interno manejado por el enrutador. La resolución la realiza SessionManager durante la carga de sesión.
artifact://<id>
Sección titulada «artifact://<id>»Manejado por ArtifactProtocolHandler:
- requiere un directorio de artefactos de sesión activo,
- el ID debe ser numérico,
- se resuelve comparando el prefijo del nombre de archivo
<id>., - devuelve texto sin formato (
text/plain) del archivo.logcoincidente, - cuando no se encuentra, el error incluye una lista de IDs de artefactos disponibles.
Comportamiento con directorio inexistente:
- si el directorio de artefactos no existe, lanza
No artifacts directory found.
agent://<id>
Sección titulada «agent://<id>»Manejado por AgentProtocolHandler sobre <artifactsDir>/<id>.md:
- la forma simple devuelve texto markdown,
- las formas
/patho?q=realizan extracción JSON, - la extracción por ruta y por consulta no se pueden combinar,
- si se solicita extracción, el contenido del archivo debe parsearse como JSON.
Comportamiento con directorio inexistente:
- lanza
No artifacts directory found.
Comportamiento con salida inexistente:
- lanza
Not found: <id>con los IDs disponibles de los archivos.mdexistentes.
Integración con la herramienta read:
readsoporta paginación con offset/limit para lecturas de URLs internas sin extracción,- rechaza
offset/limitcuando se utiliza extracción deagent://.
Semánticas de reanudación, bifurcación y movimiento
Sección titulada «Semánticas de reanudación, bifurcación y movimiento»Reanudación
Sección titulada «Reanudación»ArtifactManagerescanea los archivos{id}.*.logexistentes en la primera asignación y continúa la numeración.AgentOutputManagerescanea los IDs de salida.mdexistentes y continúa la numeración.SessionManagerrehidrata las referencias de blob a base64 durante la carga.
Bifurcación (fork)
Sección titulada «Bifurcación (fork)»SessionManager.fork() crea un nuevo archivo de sesión con un nuevo ID de sesión y un enlace parentSession, luego devuelve las rutas de archivo antigua/nueva. La copia de artefactos es manejada por AgentSession.fork():
- intenta una copia recursiva del directorio de artefactos antiguo al nuevo directorio de artefactos,
- se tolera la ausencia del directorio antiguo,
- los errores de copia que no sean ENOENT se registran como advertencias y la bifurcación se completa igualmente.
Implicaciones de IDs después de la bifurcación:
- si la copia tuvo éxito, los contadores de artefactos en la nueva sesión continúan después del ID máximo copiado,
- si la copia falló/se omitió, los IDs de artefactos de la nueva sesión comienzan desde
0.
Implicaciones de blobs después de la bifurcación:
- los blobs son globales y con direccionamiento por contenido, por lo que no se requiere copia del directorio de blobs.
Mover a un nuevo cwd
Sección titulada «Mover a un nuevo cwd»SessionManager.moveTo() renombra tanto el archivo de sesión como el directorio de artefactos al nuevo directorio de sesión predeterminado, con lógica de rollback si un paso posterior falla. Esto preserva la identidad de los artefactos mientras se reubica el alcance de la sesión.
Manejo de fallos y rutas de respaldo
Sección titulada «Manejo de fallos y rutas de respaldo»| Caso | Comportamiento |
|---|---|
| Archivo de blob inexistente durante la rehidratación | Advierte y mantiene la cadena de referencia blob:sha256: en memoria |
Blob con ENOENT al leer vía BlobStore.get | Devuelve null |
Directorio de artefactos inexistente (ArtifactManager.listFiles) | Devuelve lista vacía (la asignación puede comenzar desde cero) |
Directorio de artefactos inexistente (artifact:// / agent://) | Lanza explícitamente No artifacts directory found |
| ID de artefacto no encontrado | Lanza con listado de IDs disponibles |
| Fallo en la inicialización del escritor de artefactos de OutputSink | Continúa con truncado solo de cola (sin artefacto de salida completa) |
| Sin archivo de sesión (algunas rutas de tareas) | La herramienta Task recurre a un directorio temporal de artefactos para las salidas de subagentes |
Externalización de blobs binarios vs artefactos de salida de texto
Sección titulada «Externalización de blobs binarios vs artefactos de salida de texto»- La externalización de blobs es para cargas útiles de imágenes binarias dentro del contenido de entradas de sesión persistidas; reemplaza el base64 en línea en el JSONL con referencias de contenido estables.
- Los artefactos son archivos de texto plano para salidas de ejecución y salidas de subagentes; son direccionables mediante IDs locales de sesión a través de URLs internas.
Los dos sistemas se intersectan solo indirectamente (ambos reducen la inflación del JSONL de sesión) pero tienen diferentes identidades, ciclos de vida y rutas de recuperación.
Archivos de implementación
Sección titulada «Archivos de implementación»src/session/blob-store.ts— formato de referencia de blobs, hashing, put/get, helpers de externalización/resolución.src/session/artifacts.ts— modelo de directorio de artefactos de sesión y asignación numérica de IDs de artefactos.src/session/streaming-output.ts— comportamiento de truncado/volcado a archivo deOutputSinky metadatos de resumen.src/session/session-manager.ts— transformaciones de persistencia, rehidratación de blobs en la carga, interacciones de bifurcación/movimiento de sesión.src/session/agent-session.ts— copia del directorio de artefactos durante la bifurcación interactiva.src/tools/output-utils.ts— bootstrap del gestor de artefactos de herramientas y asignación de rutas de artefactos por herramienta.src/internal-urls/artifact-protocol.ts— resolutor deartifact://.src/internal-urls/agent-protocol.ts— resolutor deagent://+ extracción JSON.src/sdk.ts— cableado del enrutador de URLs internas y resolutor del directorio de artefactos.src/task/output-manager.ts— asignación de IDs de salida de agentes con alcance de sesión paraagent://.src/task/executor.ts— escrituras de artefactos de salida de subagentes (<id>.md) y respaldo con directorio temporal de artefactos.