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
31 KiB
JavaScript
Vendored
549 lines
31 KiB
JavaScript
Vendored
// French (fr) — same keys as en.js; missing keys fall back to English.
|
||
export default {
|
||
// brand / common
|
||
"brand.sub": "Gateway",
|
||
"common.loading": "Chargement…",
|
||
"common.save": "Enregistrer",
|
||
"common.saving": "Enregistrement…",
|
||
"common.cancel": "Annuler",
|
||
"common.add": "Ajouter",
|
||
"common.edit": "Modifier",
|
||
"common.delete": "Supprimer",
|
||
"common.close": "Fermer",
|
||
"common.test": "Tester",
|
||
"common.copy": "Copier",
|
||
"common.copied": "Copié",
|
||
"common.confirm": "Confirmer",
|
||
"common.none": "aucun",
|
||
"common.saved": "Enregistré",
|
||
"common.error": "Erreur",
|
||
"common.ok": "OK",
|
||
"common.refresh": "Actualiser",
|
||
"common.actions": "Actions",
|
||
"common.optional": "optionnel",
|
||
"common.search": "Rechercher",
|
||
"common.all": "tous",
|
||
|
||
// nav
|
||
"nav.dashboard": "Tableau de bord",
|
||
"nav.models": "Modèles",
|
||
"nav.routing": "Routage",
|
||
"nav.protocols": "Protocoles",
|
||
"nav.keys": "Clés API",
|
||
"nav.playground": "Bac à sable",
|
||
"nav.settings": "Paramètres",
|
||
"nav.foot": "Gateway · v{v}",
|
||
"nav.billing": "Clé routeur & facturation",
|
||
|
||
// topbar / status
|
||
"status.router": "Routeur",
|
||
"status.gateway": "Gateway",
|
||
"status.online": "en ligne",
|
||
"status.offline": "hors ligne",
|
||
"status.checking": "vérification…",
|
||
"status.noKey": "pas de clé",
|
||
"theme.toggle": "Thème",
|
||
"logout": "Déconnexion",
|
||
|
||
// login
|
||
"login.title": "allaigate Gateway",
|
||
"login.subtitle": "Saisissez le jeton administrateur pour gérer cette passerelle.",
|
||
"login.token": "Jeton admin",
|
||
"login.tokenPlaceholder": "coller le jeton admin",
|
||
"login.submit": "Ouvrir la console",
|
||
"login.hint": "Le jeton est affiché dans le log de la passerelle au démarrage, ou défini via [admin].token_env.",
|
||
"login.failed": "Jeton admin invalide.",
|
||
|
||
// dashboard
|
||
"dash.title": "Tableau de bord",
|
||
"dash.subtitle": "Trafic en direct, coûts et analyses de routage pour votre pool de modèles.",
|
||
"dash.range": "Période",
|
||
"dash.range.1h": "1h",
|
||
"dash.range.24h": "24h",
|
||
"dash.range.7d": "7j",
|
||
"dash.kpi.requests": "Requêtes",
|
||
"dash.kpi.tokens": "Tokens",
|
||
"dash.kpi.cost": "Coût",
|
||
"dash.kpi.latency": "Latence moy.",
|
||
"dash.kpi.success": "Taux de succès",
|
||
"dash.kpi.failovers": "Basculements",
|
||
"dash.series.title": "Requêtes dans le temps",
|
||
"dash.series.cost": "Coûts dans le temps",
|
||
"dash.series.empty": "Aucun trafic sur cette période.",
|
||
"dash.breakdown.title": "Répartition",
|
||
"dash.groupby.model": "par modèle",
|
||
"dash.groupby.tier": "par niveau",
|
||
"dash.groupby.label": "par tâche",
|
||
"dash.groupby.account": "par compte",
|
||
"dash.recent.title": "Requêtes récentes",
|
||
"dash.recent.empty": "Aucune requête enregistrée. Essayez le Bac à sable.",
|
||
"dash.col.time": "Heure",
|
||
"dash.col.model": "Modèle",
|
||
"dash.col.tier": "Niveau",
|
||
"dash.col.task": "Tâche",
|
||
"dash.col.tokens": "Tokens",
|
||
"dash.col.cost": "Coût",
|
||
"dash.col.latency": "Latence",
|
||
"dash.col.outcome": "Résultat",
|
||
"dash.col.requests": "Requêtes",
|
||
"dash.col.errors": "Erreurs",
|
||
"dash.health.title": "Santé",
|
||
"dash.health.reachable": "accessible",
|
||
"dash.health.unreachable": "inaccessible",
|
||
"dash.health.getKey": "Obtenir une clé routeur",
|
||
|
||
// models
|
||
"models.title": "Modèles",
|
||
"models.subtitle": "Votre pool de modèles — combinez modèles locaux économiques et API cloud.",
|
||
"models.add": "Ajouter un modèle",
|
||
"models.empty": "Aucun modèle. Ajoutez votre premier modèle pour commencer.",
|
||
"models.col.id": "ID",
|
||
"models.col.provider": "Fournisseur",
|
||
"models.col.model": "Modèle",
|
||
"models.col.tier": "Niveau de coût",
|
||
"models.col.key": "Clé",
|
||
"models.col.caps": "Capacités",
|
||
"models.col.price": "Prix (entrée/sortie)",
|
||
"models.probe": "Sonder",
|
||
"models.probe.ok": "Accessible ({ms} ms)",
|
||
"models.probe.fail": "Échec : {err}",
|
||
"models.form.addTitle": "Ajouter un modèle",
|
||
"models.form.editTitle": "Modifier le modèle",
|
||
"models.form.id": "ID",
|
||
"models.form.idHint": "Identifiant unique utilisé dans le routage, ex. local-qwen",
|
||
"models.form.provider": "Fournisseur",
|
||
"models.form.baseUrl": "URL de base",
|
||
"models.form.model": "Nom du modèle",
|
||
"models.form.kind": "Type",
|
||
"models.form.costTier": "Niveau de coût",
|
||
"models.form.priceIn": "Prix entrée ($/1M)",
|
||
"models.form.priceOut": "Prix sortie ($/1M)",
|
||
"models.form.apiKeyEnv": "Nom de la var. d'env. pour la clé",
|
||
"models.form.apiKeyEnvHint": "Nom de la variable d'env. ou du secret contenant la clé de ce fournisseur.",
|
||
"models.form.caps": "Capacités",
|
||
"models.form.secret": "Valeur secrète",
|
||
"models.form.secretStored": "stocké",
|
||
"models.form.secretEnv": "depuis l'env.",
|
||
"models.form.secretMissing": "non défini",
|
||
"models.form.secretPlaceholder": "définir ou remplacer la clé (écriture seule)",
|
||
"models.deleteConfirm": "Supprimer le modèle \"{id}\" ?",
|
||
|
||
// routing
|
||
"routing.title": "Routage",
|
||
"routing.subtitle": "Associez les niveaux de complexité à une liste ordonnée de modèles (priorité = repli).",
|
||
"routing.default": "Modèle par défaut",
|
||
"routing.defaultHint": "Utilisé lorsque le routeur est inaccessible.",
|
||
"routing.tiers": "Niveaux",
|
||
"routing.tierHint": "Glissez les puces pour réordonner ; le premier est préféré, les autres sont des replis.",
|
||
"routing.addModel": "+ ajouter",
|
||
"routing.addTier": "Ajouter un niveau",
|
||
"routing.tierName": "Nom du niveau",
|
||
"routing.policy": "Politique",
|
||
"routing.policy.mode": "Mode",
|
||
"routing.policy.fixed": "Table fixe",
|
||
"routing.policy.costAware": "Sensible au coût",
|
||
"routing.policy.maxCost": "Coût max par requête ($)",
|
||
"routing.policy.minClass": "Classe minimale par niveau",
|
||
"routing.empty": "Aucun modèle disponible — ajoutez des modèles d'abord.",
|
||
|
||
// protocols
|
||
"protocols.title": "Protocoles",
|
||
"protocols.subtitle": "Activez uniquement les surfaces API entrantes nécessaires. Les bascules s'appliquent en direct.",
|
||
"protocols.implemented": "implémenté",
|
||
"protocols.planned": "planifié",
|
||
"protocols.openai_chat": "OpenAI Chat Completions",
|
||
"protocols.openai_chat.d": "POST /v1/chat/completions — compatible avec OpenAI SDK, LangChain, crewAI.",
|
||
"protocols.openai_completions": "OpenAI Completions (héritage)",
|
||
"protocols.openai_completions.d": "POST /v1/completions — intégrations héritées.",
|
||
"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 — découverte automatique des clients.",
|
||
"protocols.anthropic_messages": "Anthropic Messages",
|
||
"protocols.anthropic_messages.d": "POST /v1/messages — agents natifs Claude.",
|
||
"protocols.mcp": "MCP (Model Context Protocol)",
|
||
"protocols.mcp.d": "JSON-RPC / SSE — orchestrateurs natifs MCP.",
|
||
"protocols.native_passthrough": "Passage natif",
|
||
"protocols.native_passthrough.d": "POST /route — accès direct à la décision de routage.",
|
||
|
||
// keys
|
||
"keys.title": "Clés API",
|
||
"keys.subtitle": "Clés de passerelle virtuelles pour vos agents. Les clés fournisseurs ne quittent jamais la passerelle.",
|
||
"keys.add": "Nouvelle clé",
|
||
"keys.empty": "Aucune clé configurée — la passerelle est en mode ouvert (sans auth).",
|
||
"keys.openMode": "Mode ouvert : toute requête est acceptée (aucune clé requise).",
|
||
"keys.col.key": "Clé",
|
||
"keys.col.account": "Compte",
|
||
"keys.col.rate": "Débit / min",
|
||
"keys.col.models": "Modèles autorisés",
|
||
"keys.form.title": "Nouvelle clé API",
|
||
"keys.form.account": "Compte",
|
||
"keys.form.rate": "Limite de débit / min",
|
||
"keys.form.allow": "Modèles autorisés",
|
||
"keys.form.allowHint": "Laisser vide pour autoriser tous les modèles.",
|
||
"keys.form.custom": "Clé personnalisée (optionnel)",
|
||
"keys.form.customHint": "Laisser vide pour générer automatiquement sk-gw-…",
|
||
"keys.created": "Clé créée — copiez-la maintenant, elle ne sera plus affichée :",
|
||
"keys.revoke": "Révoquer",
|
||
"keys.revokeConfirm": "Révoquer cette clé ?",
|
||
"keys.allowAll": "tous",
|
||
|
||
// playground
|
||
"pg.title": "Bac à sable",
|
||
"pg.subtitle": "Envoyez une invite via le pipeline en direct et inspectez la décision de routage.",
|
||
"pg.system": "Invite système",
|
||
"pg.systemPlaceholder": "message système optionnel",
|
||
"pg.prompt": "Invite",
|
||
"pg.promptPlaceholder": "Posez une question…",
|
||
"pg.mode": "Mode",
|
||
"pg.mode.auto": "Auto (routage)",
|
||
"pg.mode.pinned": "Modèle épinglé",
|
||
"pg.profile": "Profil",
|
||
"pg.model": "Modèle",
|
||
"pg.temp": "Température",
|
||
"pg.maxTokens": "Tokens max",
|
||
"pg.send": "Envoyer",
|
||
"pg.stream": "Streaming",
|
||
"pg.sending": "Envoi…",
|
||
"pg.answer": "Réponse",
|
||
"pg.empty": "La réponse et la décision de routage s'afficheront ici.",
|
||
"pg.decision": "Décision de routage",
|
||
"pg.task": "Tâche",
|
||
"pg.tier": "Niveau",
|
||
"pg.score": "Complexité",
|
||
"pg.selected": "Modèle sélectionné",
|
||
"pg.source": "Source du routage",
|
||
"pg.cost": "Coût",
|
||
"pg.latency": "Latence",
|
||
"pg.tokens": "Tokens (entrée/sortie)",
|
||
"pg.failover": "Basculement",
|
||
"pg.error": "Requête échouée",
|
||
|
||
// settings
|
||
"settings.title": "Paramètres",
|
||
"settings.subtitle": "Connexion passerelle, entrée de routage, fiabilité et observabilité.",
|
||
"settings.router": "Connexion routeur",
|
||
"settings.router.url": "URL du routeur",
|
||
"settings.router.keyEnv": "Nom de l'env. pour la clé du routeur",
|
||
"settings.router.timeout": "Délai d'expiration (ms)",
|
||
"settings.router.verifyTls": "Vérifier le certificat TLS",
|
||
"settings.router.taxonomy": "ID de taxonomie",
|
||
"settings.router.getKey": "Obtenir ou recharger une clé routeur sur",
|
||
"settings.router.secret": "Clé routeur (valeur)",
|
||
"settings.router.test": "Tester le routeur",
|
||
"router.probe.ok": "Routeur OK ({ms} ms)",
|
||
"router.probe.noKey": "La clé routeur n'est pas définie",
|
||
"router.probe.auth": "Clé rejetée — invalide ou révoquée",
|
||
"router.probe.payment": "Paiement requis — forfait expiré ou quota épuisé",
|
||
"router.probe.quota": "Limite de débit dépassée",
|
||
"router.probe.timeout": "Délai du routeur dépassé",
|
||
"router.probe.unreachable": "Routeur inaccessible",
|
||
"router.probe.error": "Erreur du routeur",
|
||
"router.usage": "Consommation",
|
||
"settings.route": "Entrée de routage",
|
||
"settings.route.strategy": "Stratégie de texte",
|
||
"settings.route.maxChars": "Caractères max",
|
||
"settings.route.cacheTtl": "TTL du cache",
|
||
"settings.route.profile": "Profil par défaut",
|
||
"settings.breaker": "Disjoncteur",
|
||
"settings.breaker.threshold": "Seuil d'erreur",
|
||
"settings.breaker.cooldown": "Temporisation",
|
||
"settings.log": "Journalisation",
|
||
"settings.log.level": "Niveau de log",
|
||
"settings.log.bodies": "Journaliser les corps de messages (confidentialité désactivée)",
|
||
"settings.telemetry": "Télémétrie",
|
||
"settings.telemetry.metrics": "Exposer Prometheus /metrics",
|
||
"settings.cortiq": "Métadonnées de réponse",
|
||
"settings.cortiq.echo": "Inclure le bloc de routage cortiq dans les réponses",
|
||
"settings.stats": "Statistiques",
|
||
"settings.stats.enabled": "Enregistrer les statistiques de requêtes",
|
||
"settings.stats.file": "Fichier de stats (JSONL)",
|
||
"settings.stats.retention": "Rétention",
|
||
"settings.listen": "Adresse d'écoute",
|
||
"settings.export": "Exporter la config",
|
||
"settings.import": "Importer la config",
|
||
"settings.needsRestart": "Enregistré. Certains changements (adresse d'écoute) nécessitent un redémarrage.",
|
||
|
||
// toasts / misc
|
||
"toast.saved": "Modifications enregistrées",
|
||
"toast.deleted": "Supprimé",
|
||
"toast.probing": "Sondage…",
|
||
"toast.imported": "Config importée",
|
||
"dash.cache": "Cache sémantique",
|
||
"dash.cache.hitRate": "Taux de succès",
|
||
"dash.cache.hits": "Succès",
|
||
"dash.cache.saved": "Économisé",
|
||
"dash.cache.disabled": "Le cache sémantique est désactivé — activez-le dans les Paramètres.",
|
||
"settings.cache": "Cache sémantique",
|
||
"settings.cache.enabled": "Activer le cache sémantique",
|
||
"settings.cache.threshold": "Seuil de similarité",
|
||
"settings.cache.ttl": "TTL d'entrée",
|
||
"settings.cache.embed": "Modèle d'embeddings",
|
||
"settings.cache.note": "Les paramètres du cache prennent effet après un redémarrage.",
|
||
|
||
// ── translated from en.js (previously falling back to English) ──
|
||
// nav
|
||
"nav.import": "Importer un modèle",
|
||
|
||
// dash
|
||
"dash.clear": "Effacer les journaux",
|
||
"dash.clearConfirm": "Effacer toutes les statistiques et les journaux enregistrés ? Action irréversible.",
|
||
"dash.cleared": "Journaux effacés",
|
||
|
||
// models
|
||
"models.form.idOrModel": "Saisissez un identifiant ou un nom de modèle",
|
||
"models.form.apiKey": "Clé API",
|
||
"models.form.apiKeyPlaceholder": "collez votre clé API",
|
||
"models.form.apiKeyNotNeeded": "non requise (serveur local)",
|
||
"models.form.apiKeyHint": "Stockée de façon sécurisée sur la passerelle ; elle n'est plus affichée ensuite.",
|
||
"models.form.keyStored": "Une clé est enregistrée — laissez vide pour la conserver, ou collez-en une nouvelle.",
|
||
"models.form.keyFromEnv": "Une clé issue d'une variable d'environnement est utilisée.",
|
||
"models.form.paramsTitle": "Paramètres de génération et de raisonnement (O(1), MTP, température)",
|
||
"models.form.temperature": "Température",
|
||
"models.form.temperatureHint": "Température de génération (0.0 = déterministe, 1.0+ = créatif).",
|
||
"models.form.topP": "Top-P (échantillonnage nucleus)",
|
||
"models.form.topPHint": "Seuil d'échantillonnage (0.0 .. 1.0).",
|
||
"models.form.maxTokens": "Tokens max.",
|
||
"models.form.maxTokensHint": "Nombre maximal de tokens générés.",
|
||
"models.form.thinkBudget": "Mode raisonnement / budget de réflexion",
|
||
"models.form.thinkBudgetHint": "Budget de tokens de raisonnement (0 = désactivé, N > 0 = maximum de tokens de raisonnement).",
|
||
"models.form.systemPrompt": "Prompt système par défaut",
|
||
"models.form.systemPromptHint": "Ajouté automatiquement si la requête ne contient pas de prompt système.",
|
||
"models.form.systemPromptPlaceholder": "Vous êtes un assistant utile…",
|
||
"models.form.testKey": "Tester et charger les modèles",
|
||
"models.form.testing": "vérification…",
|
||
"models.form.foundModels": "{n} modèles chargés",
|
||
"models.form.modelPlaceholder": "tapez pour rechercher…",
|
||
"models.form.modelHint": "Cliquez sur « Tester et charger les modèles » pour récupérer la liste liée à votre clé, puis choisissez-en un.",
|
||
"models.managed": "géré",
|
||
"models.managedHint": "Fourni par le serveur CMF géré (Paramètres → Modèles locaux). Configurez-le là-bas.",
|
||
|
||
// settings
|
||
"settings.router.enabled": "Utiliser le routeur (désactivé = modèles locaux uniquement)",
|
||
"settings.cmf": "Modèles locaux (CMF)",
|
||
"settings.cmf.localOnly": "Utiliser uniquement les modèles locaux",
|
||
"settings.cmf.manage": "Lancer un serveur de modèle local",
|
||
"settings.cmf.autoInstall": "Installer cortiq automatiquement (crates.io)",
|
||
"settings.cmf.autoUpdate": "Mettre cortiq à jour automatiquement",
|
||
"settings.cmf.model": "Chemin du modèle .cmf local",
|
||
"settings.cmf.port": "Port du serveur local",
|
||
"settings.cmf.modelId": "Identifiant du modèle dans le pool",
|
||
"settings.cmf.note": "Sert un .cmf local via cortiq (github.com/infosave2007/cmf). Fonctionne même quand le routeur est indisponible.",
|
||
"settings.cmf.threads": "Threads de travail",
|
||
"settings.cmf.gpu": "Utiliser le GPU (Metal / wgpu)",
|
||
"settings.cmf.speedNote": "Les threads parallélisent les matvecs de décodage (~3× plus rapide ; 0 = valeur par défaut du runtime). Le déport GPU aide surtout au prefill des longs prompts — le décodage est limité par la bande passante mémoire, donc sur Apple Silicon l'effet est à peu près neutre.",
|
||
"settings.cmf.pick": "choisir un modèle",
|
||
"settings.cmf.models": "Modèles locaux",
|
||
"settings.cmf.modelsHelp": "Chaque ligne est un modèle que la passerelle exécute (son propre cortiq serve sur son propre port) et enregistre dans le pool. Ajoutez-en autant que vous avez de fichiers .cmf et de ports libres.",
|
||
"settings.cmf.rowHint": "id · fichier .cmf · port · threads · GPU. Les changements prennent effet au redémarrage ; supprimer une ligne arrête ce serveur.",
|
||
"settings.cmf.addServer": "+ Ajouter un modèle local",
|
||
"settings.cmf.checkPort": "Vérifier le port",
|
||
"settings.cmf.portFree": "port libre",
|
||
"settings.cmf.portBusy": "port occupé",
|
||
"settings.cmf.useSuggested": "utiliser {port}",
|
||
"settings.cmf.serving": "{model} servi sur :{port}",
|
||
"settings.cmf.intro": "Exécutez des modèles en local avec le moteur cortiq — fonctionne même hors ligne ou quand le routeur est en panne.",
|
||
"settings.cmf.runtime": "Runtime cortiq",
|
||
"settings.cmf.runtimeHelp": "L'outil en ligne de commande `cortiq` qui charge et exécute les modèles .cmf. Installez-le une fois avant de démarrer un serveur local.",
|
||
"settings.cmf.install": "Installer cortiq",
|
||
"settings.cmf.reinstall": "Réinstaller / mettre à jour",
|
||
"settings.cmf.installing": "installation… (compilation, quelques minutes)",
|
||
"settings.cmf.installedOk": "cortiq installé",
|
||
"settings.cmf.notInstalled": "non installé",
|
||
"settings.cmf.addModel": "Ajouter un modèle",
|
||
"settings.cmf.addModelHelp": "Les modèles se téléchargent et se convertissent dans l'onglet Importer (HuggingFace → .cmf). Faites ensuite pointer le serveur local vers le fichier .cmf ci-dessous.",
|
||
"settings.cmf.importNote": "Pas encore de modèle ? Importez-en un :",
|
||
"settings.cmf.importLink": "Ouvrir Importer",
|
||
"settings.cmf.modelHelp": "Chemin du fichier .cmf à servir (par ex. models/qwen.cmf), produit par l'onglet Importer. Plusieurs modèles pour des tâches différentes ? Importez-les et changez ce chemin.",
|
||
"settings.cmf.portHelp": "Port TCP sur lequel écoute le serveur de modèle local (8081 par défaut). À changer seulement en cas de conflit avec un autre service.",
|
||
"settings.cmf.threadsHelp": "Nombre de cœurs CPU utilisés pour la génération. Plus = plus rapide (~3× par rapport à un seul cœur) ; 0 laisse le runtime décider.",
|
||
"settings.cmf.gpuHelp": "Déporter les calculs matriciels sur le GPU (Metal/wgpu). Sur Apple Silicon, cela accélère surtout les longs prompts — le décodage est limité par la bande passante mémoire.",
|
||
"settings.cmf.localOnlyHelp": "Router chaque requête vers le modèle local, en ignorant le routeur et tous les fournisseurs cloud.",
|
||
"settings.cmf.manageHelp": "Au démarrage, la passerelle lance `cortiq serve` pour le .cmf ci-dessous et y route les requêtes. Nécessite cortiq installé (étape 1). Prend effet au redémarrage.",
|
||
"settings.cmf.autoInstallHelp": "Si cortiq est absent au démarrage, l'installer automatiquement depuis crates.io.",
|
||
"settings.cmf.autoUpdateHelp": "Au démarrage, mettre cortiq à niveau vers la dernière version si elle est plus récente.",
|
||
"settings.router.enabledHelp": "Laisser le routeur cortiq classer chaque requête (type de tâche + complexité) et choisir un modèle. Désactivé = utiliser uniquement la table de routage locale.",
|
||
"settings.router.verifyTlsHelp": "Vérifier le certificat TLS du routeur. À désactiver uniquement pour un certificat auto-signé ou lié à une IP.",
|
||
"settings.telemetry.metricsHelp": "Exposer les métriques Prometheus sur GET /metrics.",
|
||
"settings.cortiq.echoHelp": "Ajouter un champ `cortiq` (tâche, modèle, coût) au corps de chaque réponse. Les en-têtes de réponse sont toujours envoyés.",
|
||
"settings.stats.enabledHelp": "Enregistrer les requêtes récentes pour alimenter le tableau de bord et les graphiques.",
|
||
"settings.cache.enabledHelp": "Cache sémantique : renvoyer une réponse enregistrée quand un nouveau prompt ressemble beaucoup à un précédent, en évitant l'appel au modèle. Nécessite un modèle d'embedding dans le pool.",
|
||
"settings.log.bodiesHelp": "Journaliser le corps complet des messages de requête et de réponse. Désactivé par défaut pour la confidentialité.",
|
||
"settings.router.saveKey": "Enregistrer la clé",
|
||
"settings.router.keySaved": "Clé du routeur enregistrée",
|
||
"settings.router.keyEmpty": "Collez d'abord la clé",
|
||
"settings.router.secretHelp": "Collez la clé reçue par e-mail depuis api.allaigate.com, puis cliquez sur Enregistrer la clé. Ce n'est PAS une valeur de « Clés API » — celles-ci servent aux clients qui appellent votre passerelle.",
|
||
"settings.router.keyStoredMask": "•••••••••••• — clé enregistrée (recollez-en une pour la remplacer)",
|
||
"settings.route.strategyHelp": "Texte envoyé au routeur pour la classification : last_user = uniquement le dernier message utilisateur ; last_user_plus_system = dernier message utilisateur + prompt système ; concat_all = toute la conversation.",
|
||
"settings.route.maxCharsHelp": "Nombre maximal de caractères de ce texte envoyés au routeur (au-delà, il est tronqué). Plus = classification plus précise, mais appels au routeur plus lents et plus coûteux.",
|
||
"settings.route.cacheTtlHelp": "Durée de mise en cache d'une décision de routage pour une requête identique avant de réinterroger le routeur (par ex. 60s, 5m).",
|
||
"settings.route.profileHelp": "Profil de routage par défaut quand la requête n'en précise aucun : cost-saver (le moins cher), balanced ou quality-first (meilleur modèle). Influence le modèle choisi par le routeur.",
|
||
|
||
// import
|
||
"import.subtitle": "Cherchez sur HuggingFace, convertissez en .cmf local et servez-le.",
|
||
"import.searchPlaceholder": "Rechercher des modèles HuggingFace (par ex. qwen3, llama)…",
|
||
"import.searching": "Recherche…",
|
||
"import.noResults": "Aucun modèle trouvé.",
|
||
"import.configure": "Configurer la conversion",
|
||
"import.outName": "Nom de sortie",
|
||
"import.outNameHint": "Nom du fichier .cmf (lettres, chiffres, - et _).",
|
||
"import.quant": "Quantification",
|
||
"import.convert": "Convertir et charger",
|
||
"import.converting": "Conversion",
|
||
"import.started": "Conversion lancée",
|
||
"import.failed": "Échec de la conversion — voir le journal.",
|
||
"import.register": "Enregistrer comme modèle local",
|
||
"import.registered": "Enregistré sous « {id} ». Lancez cortiq-server pour le servir.",
|
||
"import.jobs": "Téléchargements et conversions",
|
||
"import.cancel": "Annuler",
|
||
"import.cancelling": "Annulation — nettoyage du fichier incomplet…",
|
||
"import.delete": "Supprimer",
|
||
"import.deleteConfirm": "Supprimer ce modèle et son fichier .cmf converti du disque ?",
|
||
"import.deleted": "Supprimé avec ses fichiers",
|
||
"import.state.running": "en cours",
|
||
"import.state.done": "terminé",
|
||
"import.state.error": "erreur",
|
||
"import.state.cancelled": "annulé",
|
||
"import.featuredTitle": "Modèles .cmf prêts à l'emploi",
|
||
"import.featuredSub": "Modèles .cmf déjà convertis du compte infosave sur HuggingFace — la liste est lue en direct, les nouveaux modèles apparaissent d'eux-mêmes.",
|
||
"import.readyCmfBadge": ".cmf prêt",
|
||
"import.directDownload": "Télécharger",
|
||
"import.q.q8_2f": "8 bits à deux champs (𝒲×θ) — recommandé : meilleur rapport qualité/taille.",
|
||
"import.q.q8_row": "8 bits par ligne — simple et robuste.",
|
||
"import.q.q4": "4 bits par bloc — le plus compact, qualité moindre.",
|
||
"import.q.q4_tiled": "4 bits en tuiles (Q4_TILED) — 1,66× plus rapide sur GPU Metal.",
|
||
"import.q.vbit": "Variable 3–8 bits — budget de bits par expert.",
|
||
"import.q.q1t": "Ternaire 1,58 bit (Q1T) — BitNet b1.58 avec valeurs aberrantes éparses.",
|
||
"import.q.q1s": "1 bit épars (Q1S) — base 1 bit avec valeurs aberrantes holographiques.",
|
||
"import.q.q1p": "1 bit PTQ (Q1P) — 1 bit avec diffusion d'erreur.",
|
||
"import.q.q1": "1 bit (Q1) — format purement binaire.",
|
||
"import.q.f16": "16 bits — sans quantification.",
|
||
"import.q.f32": "32 bits — pleine précision (fichier volumineux).",
|
||
"import.adv.title": "Paramètres avancés",
|
||
"import.adv.auto": "auto",
|
||
"import.adv.linearCore": "Cœur linéaire",
|
||
"import.adv.linearHint": "Comment les couches d'attention linéaire sont reportées ou fusionnées.",
|
||
"import.adv.nphase": "vmf_phase phases/tête",
|
||
"import.adv.vbitShape": "Forme du budget VBIT",
|
||
"import.adv.meanBits": "Bits moyens VBIT",
|
||
"import.adv.shard": "Taille max. des shards (Go)",
|
||
"import.adv.noShard": "pas de découpage",
|
||
"import.adv.skipMtp": "ignorer la tête MTP",
|
||
"import.adv.o1": "Attention O(1)",
|
||
"import.adv.o1Hint": "Attention en flux à mémoire constante : le cache KV est libéré après le prefill, la mémoire ne croît donc pas avec de longs contextes. Les poids restent identiques octet pour octet — seule une indication de chargement est enregistrée ; vous pouvez revenir en arrière à tout moment (servir avec --o1 off). Validé sur Qwen3-0.6B : toutes couches ≈ ×1,18 de perplexité.",
|
||
"import.adv.o1Off": "désactivé — attention exacte (par défaut)",
|
||
"import.adv.o1All": "all — convertir chaque couche softmax",
|
||
"import.adv.o1Deep": "deep N — seulement les N couches les plus profondes",
|
||
"import.adv.o1Custom": "personnalisé — liste explicite de couches",
|
||
"import.adv.o1DeepN": "N couches profondes",
|
||
"import.adv.o1Layers": "Couches (séparées par des virgules)",
|
||
"import.adv.o1mHint": "budget de landmarks (32 par défaut)",
|
||
"import.adv.o1windowHint": "largeur de la fenêtre exacte (128 par défaut)",
|
||
"import.adv.o1sinkHint": "clés sink exactes permanentes (4 par défaut)",
|
||
|
||
// onboarding
|
||
"onboarding.title": "Configuration initiale",
|
||
"onboarding.welcome": "Bienvenue dans Cortiq Gateway",
|
||
"onboarding.welcomeSub": "Choisissez votre langue — vous pourrez la changer à tout moment dans l'en-tête.",
|
||
"onboarding.next": "Suivant",
|
||
"onboarding.back": "Retour",
|
||
"onboarding.skip": "Passer pour l'instant",
|
||
"onboarding.skipSetup": "Passer",
|
||
"onboarding.finish": "Terminer la configuration",
|
||
"onboarding.featuredTitle": "Modèles prêts à l'emploi (en un clic)",
|
||
"onboarding.featuredSub": "Ce sont des modèles .cmf déjà convertis, publiés par infosave sur HuggingFace — il suffit de les télécharger, aucune conversion nécessaire. Choisissez-en un ou plusieurs pour démarrer immédiatement.",
|
||
"onboarding.download": "Télécharger",
|
||
"onboarding.hfTitle": "N'importe quel modèle HuggingFace — conversion automatique",
|
||
"onboarding.hfSub": "Cherchez un modèle, choisissez une quantification, et nous le convertissons automatiquement en .cmf. Aucune modification manuelle de la configuration.",
|
||
"onboarding.noJobs": "Aucun téléchargement pour l'instant.",
|
||
"onboarding.doneTitle": "Tout est prêt",
|
||
"onboarding.doneSub": "Les modèles téléchargés seront enregistrés automatiquement. Vous pourrez en ajouter d'autres dans Importer ou Modèles.",
|
||
"onboarding.doneHint": "« Terminer la configuration » connecte chaque téléchargement achevé comme modèle local, démarre son serveur .cmf et y dirige le routage. Tout cela reste modifiable ensuite dans Modèles.",
|
||
"onboarding.willRegister": "Seront connectés comme modèles locaux",
|
||
"onboarding.nothingToRegister": "Aucun téléchargement terminé — rien à connecter. Revenez à l'étape précédente pour choisir un modèle.",
|
||
"onboarding.registeredN": "{n} modèle(s) connecté(s) : {ids}",
|
||
"onboarding.runtimeMissing": "Le runtime cortiq n'est pas installé — installez-le dans Paramètres → Modèles locaux pour les servir.",
|
||
"onboarding.downloaded": "téléchargé",
|
||
"onboarding.update": "Mettre à jour",
|
||
"onboarding.deleteFile": "Supprimer le fichier .cmf du disque",
|
||
"onboarding.confirmDelete": "Supprimer « {id} » ? Le fichier .cmf sera retiré du disque.",
|
||
"onboarding.unregistered": "Également désenregistré : {ids}",
|
||
|
||
// playground: media generation + streaming metrics
|
||
"pg.tab.chat": "Chat",
|
||
"pg.tab.image": "Image",
|
||
"pg.tab.video": "Vidéo",
|
||
"pg.generate": "Générer",
|
||
"pg.generating": "Génération…",
|
||
"pg.genFailed": "Échec de la génération — voir le journal.",
|
||
"pg.result": "Résultat",
|
||
"pg.genMetrics": "Métriques de génération",
|
||
"pg.imagePromptPlaceholder": "un renard roux dans la neige au coucher du soleil, photoréaliste, fourrure détaillée",
|
||
"pg.videoPromptPlaceholder": "un corgi en toque de chef fait sauter une crêpe, grésillements et aboiement joyeux",
|
||
"pg.imageEmpty": "L'image générée apparaîtra ici.",
|
||
"pg.videoEmpty": "Le clip généré (avec le son) apparaîtra ici.",
|
||
"pg.width": "Largeur",
|
||
"pg.height": "Hauteur",
|
||
"pg.steps": "Étapes",
|
||
"pg.seed": "Seed",
|
||
"pg.randomSeed": "Seed aléatoire",
|
||
"pg.cfgHint": "Force du guidance ; ≤ 1 désactive le CFG et divise le travail par deux.",
|
||
"pg.frames": "Images",
|
||
"pg.framesHint": "À 24 fps ; arrondi à la grille du modèle.",
|
||
"pg.quality": "Qualité JPEG",
|
||
"pg.videoSizeHint": "Multiples de 32 ; le petit côté entraîné est 768.",
|
||
"pg.videoStepsHint": "La LoRA Turbo est entraînée pour 4 étapes.",
|
||
"pg.firstFrame": "Première image (optionnel)",
|
||
"pg.lastFrame": "Dernière image (optionnel)",
|
||
"pg.keyframeHint": "Transforme la génération en keyframe-to-video.",
|
||
"pg.resolution": "Résolution",
|
||
"pg.genTime": "Temps de génération",
|
||
"pg.timePerStep": "Par étape",
|
||
"pg.timePerFrame": "Par image",
|
||
"pg.fileSize": "Taille du fichier",
|
||
"pg.duration": "Durée",
|
||
"pg.play": "Lire",
|
||
"pg.noMediaModels": "Pas encore de modèle {kind} local. Téléchargez-en un (par ex. de la collection infosave) dans Importer :",
|
||
"pg.tokSpeed": "Vitesse",
|
||
"pg.ttft": "Premier token",
|
||
|
||
// ops: logs, system, notices, gallery, chat, snippets, bench
|
||
"nav.logs": "Journaux",
|
||
"logs.subtitle": "Journal récent de la passerelle — ce que montrerait le terminal.",
|
||
"logs.filterPlaceholder": "filtrer…",
|
||
"logs.pause": "Pause",
|
||
"logs.resume": "Reprendre",
|
||
"logs.empty": "Rien ne correspond.",
|
||
"notice.openAdmin": "La console est ouverte sans jeton et accessible depuis d'autres machines. Définissez un jeton si cette machine n'est pas privée.",
|
||
"notice.update": "Mise à jour disponible : v{v}.",
|
||
"dash.sys.title": "Système",
|
||
"dash.sys.cores": "cœurs",
|
||
"dash.sys.disk": "Disque (modèles)",
|
||
"dash.sys.free": "libre",
|
||
"dash.sys.gateway": "passerelle",
|
||
"fit.disk": "espace disque insuffisant",
|
||
"fit.diskTitle": "Le téléchargement dépasse l'espace libre du disque des modèles.",
|
||
"fit.ram": "risque de ne pas tenir en RAM",
|
||
"fit.ramTitle": "Le modèle approche ou dépasse la RAM de cette machine — il pourrait ne pas tourner.",
|
||
"pg.eta": "restant",
|
||
"pg.min": "min",
|
||
"pg.queued": "En file d'attente — position {n}. Démarre dès la fin de la génération en cours.",
|
||
"pg.gallery": "Générations récentes",
|
||
"pg.galDeleteConfirm": "Supprimer cette génération et ses fichiers ?",
|
||
"pg.clearChat": "Effacer",
|
||
"keys.snip.title": "Connecter votre application",
|
||
"keys.snip.hint": "Collez un de ces exemples dans votre projet — seul le espace réservé de la clé est à remplacer.",
|
||
"keys.snip.withKey": "Les exemples ci-dessous incluent la clé que vous venez de créer.",
|
||
"keys.snip.openMode": "Aucune clé API configurée — la passerelle accepte n'importe quelle valeur.",
|
||
"keys.snip.keyPh": "votre clé API",
|
||
"settings.restart": "Redémarrer la passerelle",
|
||
"settings.restartConfirm": "Redémarrer la passerelle ? Les requêtes en cours seront coupées ; les serveurs de modèles locaux redémarrent aussi.",
|
||
"settings.restarting": "Redémarrage — la page se recharge dès que la passerelle revient…",
|
||
"bench.title": "Vitesse des modèles locaux",
|
||
"bench.hint": "Exécute `cortiq bench` sur cette machine — de vrais tok/s, un modèle à la fois.",
|
||
"bench.run": "Mesurer",
|
||
"bench.running": "mesure…",
|
||
"bench.failed": "échec",
|
||
"bench.none": "Pas encore de modèles de chat .cmf locaux.",
|
||
};
|