Files
cortiq-gateway/web/js/i18n/es.js
T
infosave2007 15de36be3b feat: ops & UX batch — jobs survive restarts, logs/system in the console, media queue, gallery, chat, exact stream tokens
Fifteen changes aimed at the first day of real use:

- Import and media jobs persist to <data>/jobs-*.json and reload on start
  (running ones settle as errors); the Register button no longer vanishes
  because the gateway restarted.
- Docker ships the cortiq binary (built in the builder stage) — local .cmf
  chat models and image/video generation now work in containers, where
  auto-install never could (no cargo in the runtime image). libvulkan1 added
  for optional GPU offload.
- Open admin console on 0.0.0.0 without a token now warns in the log and
  shows a dismissible banner — the VPS footgun is at least labeled.
- "Restart gateway" button in Settings: stops managed model servers, spawns
  a fresh copy (bind retried while the port frees), Docker relies on the
  container restart policy instead.
- Dashboard "System" panel: CPU sparkline + load, RAM (with the gateway's
  own RSS), free disk at the models dir — sampled by sysinfo every 2 s.
- Featured model cards warn "not enough disk" / "may not fit in RAM" before
  the download, from the same live snapshot.
- Log viewer in the sidebar: a 500-line in-memory ring fed by a second
  ANSI-free tracing layer; filter, level, pause, copy.
- Update check: crates.io polled twice a day, the console shows an
  "update available" notice.
- Media generations queue up (with position shown) instead of being
  rejected; progress gained an honest ETA from measured throughput.
- Generation gallery under the image/video tabs: lazy PPM thumbnails,
  click to reopen with seed/steps, delete.
- Playground chat is a real dialogue now: history is resent, bubbles,
  Clear, Cmd/Ctrl+Enter.
- "Connect your app" snippets (curl / Python / JS) on the keys page, with
  the real key inlined right after creation.
- One-click benchmark on the Models page via `cortiq bench --json`.
- Config export now downloads the actual gateway.toml (comments intact);
  import accepts TOML (validated, hot-reloaded) and the legacy JSON.
- Streaming token counts are exact when the model server provides usage
  (cortiq-server patch, shipped separately); the gateway fallback now
  counts content chunks (1/token on cortiq) instead of chars/4.

Wizard's Finish lands on the Playground. 37 new strings in all 7 languages.
2026-08-07 17:07:48 +03:00

549 lines
30 KiB
JavaScript
Vendored
Raw Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
// Spanish — traducciones para la consola de administración de allaigate Gateway.
export default {
// brand / common
"brand.sub": "Gateway",
"common.loading": "Cargando…",
"common.save": "Guardar",
"common.saving": "Guardando…",
"common.cancel": "Cancelar",
"common.add": "Agregar",
"common.edit": "Editar",
"common.delete": "Eliminar",
"common.close": "Cerrar",
"common.test": "Probar",
"common.copy": "Copiar",
"common.copied": "Copiado",
"common.confirm": "Confirmar",
"common.none": "ninguno",
"common.saved": "Guardado",
"common.error": "Error",
"common.ok": "OK",
"common.refresh": "Actualizar",
"common.actions": "Acciones",
"common.optional": "opcional",
"common.search": "Buscar",
"common.all": "todos",
// nav
"nav.dashboard": "Panel",
"nav.models": "Modelos",
"nav.routing": "Enrutamiento",
"nav.protocols": "Protocolos",
"nav.keys": "Claves API",
"nav.playground": "Zona de pruebas",
"nav.settings": "Configuración",
"nav.foot": "Gateway · v{v}",
"nav.billing": "Clave del router y pagos",
// topbar / status
"status.router": "Router",
"status.gateway": "Gateway",
"status.online": "en línea",
"status.offline": "sin conexión",
"status.checking": "verificando…",
"status.noKey": "sin clave",
"theme.toggle": "Tema",
"logout": "Cerrar sesión",
// login
"login.title": "allaigate Gateway",
"login.subtitle": "Ingresa el token de administrador para gestionar este gateway.",
"login.token": "Token de administrador",
"login.tokenPlaceholder": "pega el token de administrador",
"login.submit": "Abrir consola",
"login.hint": "El token se imprime en el log del gateway al iniciar, o se configura mediante [admin].token_env.",
"login.failed": "Token de administrador inválido.",
// dashboard
"dash.title": "Panel",
"dash.subtitle": "Tráfico en vivo, costos y análisis de enrutamiento de tu pool de modelos.",
"dash.range": "Rango",
"dash.range.1h": "1h",
"dash.range.24h": "24h",
"dash.range.7d": "7d",
"dash.kpi.requests": "Solicitudes",
"dash.kpi.tokens": "Tokens",
"dash.kpi.cost": "Costo",
"dash.kpi.latency": "Latencia promedio",
"dash.kpi.success": "Tasa de éxito",
"dash.kpi.failovers": "Failovers",
"dash.series.title": "Solicitudes en el tiempo",
"dash.series.cost": "Costo en el tiempo",
"dash.series.empty": "Sin tráfico en este rango.",
"dash.breakdown.title": "Desglose",
"dash.groupby.model": "por modelo",
"dash.groupby.tier": "por nivel",
"dash.groupby.label": "por tarea",
"dash.groupby.account": "por cuenta",
"dash.recent.title": "Solicitudes recientes",
"dash.recent.empty": "Sin solicitudes registradas. Prueba la Zona de pruebas.",
"dash.col.time": "Hora",
"dash.col.model": "Modelo",
"dash.col.tier": "Nivel",
"dash.col.task": "Tarea",
"dash.col.tokens": "Tokens",
"dash.col.cost": "Costo",
"dash.col.latency": "Latencia",
"dash.col.outcome": "Resultado",
"dash.col.requests": "Solicitudes",
"dash.col.errors": "Errores",
"dash.health.title": "Estado",
"dash.health.reachable": "accesible",
"dash.health.unreachable": "inaccesible",
"dash.health.getKey": "Obtener una clave del router",
// models
"models.title": "Modelos",
"models.subtitle": "Tu pool de modelos — combina modelos locales económicos con APIs en la nube.",
"models.add": "Agregar modelo",
"models.empty": "Sin modelos aún. Agrega tu primer modelo para comenzar.",
"models.col.id": "ID",
"models.col.provider": "Proveedor",
"models.col.model": "Modelo",
"models.col.tier": "Nivel de costo",
"models.col.key": "Clave",
"models.col.caps": "Capacidades",
"models.col.price": "Precio (entrada/salida)",
"models.probe": "Sondear",
"models.probe.ok": "Accesible ({ms} ms)",
"models.probe.fail": "Error: {err}",
"models.form.addTitle": "Agregar modelo",
"models.form.editTitle": "Editar modelo",
"models.form.id": "ID",
"models.form.idHint": "ID único usado en enrutamiento, ej. local-qwen",
"models.form.provider": "Proveedor",
"models.form.baseUrl": "URL base",
"models.form.model": "Nombre del modelo",
"models.form.kind": "Tipo",
"models.form.costTier": "Nivel de costo",
"models.form.priceIn": "Precio entrada ($/1M)",
"models.form.priceOut": "Precio salida ($/1M)",
"models.form.apiKeyEnv": "Nombre de variable env para clave API",
"models.form.apiKeyEnvHint": "Nombre de la variable de entorno o secreto que contiene la clave del proveedor.",
"models.form.caps": "Capacidades",
"models.form.secret": "Valor secreto",
"models.form.secretStored": "almacenado",
"models.form.secretEnv": "desde env",
"models.form.secretMissing": "no configurado",
"models.form.secretPlaceholder": "establecer o reemplazar clave (solo escritura)",
"models.deleteConfirm": "¿Eliminar modelo \"{id}\"?",
// routing
"routing.title": "Enrutamiento",
"routing.subtitle": "Asigna niveles de complejidad a una lista ordenada de modelos (prioridad = fallback).",
"routing.default": "Modelo predeterminado",
"routing.defaultHint": "Usado cuando el router no está disponible.",
"routing.tiers": "Niveles",
"routing.tierHint": "Arrastra los chips para reordenar; el primero es preferido, los demás son fallbacks.",
"routing.addModel": "+ agregar",
"routing.addTier": "Agregar nivel",
"routing.tierName": "Nombre del nivel",
"routing.policy": "Política",
"routing.policy.mode": "Modo",
"routing.policy.fixed": "Tabla fija",
"routing.policy.costAware": "Consciente del costo",
"routing.policy.maxCost": "Costo máx. por solicitud ($)",
"routing.policy.minClass": "Clase mínima por nivel",
"routing.empty": "Sin modelos disponibles — agrega modelos primero.",
// protocols
"protocols.title": "Protocolos",
"protocols.subtitle": "Activa solo las APIs de entrada que necesitas. Los cambios se aplican en vivo.",
"protocols.implemented": "implementado",
"protocols.planned": "planificado",
"protocols.openai_chat": "OpenAI Chat Completions",
"protocols.openai_chat.d": "POST /v1/chat/completions — compatible con OpenAI SDK, LangChain, crewAI.",
"protocols.openai_completions": "OpenAI Completions (legacy)",
"protocols.openai_completions.d": "POST /v1/completions — integraciones heredadas.",
"protocols.openai_embeddings": "OpenAI Embeddings",
"protocols.openai_embeddings.d": "POST /v1/embeddings — pipelines RAG.",
"protocols.openai_models": "OpenAI Models",
"protocols.openai_models.d": "GET /v1/models — autodescubrimiento de clientes.",
"protocols.anthropic_messages": "Anthropic Messages",
"protocols.anthropic_messages.d": "POST /v1/messages — agentes nativos Claude.",
"protocols.mcp": "MCP (Model Context Protocol)",
"protocols.mcp.d": "JSON-RPC / SSE — orquestadores nativos MCP.",
"protocols.native_passthrough": "Passthrough nativo",
"protocols.native_passthrough.d": "POST /route — acceso directo a la decisión de enrutamiento.",
// keys
"keys.title": "Claves API",
"keys.subtitle": "Claves de gateway virtuales para tus agentes. Las claves del proveedor nunca salen del gateway.",
"keys.add": "Nueva clave",
"keys.empty": "Sin claves configuradas — el gateway está en modo abierto (sin autenticación).",
"keys.openMode": "Modo abierto: cualquier solicitud es aceptada (no se requiere clave).",
"keys.col.key": "Clave",
"keys.col.account": "Cuenta",
"keys.col.rate": "Límite / min",
"keys.col.models": "Modelos permitidos",
"keys.form.title": "Nueva clave API",
"keys.form.account": "Cuenta",
"keys.form.rate": "Límite de tasa / min",
"keys.form.allow": "Modelos permitidos",
"keys.form.allowHint": "Deja vacío para permitir todos los modelos.",
"keys.form.custom": "Clave personalizada (opcional)",
"keys.form.customHint": "Deja vacío para generar automáticamente sk-gw-…",
"keys.created": "Clave creada — cópiala ahora, no se mostrará de nuevo:",
"keys.revoke": "Revocar",
"keys.revokeConfirm": "¿Revocar esta clave?",
"keys.allowAll": "todos",
// playground
"pg.title": "Zona de pruebas",
"pg.subtitle": "Envía un prompt por el pipeline en vivo e inspecciona la decisión de enrutamiento.",
"pg.system": "Prompt del sistema",
"pg.systemPlaceholder": "mensaje de sistema opcional",
"pg.prompt": "Prompt",
"pg.promptPlaceholder": "Escribe algo…",
"pg.mode": "Modo",
"pg.mode.auto": "Auto (enrutar)",
"pg.mode.pinned": "Modelo fijo",
"pg.profile": "Perfil",
"pg.model": "Modelo",
"pg.temp": "Temperatura",
"pg.maxTokens": "Tokens máx.",
"pg.send": "Enviar",
"pg.stream": "Streaming",
"pg.sending": "Enviando…",
"pg.answer": "Respuesta",
"pg.empty": "La respuesta y la decisión de enrutamiento aparecerán aquí.",
"pg.decision": "Decisión de enrutamiento",
"pg.task": "Tarea",
"pg.tier": "Nivel",
"pg.score": "Complejidad",
"pg.selected": "Modelo seleccionado",
"pg.source": "Fuente de ruta",
"pg.cost": "Costo",
"pg.latency": "Latencia",
"pg.tokens": "Tokens (entrada/salida)",
"pg.failover": "Failover",
"pg.error": "Solicitud fallida",
// settings
"settings.title": "Configuración",
"settings.subtitle": "Conexión del gateway, entrada de enrutamiento, fiabilidad y observabilidad.",
"settings.router": "Conexión del router",
"settings.router.url": "URL del router",
"settings.router.keyEnv": "Nombre de variable env para clave del router",
"settings.router.timeout": "Tiempo de espera (ms)",
"settings.router.verifyTls": "Verificar certificado TLS",
"settings.router.taxonomy": "ID de taxonomía",
"settings.router.getKey": "Obtén o recarga una clave del router en",
"settings.router.secret": "Clave del router (valor)",
"settings.router.test": "Probar router",
"router.probe.ok": "Router OK ({ms} ms)",
"router.probe.noKey": "La clave del router no está configurada",
"router.probe.auth": "Clave rechazada — inválida o revocada",
"router.probe.payment": "Pago requerido — plan vencido o cuota agotada",
"router.probe.quota": "Límite de tasa excedido",
"router.probe.timeout": "Tiempo de espera del router agotado",
"router.probe.unreachable": "Router inaccesible",
"router.probe.error": "Error del router",
"router.usage": "Consumo",
"settings.route": "Entrada de enrutamiento",
"settings.route.strategy": "Estrategia de texto",
"settings.route.maxChars": "Máx. caracteres",
"settings.route.cacheTtl": "TTL de caché",
"settings.route.profile": "Perfil predeterminado",
"settings.breaker": "Circuit breaker",
"settings.breaker.threshold": "Umbral de errores",
"settings.breaker.cooldown": "Cooldown",
"settings.log": "Registro",
"settings.log.level": "Nivel de log",
"settings.log.bodies": "Registrar cuerpos de mensajes (privacidad desactivada)",
"settings.telemetry": "Telemetría",
"settings.telemetry.metrics": "Exponer Prometheus /metrics",
"settings.cortiq": "Metadatos de respuesta",
"settings.cortiq.echo": "Incluir bloque de enrutamiento cortiq en respuestas",
"settings.stats": "Estadísticas",
"settings.stats.enabled": "Registrar estadísticas de solicitudes",
"settings.stats.file": "Archivo de estadísticas (JSONL)",
"settings.stats.retention": "Retención",
"settings.listen": "Dirección de escucha",
"settings.export": "Exportar configuración",
"settings.import": "Importar configuración",
"settings.needsRestart": "Guardado. Algunos cambios (dirección de escucha) requieren reinicio.",
// toasts / misc
"toast.saved": "Cambios guardados",
"toast.deleted": "Eliminado",
"toast.probing": "Sondeando…",
"toast.imported": "Configuración importada",
"dash.cache": "Caché semántico",
"dash.cache.hitRate": "Aciertos",
"dash.cache.hits": "Aciertos",
"dash.cache.saved": "Ahorrado",
"dash.cache.disabled": "El caché semántico está desactivado — actívalo en Ajustes.",
"settings.cache": "Caché semántico",
"settings.cache.enabled": "Activar caché semántico",
"settings.cache.threshold": "Umbral de similitud",
"settings.cache.ttl": "TTL de entrada",
"settings.cache.embed": "Modelo de embeddings",
"settings.cache.note": "Los ajustes del caché se aplican tras reiniciar.",
// ── translated from en.js (previously falling back to English) ──
// nav
"nav.import": "Importar modelo",
// dash
"dash.clear": "Borrar registros",
"dash.clearConfirm": "¿Borrar todas las estadísticas y registros guardados? Esta acción no se puede deshacer.",
"dash.cleared": "Registros borrados",
// models
"models.form.idOrModel": "Introduce un id o un nombre de modelo",
"models.form.apiKey": "Clave API",
"models.form.apiKeyPlaceholder": "pega tu clave API",
"models.form.apiKeyNotNeeded": "no necesaria (servidor local)",
"models.form.apiKeyHint": "Se guarda de forma segura en la pasarela; no se vuelve a mostrar.",
"models.form.keyStored": "Hay una clave guardada — déjalo vacío para conservarla o pega una nueva.",
"models.form.keyFromEnv": "Se está usando una clave de una variable de entorno.",
"models.form.paramsTitle": "Parámetros de generación y razonamiento (O(1), MTP, temperatura)",
"models.form.temperature": "Temperatura",
"models.form.temperatureHint": "Temperatura de generación (0.0 = determinista, 1.0+ = creativa).",
"models.form.topP": "Top-P (muestreo nucleus)",
"models.form.topPHint": "Umbral de muestreo (0.0 .. 1.0).",
"models.form.maxTokens": "Tokens máx.",
"models.form.maxTokensHint": "Número máximo de tokens generados.",
"models.form.thinkBudget": "Modo razonamiento / presupuesto de pensamiento",
"models.form.thinkBudgetHint": "Presupuesto de tokens de razonamiento (0 = desactivado, N > 0 = máximo de tokens de razonamiento).",
"models.form.systemPrompt": "Prompt de sistema por defecto",
"models.form.systemPromptHint": "Se antepone automáticamente si la petición no trae prompt de sistema.",
"models.form.systemPromptPlaceholder": "Eres un asistente útil…",
"models.form.testKey": "Probar y cargar modelos",
"models.form.testing": "comprobando…",
"models.form.foundModels": "{n} modelos cargados",
"models.form.modelPlaceholder": "escribe para buscar…",
"models.form.modelHint": "Pulsa «Probar y cargar modelos» para traer la lista con tu clave y luego elige uno.",
"models.managed": "gestionado",
"models.managedHint": "Lo proporciona el servidor CMF gestionado (Ajustes → Modelos locales). Configúralo allí.",
// settings
"settings.router.enabled": "Usar el router (desactivado = solo modelos locales)",
"settings.cmf": "Modelos locales (CMF)",
"settings.cmf.localOnly": "Usar solo modelos locales",
"settings.cmf.manage": "Ejecutar un servidor de modelo local",
"settings.cmf.autoInstall": "Instalar cortiq automáticamente (crates.io)",
"settings.cmf.autoUpdate": "Actualizar cortiq automáticamente",
"settings.cmf.model": "Ruta del modelo .cmf local",
"settings.cmf.port": "Puerto del servidor local",
"settings.cmf.modelId": "Id del modelo en el pool",
"settings.cmf.note": "Sirve un .cmf local mediante cortiq (github.com/infosave2007/cmf). Funciona incluso cuando el router no está disponible.",
"settings.cmf.threads": "Hilos de trabajo",
"settings.cmf.gpu": "Usar GPU (Metal / wgpu)",
"settings.cmf.speedNote": "Los hilos paralelizan los matvec de decodificación (~3× más rápido; 0 = valor por defecto del runtime). Descargar en GPU ayuda sobre todo al prefill de prompts largos — la decodificación está limitada por el ancho de banda de memoria, así que en Apple Silicon es prácticamente neutro.",
"settings.cmf.pick": "selecciona un modelo",
"settings.cmf.models": "Modelos locales",
"settings.cmf.modelsHelp": "Cada fila es un modelo que la pasarela ejecuta (su propio cortiq serve en su propio puerto) y registra en el pool. Añade tantos como archivos .cmf y puertos libres tengas.",
"settings.cmf.rowHint": "id · archivo .cmf · puerto · hilos · GPU. Los cambios se aplican al reiniciar; borrar una fila detiene ese servidor.",
"settings.cmf.addServer": "+ Añadir modelo local",
"settings.cmf.checkPort": "Comprobar puerto",
"settings.cmf.portFree": "puerto libre",
"settings.cmf.portBusy": "puerto ocupado",
"settings.cmf.useSuggested": "usar {port}",
"settings.cmf.serving": "sirviendo {model} en :{port}",
"settings.cmf.intro": "Ejecuta modelos en local con el motor cortiq — funciona incluso sin conexión o cuando el router está caído.",
"settings.cmf.runtime": "Runtime cortiq",
"settings.cmf.runtimeHelp": "La herramienta de línea de comandos `cortiq` que carga y ejecuta modelos .cmf. Instálala una vez antes de arrancar un servidor local.",
"settings.cmf.install": "Instalar cortiq",
"settings.cmf.reinstall": "Reinstalar / actualizar",
"settings.cmf.installing": "instalando… (compila, unos minutos)",
"settings.cmf.installedOk": "cortiq instalado",
"settings.cmf.notInstalled": "no instalado",
"settings.cmf.addModel": "Añadir un modelo",
"settings.cmf.addModelHelp": "Los modelos se descargan y convierten en la pestaña Importar (HuggingFace → .cmf). Después apunta el servidor local al archivo .cmf de abajo.",
"settings.cmf.importNote": "¿Aún no tienes modelo? Importa uno:",
"settings.cmf.importLink": "Abrir Importar",
"settings.cmf.modelHelp": "Ruta del archivo .cmf que se va a servir (p. ej. models/qwen.cmf), generado en la pestaña Importar. ¿Varios modelos para distintas tareas? Impórtalos y cambia esta ruta.",
"settings.cmf.portHelp": "Puerto TCP en el que escucha el servidor de modelo local (8081 por defecto). Cámbialo solo si choca con otro servicio.",
"settings.cmf.threadsHelp": "Cuántos núcleos de CPU usar para la generación. Más = más rápido (~3× frente a un núcleo); 0 deja que decida el runtime.",
"settings.cmf.gpuHelp": "Descargar el cálculo matricial en la GPU (Metal/wgpu). En Apple Silicon acelera sobre todo los prompts largos — la decodificación está limitada por el ancho de banda de memoria.",
"settings.cmf.localOnlyHelp": "Enviar cada petición al modelo local, ignorando el router y cualquier proveedor en la nube.",
"settings.cmf.manageHelp": "La pasarela arranca `cortiq serve` para el .cmf de abajo al iniciarse y enruta hacia él. Requiere cortiq instalado (paso 1). Se aplica al reiniciar.",
"settings.cmf.autoInstallHelp": "Si cortiq falta al arrancar, instalarlo automáticamente desde crates.io.",
"settings.cmf.autoUpdateHelp": "Al arrancar, actualizar cortiq a la versión más reciente si existe una más nueva.",
"settings.router.enabledHelp": "Dejar que el router de cortiq clasifique cada petición (tipo de tarea + complejidad) y elija un modelo. Desactivado = usar solo la tabla de enrutado local.",
"settings.router.verifyTlsHelp": "Verificar el certificado TLS del router. Desactívalo solo con un certificado autofirmado o ligado a una IP.",
"settings.telemetry.metricsHelp": "Exponer métricas Prometheus en GET /metrics.",
"settings.cortiq.echoHelp": "Añadir un campo `cortiq` (tarea, modelo, coste) al cuerpo de cada respuesta. Las cabeceras de respuesta se envían siempre.",
"settings.stats.enabledHelp": "Registrar las peticiones recientes para alimentar el panel y las gráficas.",
"settings.cache.enabledHelp": "Caché semántica: devolver una respuesta guardada cuando un prompt nuevo se parece mucho a uno anterior, evitando la llamada al modelo. Requiere un modelo de embeddings en el pool.",
"settings.log.bodiesHelp": "Registrar el cuerpo completo de los mensajes de petición y respuesta. Desactivado por defecto por privacidad.",
"settings.router.saveKey": "Guardar clave",
"settings.router.keySaved": "Clave del router guardada",
"settings.router.keyEmpty": "Pega antes la clave",
"settings.router.secretHelp": "Pega la clave del correo de api.allaigate.com y pulsa Guardar clave. NO es un valor de «Claves API» — esas son para los clientes que llaman a tu pasarela.",
"settings.router.keyStoredMask": "•••••••••••• — clave guardada (pega otra para reemplazarla)",
"settings.route.strategyHelp": "Qué texto se envía al router para clasificar: last_user = solo el último mensaje del usuario; last_user_plus_system = último mensaje del usuario + prompt de sistema; concat_all = toda la conversación.",
"settings.route.maxCharsHelp": "Máximo de caracteres de ese texto enviados al router (lo que exceda se recorta). Más = clasificación más precisa, pero llamadas al router más lentas y caras.",
"settings.route.cacheTtlHelp": "Cuánto tiempo se cachea una decisión de enrutado para una petición idéntica antes de volver a preguntar al router (p. ej. 60s, 5m).",
"settings.route.profileHelp": "Perfil de enrutado por defecto cuando la petición no indica ninguno: cost-saver (el más barato), balanced o quality-first (el mejor modelo). Influye en qué modelo elige el router.",
// import
"import.subtitle": "Busca en HuggingFace, convierte a un .cmf local y sírvelo.",
"import.searchPlaceholder": "Buscar modelos en HuggingFace (p. ej. qwen3, llama)…",
"import.searching": "Buscando…",
"import.noResults": "No se encontraron modelos.",
"import.configure": "Configurar la conversión",
"import.outName": "Nombre de salida",
"import.outNameHint": "Nombre del archivo .cmf (letras, dígitos, - y _).",
"import.quant": "Cuantización",
"import.convert": "Convertir y cargar",
"import.converting": "Convirtiendo",
"import.started": "Conversión iniciada",
"import.failed": "La conversión falló — revisa el registro.",
"import.register": "Registrar como modelo local",
"import.registered": "Registrado como «{id}». Ejecuta cortiq-server para servirlo.",
"import.jobs": "Descargas y conversiones",
"import.cancel": "Cancelar",
"import.cancelling": "Cancelando — limpiando el archivo incompleto…",
"import.delete": "Eliminar",
"import.deleteConfirm": "¿Eliminar este modelo y su archivo .cmf convertido del disco?",
"import.deleted": "Eliminado junto con sus archivos",
"import.state.running": "en curso",
"import.state.done": "listo",
"import.state.error": "error",
"import.state.cancelled": "cancelado",
"import.featuredTitle": "Modelos .cmf listos para usar",
"import.featuredSub": "Modelos .cmf ya convertidos de la cuenta infosave en HuggingFace — la lista se lee en vivo, los modelos nuevos aparecen solos.",
"import.readyCmfBadge": ".cmf listo",
"import.directDownload": "Descargar",
"import.q.q8_2f": "8 bits de dos campos (𝒲×θ) — recomendado: mejor relación calidad/tamaño.",
"import.q.q8_row": "8 bits por fila — simple y robusto.",
"import.q.q4": "4 bits por bloque — el más pequeño, menor calidad.",
"import.q.q4_tiled": "4 bits en mosaico (Q4_TILED) — 1,66× más rápido en GPU Metal.",
"import.q.vbit": "Variable 3–8 bits — presupuesto de bits por experto.",
"import.q.q1t": "Ternario de 1,58 bits (Q1T) — BitNet b1.58 con valores atípicos dispersos.",
"import.q.q1s": "1 bit disperso (Q1S) — base de 1 bit con valores atípicos holográficos.",
"import.q.q1p": "1 bit PTQ (Q1P) — 1 bit con difusión de error.",
"import.q.q1": "1 bit (Q1) — formato puramente binario.",
"import.q.f16": "16 bits — sin cuantización.",
"import.q.f32": "32 bits — precisión completa (archivo grande).",
"import.adv.title": "Ajustes avanzados",
"import.adv.auto": "auto",
"import.adv.linearCore": "Núcleo lineal",
"import.adv.linearHint": "Cómo se trasladan o pliegan las capas de atención lineal.",
"import.adv.nphase": "vmf_phase fases/cabeza",
"import.adv.vbitShape": "Forma del presupuesto VBIT",
"import.adv.meanBits": "Bits medios VBIT",
"import.adv.shard": "Tamaño máx. de shard (GB)",
"import.adv.noShard": "sin fragmentar",
"import.adv.skipMtp": "omitir la cabeza MTP",
"import.adv.o1": "Atención O(1)",
"import.adv.o1Hint": "Atención en streaming con memoria constante: la caché KV se libera tras el prefill, así que los contextos largos no hacen crecer la memoria. Los pesos quedan idénticos byte a byte — solo se guarda una indicación para el momento de carga; puedes volver atrás cuando quieras (servir con --o1 off). Validado en Qwen3-0.6B: todas las capas ≈ ×1,18 de perplejidad.",
"import.adv.o1Off": "desactivada — atención exacta (por defecto)",
"import.adv.o1All": "all — convertir todas las capas softmax",
"import.adv.o1Deep": "deep N — solo las N capas más profundas",
"import.adv.o1Custom": "personalizado — lista explícita de capas",
"import.adv.o1DeepN": "N capas profundas",
"import.adv.o1Layers": "Capas (separadas por comas)",
"import.adv.o1mHint": "presupuesto de landmarks (32 por defecto)",
"import.adv.o1windowHint": "ancho de la ventana exacta (128 por defecto)",
"import.adv.o1sinkHint": "claves sink exactas permanentes (4 por defecto)",
// onboarding
"onboarding.title": "Configuración inicial",
"onboarding.welcome": "Bienvenido a Cortiq Gateway",
"onboarding.welcomeSub": "Elige tu idioma — puedes cambiarlo cuando quieras en la cabecera.",
"onboarding.next": "Siguiente",
"onboarding.back": "Atrás",
"onboarding.skip": "Omitir por ahora",
"onboarding.skipSetup": "Omitir",
"onboarding.finish": "Finalizar configuración",
"onboarding.featuredTitle": "Modelos listos para usar (un clic)",
"onboarding.featuredSub": "Son modelos .cmf ya convertidos de infosave en HuggingFace — basta con descargarlos, sin conversión. Elige uno o varios para empezar al instante.",
"onboarding.download": "Descargar",
"onboarding.hfTitle": "Cualquier modelo de HuggingFace — conversión automática",
"onboarding.hfSub": "Busca cualquier modelo, elige una cuantización y lo convertimos a .cmf automáticamente. Sin editar la configuración a mano.",
"onboarding.noJobs": "Todavía no hay descargas.",
"onboarding.doneTitle": "Todo listo",
"onboarding.doneSub": "Los modelos descargados se registrarán automáticamente. Puedes añadir más en Importar o Modelos.",
"onboarding.doneHint": "«Finalizar configuración» conecta cada descarga completada como modelo local, arranca su servidor .cmf y apunta el enrutado hacia él. Todo esto se puede cambiar luego en Modelos.",
"onboarding.willRegister": "Se conectarán como modelos locales",
"onboarding.nothingToRegister": "Aún no hay descargas terminadas — no hay nada que conectar. Vuelve un paso atrás y elige un modelo.",
"onboarding.registeredN": "{n} modelo(s) conectado(s): {ids}",
"onboarding.runtimeMissing": "El runtime cortiq no está instalado — instálalo en Ajustes → Modelos locales para poder servirlos.",
"onboarding.downloaded": "descargado",
"onboarding.update": "Actualizar",
"onboarding.deleteFile": "Eliminar el archivo .cmf del disco",
"onboarding.confirmDelete": "¿Eliminar «{id}»? El archivo .cmf se borrará del disco.",
"onboarding.unregistered": "También se dio de baja: {ids}",
// playground: media generation + streaming metrics
"pg.tab.chat": "Chat",
"pg.tab.image": "Imagen",
"pg.tab.video": "Vídeo",
"pg.generate": "Generar",
"pg.generating": "Generando…",
"pg.genFailed": "La generación falló — revisa el registro.",
"pg.result": "Resultado",
"pg.genMetrics": "Métricas de generación",
"pg.imagePromptPlaceholder": "un zorro rojo en la nieve al atardecer, fotorrealista, pelaje detallado",
"pg.videoPromptPlaceholder": "un corgi con gorro de chef voltea una tortita, chisporroteo y un ladrido alegre",
"pg.imageEmpty": "La imagen generada aparecerá aquí.",
"pg.videoEmpty": "El clip generado (con audio) aparecerá aquí.",
"pg.width": "Ancho",
"pg.height": "Alto",
"pg.steps": "Pasos",
"pg.seed": "Seed",
"pg.randomSeed": "Seed aleatorio",
"pg.cfgHint": "Escala de guidance; ≤ 1 desactiva el CFG y reduce el trabajo a la mitad.",
"pg.frames": "Fotogramas",
"pg.framesHint": "A 24 fps; se ajusta a la rejilla del modelo.",
"pg.quality": "Calidad JPEG",
"pg.videoSizeHint": "Múltiplos de 32; el lado corto entrenado es 768.",
"pg.videoStepsHint": "La LoRA Turbo está entrenada para 4 pasos.",
"pg.firstFrame": "Primer fotograma (opcional)",
"pg.lastFrame": "Último fotograma (opcional)",
"pg.keyframeHint": "Convierte la ejecución en keyframe-to-video.",
"pg.resolution": "Resolución",
"pg.genTime": "Tiempo de generación",
"pg.timePerStep": "Por paso",
"pg.timePerFrame": "Por fotograma",
"pg.fileSize": "Tamaño del archivo",
"pg.duration": "Duración",
"pg.play": "Reproducir",
"pg.noMediaModels": "Aún no hay un modelo {kind} local. Descarga uno (p. ej. de la colección infosave) en Importar:",
"pg.tokSpeed": "Velocidad",
"pg.ttft": "Primer token",
// ops: logs, system, notices, gallery, chat, snippets, bench
"nav.logs": "Registros",
"logs.subtitle": "Registro reciente de la pasarela — lo que mostraría la terminal.",
"logs.filterPlaceholder": "filtrar…",
"logs.pause": "Pausa",
"logs.resume": "Reanudar",
"logs.empty": "Nada coincide.",
"notice.openAdmin": "La consola está abierta sin token y accesible desde otras máquinas. Configura un token si esta máquina no es privada.",
"notice.update": "Actualización disponible: v{v}.",
"dash.sys.title": "Sistema",
"dash.sys.cores": "núcleos",
"dash.sys.disk": "Disco (modelos)",
"dash.sys.free": "libre",
"dash.sys.gateway": "pasarela",
"fit.disk": "no hay espacio suficiente",
"fit.diskTitle": "La descarga supera el espacio libre del disco de modelos.",
"fit.ram": "puede no caber en RAM",
"fit.ramTitle": "El modelo se acerca o supera la RAM de esta máquina — puede que no funcione.",
"pg.eta": "restante",
"pg.min": "min",
"pg.queued": "En cola — posición {n}. Arranca en cuanto termine la generación actual.",
"pg.gallery": "Generaciones recientes",
"pg.galDeleteConfirm": "¿Eliminar esta generación y sus archivos?",
"pg.clearChat": "Limpiar",
"keys.snip.title": "Conecta tu aplicación",
"keys.snip.hint": "Pega uno de estos ejemplos en tu proyecto — solo hay que sustituir el marcador de la clave.",
"keys.snip.withKey": "Los ejemplos de abajo ya incluyen la clave que acabas de crear.",
"keys.snip.openMode": "No hay claves API configuradas — la pasarela acepta cualquier valor.",
"keys.snip.keyPh": "tu clave API",
"settings.restart": "Reiniciar la pasarela",
"settings.restartConfirm": "¿Reiniciar la pasarela? Las peticiones en curso se cortarán; los servidores de modelos locales también se reinician.",
"settings.restarting": "Reiniciando — la página se recargará cuando la pasarela vuelva…",
"bench.title": "Velocidad de modelos locales",
"bench.hint": "Ejecuta `cortiq bench` en esta máquina — tok/s reales, un modelo a la vez.",
"bench.run": "Medir",
"bench.running": "midiendo…",
"bench.failed": "falló",
"bench.none": "Aún no hay modelos de chat .cmf locales.",
};