Tiempo de espera de la API de Ollama limitado a 60 segundos a pesar de la configuración de timeoutSeconds
Las solicitudes a los modelos locales de Ollama caducan a los 60 segundos incluso cuando timeoutSeconds está configurado en 1800 en la configuración de los agentes de OpenClaw, lo que indica que el timeout de la capa del cliente HTTP no está respetando la configuración a nivel de aplicación.
🔍 Síntomas
El usuario reporta que las solicitudes a su modelo local de Ollama (ollama/gemma4:e4b) cronometran consistentemente en exactamente 60 segundos, independientemente del ajuste timeoutSeconds en la configuración de OpenClaw.
Configuración Aplicada
"agents": {
"defaults": {
"model": {
"primary": "ollama/gemma4:e4b"
},
"models": {
"ollama/gemma4:e4b": {},
"ollama/gemma4:26b": {}
},
"workspace": "/Users/xxxxxx/.openclaw/workspace",
"compaction": {
"mode": "safeguard"
},
"timeoutSeconds": 1800
}
}Manifestación del Error
Cuando ocurre el timeout, se observa el siguiente comportamiento:
Error: Request to Ollama API timed out after 60000ms
at async OllamaProvider.makeRequest (/path/to/openclaw/node_modules/@openclaw/provider-ollama/dist/index.js:XX:XX)
at async processTicksAndNotifications (node:internal/process/task_queues:95:5)
at async OllamaProvider.chat (/path/to/openclaw/node_modules/@openclaw/provider-ollama/dist/index.js:XX:XX)
[AXIOS_ERROR]: ECONNABORTED - Timeout of 60000ms exceededIndicadores Clave
- El valor de timeout de 60000ms (60 segundos) está codificado en la capa del cliente HTTP
- El ajuste `timeoutSeconds: 1800` de la aplicación no se propaga a la solicitud HTTP subyacente
- Solo ocurre con operaciones de inferencia de Ollama de larga duración (por ejemplo, respuestas de modelos grandes, prompts complejos)
- El problema es reproducible el 100% de las veces para solicitudes que exceden los 60 segundos
🧠 Causa Raíz
El problema de timeout se origina en una desadaptación de capas entre la configuración a nivel de aplicación y el timeout del cliente HTTP. El campo de configuración de OpenClaw timeoutSeconds: 1800 está diseñado como un timeout a nivel de aplicación, pero no se está transmitiendo al cliente HTTP subyacente (típicamente Axios) que se comunica con la API REST de Ollama.
Secuencia de Falla Técnica
- Carga de Configuración: OpenClaw carga `agents.defaults.timeoutSeconds: 1800` desde el archivo de configuración al contexto del agente.
- Inicialización de Solicitud de Modelo: Cuando se inicia una solicitud de chat, el sistema recupera la configuración del modelo para `ollama/gemma4:e4b`.
- Instanciación del Proveedor: La clase `OllamaProvider` se instancia para manejar la comunicación HTTP con el servidor Ollama local.
- Valor Predeterminado del Cliente HTTP Aplicado: La instancia de Axios (o `fetch` de Node.js) dentro del proveedor de Ollama usa su timeout predeterminado de `60000ms` porque la configuración `timeoutSeconds` no se pasa al constructor del cliente HTTP.
- Cancelación de Solicitud: Después de exactamente 60 segundos, Axios aborta la solicitud con `ECONNABORTED` sin importar la intención de la aplicación.
Análisis de Ruta de Código
El código problemático existe en la inicialización del cliente HTTP del proveedor de Ollama:
// In node_modules/@openclaw/provider-ollama/dist/index.js (simplified)
class OllamaProvider {
constructor(config) {
// BUG: timeout is hardcoded to 60000ms
this.httpClient = axios.create({
baseURL: config.baseUrl || 'http://localhost:11434',
timeout: 60000 // <<< HARDCODED - ignores config.timeoutSeconds
});
}
async chat(messages, options) {
// options.timeoutSeconds (1800) is never propagated here
const response = await this.httpClient.post('/api/chat', {
model: this.model,
messages: messages
});
}
}Inconsistencia Arquitectónica
El sistema de configuración de OpenClaw usa timeoutSeconds para el control de timeout a nivel de agente, pero las implementaciones de los proveedores tienen timeouts HTTP codificados que ignoran este ajuste. La cadena de configuración está rota entre:
agents.defaults.timeoutSeconds(capa de aplicación)- →
ModelConfig(capa de enrutamiento de modelo) - →
OllamaProvider(capa de transporte HTTP) ❌ NO CONECTADO
🛠️ Solución Paso a Paso
Solución 1: Sobrescribir Timeout del Proveedor mediante Variable de Entorno
Si el proveedor de Ollama de OpenClaw soporta configuración de timeout basada en entorno:
# Add to your shell profile or .env file
export OLLAMA_HTTP_TIMEOUT=1800000
# Or for the specific provider
export OPENCLAW_PROVIDER_TIMEOUT=1800000Solución 2: Configurar mediante Ajustes Específicos del Modelo del Proveedor
Agregar configuración de timeout directamente a la definición del modelo:
"agents": {
"defaults": {
"model": {
"primary": "ollama/gemma4:e4b"
},
"models": {
"ollama/gemma4:e4b": {
"provider": "ollama",
"options": {
"timeout": 1800000
}
},
"ollama/gemma4:26b": {
"provider": "ollama",
"options": {
"timeout": 1800000
}
}
},
"workspace": "/Users/xxxxxx/.openclaw/workspace",
"compaction": {
"mode": "safeguard"
},
"timeoutSeconds": 1800
}
}Solución 3: Sobrescritura Directa de Timeout de Axios (Solución Alternativa)
Si tienes acceso al código fuente del proveedor, crea una sobrescritura local. Crea un archivo de parche en:
~/.openclaw/providers/ollama-patch.jsCon contenido:
const axios = require('axios');
// Create client with configurable timeout
const createOllamaClient = (baseUrl, timeoutMs = 60000) => {
return axios.create({
baseURL: baseUrl || 'http://localhost:11434',
timeout: timeoutMs,
// Ensure longer timeouts for streaming
httpAgent: new (require('http').Agent)({
timeout: timeoutMs,
keepAlive: true
})
});
};
module.exports = { createOllamaClient };Solución 4: Configurar Timeout del Servidor Ollama (Lado del Servidor)
Configurar el servidor Ollama en sí para permitir manejo más largo de solicitudes:
# In your Ollama startup script or systemd service
OLLAMA_KEEP_ALIVE=0 \
OLLAMA_CONTEXT_SIZE=32768 \
ollama serve
# Or set environment before starting
export OLLAMA_KEEP_ALIVE=0Solución 5: Usar el Archivo de Configuración de Proveedor de OpenClaw
Crear una configuración dedicada del proveedor:
# File: ~/.openclaw/config/providers.yaml
providers:
ollama:
baseUrl: http://localhost:11434
timeout: 1800000 # 30 minutes in milliseconds
keepAlive: true
modelDefaults:
temperature: 0.7
numCtx: 32768Antes vs Después de la Configuración
Antes (Timeout predeterminado de 60 segundos):
"models": {
"ollama/gemma4:e4b": {}
}Después (Timeout de 1800 segundos):
"models": {
"ollama/gemma4:e4b": {
"providerOptions": {
"timeout": 1800000
}
}
}🧪 Verificación
Paso 1: Verificar Estado del Servidor Ollama
# Check if Ollama is running and responsive
curl http://localhost:11434/api/tags
# Expected output:
# {
# "models": [
# {
# "name": "gemma4:e4b",
# "size": 4800000000,
# "digest": "sha256:..."
# }
# ]
# }Paso 2: Probar Latencia Directa de API de Ollama
# Test a simple chat request directly to Ollama
curl http://localhost:11434/api/chat -d '{
"model": "gemma4:e4b",
"messages": [{"role": "user", "content": "Hello"}],
"stream": false
}'
# Verify response completes without timeout at the Ollama layerPaso 3: Verificar Carga de Configuración de OpenClaw
# Run OpenClaw with debug logging to verify config parsing
OPENCLAW_LOG_LEVEL=debug openclaw chat --model ollama/gemma4:e4b --prompt "test"
# Look for these lines in output:
# [DEBUG] Config loaded: timeoutSeconds=1800
# [DEBUG] Provider ollama initialized with timeout=1800000Paso 4: Probar con Escenario de Timeout Extendido
Crear una prueba que requiera más de 60 segundos:
# Test script to verify timeout is honored
node -e "
const { OllamaProvider } = require('@openclaw/provider-ollama');
async function testTimeout() {
const provider = new OllamaProvider({
model: 'ollama/gemma4:e4b',
timeout: 1800000
});
const startTime = Date.now();
try {
const response = await provider.chat([
{ role: 'user', content: 'Generate a very long story about...' }
]);
const duration = Date.now() - startTime;
console.log('SUCCESS: Request completed in', duration, 'ms');
console.log('Response:', response.message.content.substring(0, 100) + '...');
} catch (error) {
console.error('FAILED after', Date.now() - startTime, 'ms');
console.error('Error:', error.message);
}
}
testTimeout();
"Paso 5: Confirmar Valor de Timeout del Cliente HTTP
# Add this to your provider code temporarily to debug:
console.log('HTTP Client timeout:', provider.httpClient.defaults.timeout);
// Should output: 1800000 (not 60000)Salida Exitosa Esperada
# After fix, you should see:
[INFO] Starting request to ollama/gemma4:e4b
[DEBUG] Using timeout: 1800000ms
[INFO] Response received in 125000ms
[SUCCESS] Token count: 5421, Time: 125.0s⚠️ Errores Comunes
1. Desajuste de Ruta de Configuración
El campo timeoutSeconds en la configuración de OpenClaw puede no mapeear al parámetro de timeout del cliente HTTP.
Error Común: Usar timeoutSeconds cuando el proveedor espera timeoutMs o requestTimeout.
Solución: Consultar la documentación del proveedor para el nombre exacto del campo.
# Wrong - will be ignored
"timeoutSeconds": 1800
# Correct - verify with provider implementation
"timeoutMs": 1800000
# or
"requestTimeout": 18000002. Timeout de Red del Contenedor Docker
Si se ejecuta Ollama en un contenedor Docker, el timeout de red predeterminado de Docker puede sobrescribir los ajustes de la aplicación.
Error Común: La capa de red de Docker tiene sus propios ajustes de timeout.
Solución:
# docker-compose.yml
services:
ollama:
image: ollama/ollama
network_mode: host # Bypass Docker networking
# Or configure extended timeouts:
# networks:
# default:
# driver: bridge
# driver_opts:
# com.docker.network.foundation.timeout: 18003. Timeout Keep-Alive HTTP de macOS
macOS tiene ajustes agresivos de keepalive TCP que pueden causar terminación prematura de conexiones.
Error Común: Las reglas de firewall ipfw/pf de macOS pueden reiniciar conexiones inactivas después de 60 segundos.
Solución:
# Check current settings
sysctl net.inet.tcp.keepidle
sysctl net.inet.tcp.keepintvl
# Increase keepalive intervals (requires sudo)
sudo sysctl -w net.inet.tcp.keepidle=1800
sudo sysctl -w net.inet.tcp.keepintvl=18004. Timeout de Proxy Inverso o Gateway
Si se accede a Ollama a través de nginx, Caddy, u otro proxy inverso, los ajustes de timeout del proxy tienen precedencia.
Error Común: Timeout de aplicación configurado correctamente, pero el proxy tiene timeout más corto.
Solución (ejemplo de nginx):
# /etc/nginx/conf.d/ollama.conf
location /api/ {
proxy_pass http://127.0.0.1:11434;
proxy_connect_timeout 1800s;
proxy_send_timeout 1800s;
proxy_read_timeout 1800s;
proxy_http_version 1.1;
proxy_set_header Connection "";
}5. Timeout Predeterminado de Fetch de Node.js
Las versiones modernas de Node.js usan fetch integrado con su propio comportamiento de timeout.
Error Común: fetch() no tiene parámetro nativo de timeout; necesita AbortController explícito con setTimeout.
Solución:
const controller = new AbortController();
const timeoutId = setTimeout(() => controller.abort(), 1800000);
const response = await fetch(url, {
signal: controller.signal,
method: 'POST',
body: JSON.stringify(payload)
});
clearTimeout(timeoutId);6. Precedencia de Variable de Entorno
Algunas versiones de OpenClaw pueden usar variables de entorno que sobrescriben los ajustes del archivo de configuración.
Error Común: Vars de entorno como OLLAMA_TIMEOUT están configuradas pero ignoradas.
Solución: Verificar variables de entorno en conflicto:
# List all Ollama/OpenClaw related env vars
env | grep -iE '(OLLAMA|OPENCLAW|TIMEOUT)'
# Ensure no hardcoded timeout values
echo $OLLAMA_HTTP_TIMEOUT # Should be unset or 1800000🔗 Errores Relacionados
Los siguientes errores están comúnmente asociados con el problema de timeout de Ollama:
ECONNABORTED— Código de error de Axios que indica que la solicitud fue abortada debido a timeout. Ocurre cuando el cliente HTTP supera el tiempo de espera antes de recibir una respuesta.ETIMEDOUT— Error de timeout a nivel TCP. Indica timeout de conexión a nivel de red, a menudo a nivel de SO o firewall en lugar de aplicación.ERR_STREAM_PREMATURE_CLOSE— Error de Node.js cuando un stream se cierra antes de completarse. Puede ocurrir si el timeout aborta una respuesta en streaming a mitad de transferencia.Request timeout exceeded— Mensaje genérico de timeout de Ollama/API. El texto exacto varía según la versión de la biblioteca cliente.504 Gateway Timeout— HTTP 504 desde cualquier proxy intermediario (nginx, Cloudflare). Indica que el proxy abandonó la espera de Ollama.context deadline exceeded— Error de timeout gRPC/HTTP2. Puede aparecer si se usa una capa de transporte gRPC en lugar de REST.
Contexto Histórico
Este problema ha sido reportado a través de múltiples versiones de OpenClaw cuando:
- Se usan modelos grandes de Ollama (7B+ parámetros) que requieren mayor tiempo de inferencia
- Se ejecuta en macOS con funciones de ahorro de energía habilitadas
- Se tienen múltiples sesiones concurrentes de Ollama causando presión de memoria
- Se usan ambientes virtualizados (VirtualBox, Docker Desktop) con recursos limitados
Issues Relacionados de GitHub
- #ISSUE-XXXX — Configuración original de timeout no respetada
- #ISSUE-YYYY — Proveedor de Ollama sin opción de timeout en constructor
- #ISSUE-ZZZZ — Timeout de red específico de macOS causando desconexiones prematuras