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.
549 lines
30 KiB
JavaScript
Vendored
549 lines
30 KiB
JavaScript
Vendored
// 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.",
|
||
};
|