chain-studio/lib/l10n/app_en.arb
flemming-it 5313266cc4 feat(studio): first-run UX, recovery affordances, l10n, bundled fonts
- Connection-aware Welcome: when the hub is down, show a hero with a
  primary "Start hub" CTA + install fallback instead of a dead,
  all-unchecked onboarding checklist (the first-run cliff).
- Actionable binary-not-found (file picker + install link, not a
  "set FAI_BIN" dead end) and a connect-failure banner after
  repeated failed health polls.
- Localize six hardcoded English error/toast clusters (DE+EN ARB).
- Bundle Inter + JetBrains Mono as assets; drop the runtime
  google_fonts fetch (air-gap / KRITIS safe, no font-swap flash).

Signed-off-by: flemming-it <stefan.a.flemming@googlemail.com>
2026-06-11 23:52:18 +02:00

1601 lines
58 KiB
Text
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.

{
"@@locale": "en",
"appTitle": "F∆I Studio",
"@appTitle": {
"description": "App-bar title in the OS task switcher."
},
"navWelcome": "Welcome",
"welcomeHeroTitle": "F∆I Platform",
"welcomeHeroSubtitle": "Deterministic workflow engine for AI-assisted document processing in regulated environments.",
"welcomePillarHubTitle": "Hub",
"welcomePillarHubBody": "One Rust binary that loads modules and runs flows. SQLite for state. No Docker, no message broker, no background services to babysit.",
"welcomePillarModuleTitle": "Module",
"welcomePillarModuleBody": "A small WebAssembly component that does one thing. Declares the network endpoints, files, and environment variables it touches; the hub enforces the list.",
"welcomePillarFlowTitle": "Flow",
"welcomePillarFlowBody": "A YAML file that chains modules together. Inputs go in, modules run in declared order, outputs come out — every step recorded in a hash-chained audit log.",
"welcomeTrustHeader": "TRUST POSTURE",
"welcomeTrustSandboxTitle": "Sandbox by default",
"welcomeTrustSandboxBody": "Every module ships with an explicit permission list — network endpoints, files, environment variables. The hub enforces it; nothing reaches outside the sandbox without operator approval.",
"welcomeTrustAuditTitle": "Tamper-evident audit log",
"welcomeTrustAuditBody": "Flow runs, install / uninstall actions, approval decisions — all of them write into a hash-chained audit log. The Doctor page verifies the chain end-to-end on every load.",
"welcomeTrustAirgapTitle": "Air-gap ready",
"welcomeTrustAirgapBody": "The whole hub fits in a single binary that runs on Linux, macOS and Windows. Once a module is installed, the flow it powers runs without further network access — perfect for regulated environments.",
"welcomeDocsHeader": "DOCUMENTATION",
"welcomeDocsBody": "Operator-facing explainers, rendered inline. No browser, no external link — air-gap-friendly.",
"welcomeDocArchitectureTitle": "Architecture in one paragraph",
"welcomeDocArchitectureBlurb": "Hub, Module, Flow — and how the three fit together.",
"welcomeDocSecurityTitle": "Sandbox model",
"welcomeDocSecurityBlurb": "What a module declares, what the operator caps, what the hub enforces.",
"welcomeDocAuditTitle": "Tamper-evident audit log",
"welcomeDocAuditBlurb": "How the hash chain works and why WORM-1 is enough for KRITIS.",
"welcomeDocFlowsTitle": "Flow composition",
"welcomeDocFlowsBlurb": "YAML basics, templating reference, the extract→summarize example.",
"welcomeDocApprovalsTitle": "Approvals",
"welcomeDocApprovalsBlurb": "Human-in-the-loop checkpoints — when to use them, how the audit log records them.",
"helpTooltip": "Help",
"errApprovalRejected": "Approval rejected by reviewer.",
"errApprovalRejectedHint": "The reviewer marked this step as rejected. Check the audit log for the reviewer's reason.",
"errApprovalTimedOut": "Approval timed out.",
"errApprovalTimedOutHint": "No reviewer decided within the configured time. Raise `timeout_seconds` on the approval step or alert the reviewer.",
"errOutputTooLarge": "Step output exceeded the size limit.",
"errOutputTooLargeHint": "Either trim the output (truncate text, downsample bytes) or raise `max_output_size_mb` in the operator config.",
"errServiceUnavailableForStep": "Host service not configured.",
"errServiceUnavailableForStepHint": "The module requires a service (e.g. ollama, playwright) the operator hasn't declared. Add it under `services:` in ~/.fai/config.yaml.",
"errMissingValue": "Required value is missing.",
"errMissingValueHint": "The step expected an input that wasn't wired up — either supply it at run time or fix the upstream `$ref`.",
"errMcpUnreachable": "MCP endpoint unreachable.",
"errMcpUnreachableHint": "The MCP server didn't respond. Check the endpoint in Settings → Integrations and confirm it's running.",
"errCapabilityNotInstalled": "Required capability is not installed.",
"errCapabilityNotInstalledHint": "Open the flow's Text tab — the analyzer's Fix button installs the capability if it's in the store.",
"welcomeDocClose": "Close",
"welcomeDocFailedToLoad": "Could not load documentation: {error}",
"@welcomeDocFailedToLoad": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"welcomeChecklistHeader": "GETTING STARTED",
"welcomeChecklistBody": "Four steps to a working hub. Live state — refresh after changing anything.",
"welcomeChecklistAi": "Configure System AI",
"welcomeChecklistAiHint": "Settings → System AI. Required for the AI search and inline failure explanations.",
"welcomeChecklistMcp": "Add a public capability source",
"welcomeChecklistMcpHint": "Add an MCP source from the Store, or configure one under Settings → MCP Clients.",
"welcomeChecklistModule": "Install a text module",
"welcomeChecklistModuleHint": "Install a module from the Store — pick whichever category fits your work. Modules are sandboxed F∆I components.",
"welcomeChecklistFlow": "Run a saved flow",
"welcomeChecklistFlowHint": "Flows → pick one → Run. Studio ships a few demo flows; one of your own works too.",
"welcomeChecklistAllDone": "All four steps complete.",
"welcomeChecklistDismiss": "Hide checklist",
"welcomeChecklistRefresh": "Refresh",
"welcomeChecklistRefreshing": "Checking…",
"welcomeChecklistDone": "Done",
"welcomeChecklistTodo": "Pending",
"navDoctor": "Doctor",
"navModules": "Modules",
"navStore": "Store",
"navFlows": "Flows",
"navAudit": "Audit",
"navApprovals": "Approvals",
"connectionConnected": "connected",
"connectionUnreachable": "unreachable",
"connectionConnecting": "connecting…",
"connectionStartHub": "Start hub",
"connectionTapToStart": "tap to start",
"sidebarSettingsTooltip": "Settings (⌘;)",
"sidebarChannelTooltip": "Active channel — click to switch in Settings (⌘;).\nproduction = stable · beta = pre-release · dev = rolling · local = workspace",
"buttonCancel": "Cancel",
"buttonSave": "Save",
"buttonClose": "Close",
"buttonRetry": "Retry",
"buttonRefresh": "Refresh",
"buttonInstall": "Install",
"buttonUninstall": "Uninstall",
"buttonDetails": "Details",
"buttonAdd": "Add",
"buttonRemove": "Remove",
"buttonOpen": "Open",
"buttonExplain": "Explain",
"buttonReadDocs": "Read docs",
"buttonCopy": "Copy to clipboard",
"buttonCopied": "Copied",
"buttonShowDetails": "Show details",
"buttonHideDetails": "Hide details",
"storeInstallableOnly": "Installable only",
"storePillComingSoon": "Coming soon",
"storeNotInstallableInline": "This module is on the roadmap (status: {status}). It has no installable bundle yet — follow the repository for updates.",
"@storeNotInstallableInline": {
"placeholders": {
"status": {
"type": "String"
}
}
},
"mcpSuggestionDeepwikiDesc": "Public HTTPS — GitHub repo documentation search (AI-powered). No Node, no API key.",
"mcpSuggestionSemgrepDesc": "Public HTTPS — security scanning for code vulnerabilities. No Node, no API key.",
"mcpSuggestionFilesystemDesc": "Anthropic — read / write files in /tmp. Edit the path before saving.",
"mcpSuggestionFetchDesc": "Anthropic — fetch arbitrary HTTP(S) URLs as markdown.",
"mcpSuggestionGithubDesc": "Anthropic — issues, PRs, repo files. Needs a GitHub PAT in the env var.",
"mcpSuggestionPuppeteerDesc": "Anthropic — headless browser automation for screenshots / scraping.",
"mcpSuggestionPostgresDesc": "Anthropic — read-only SQL queries against a Postgres database. Edit the URL.",
"mcpSuggestionSqliteDesc": "Anthropic — query a local SQLite file. Edit the path.",
"mcpSuggestionBraveSearchDesc": "Anthropic — web search via Brave. API key required.",
"mcpSuggestionMemoryDesc": "Anthropic — persistent knowledge graph for an agent's memory.",
"mcpSuggestionTimeDesc": "Anthropic — current time + timezone conversion.",
"mcpServerEnLanguageBadge": "Server text in English — Studio shows it as supplied.",
"themePluginHeader": "Theme plugin (applies instantly)",
"themeApplied": "Theme applied: {name}",
"@themeApplied": {
"placeholders": {
"name": {"type": "String"}
}
},
"themePluginFailed": "Theme plugin could not load — keeping previous theme.",
"themePluginNone": "Built-in (no plugin)",
"themePluginHint": "Built-in and plugin tiles ship hand-curated palettes. The Custom tile derives a full Material 3 palette (primary, secondary, tertiary, surface, …) from one seed colour you pick — it's a complete theme, not a single-colour tweak.",
"themePluginEmpty": "No theme plugins installed. Open the Store and pick one in the studio-plugin category.",
"themePluginCustom": "Custom colour",
"themePluginCustomDialogTitle": "Custom theme — pick a seed colour",
"themePluginCustomHexLabel": "Hex colour",
"themePluginCustomPreview": "Live preview",
"themePluginCustomCancel": "Cancel",
"themePluginCustomApply": "Apply",
"settingsTitle": "Hub endpoint",
"settingsHost": "Host",
"settingsPort": "Port",
"settingsTls": "TLS",
"settingsSaveAndConnect": "Connect to endpoint",
"settingsLanguage": "Language",
"settingsLanguageHint": "App language. Affects every page; bilingual store entries also flip via this toggle.",
"settingsHubEndpointHint": "Where should Studio connect? Default is the local hub at 127.0.0.1:50051.",
"settingsTlsSubtitle": "https/grpc-secure",
"settingsPortError": "port must be 165535",
"channelsBlurb": "Switch hub channel (writes ~/.fai/current-channel and restarts the daemon). Connect just changes Studio's wire.",
"channelsActionsTooltip": "Channel actions",
"systemAiHeader": "SYSTEM AI",
"systemAiEnabled": "enabled",
"systemAiOff": "off",
"systemAiEdit": "Edit…",
"systemAiConfigure": "Configure…",
"systemAiOffBlurb": "Off — failure explanations on the audit page are disabled. Click Configure… to pick a provider (Ollama / OpenAI / LM Studio / vLLM / Custom). Operator config is rewritten in place; no daemon restart needed.",
"mcpServersCount": "{n} {n, plural, =1{server} other{servers}}",
"@mcpServersCount": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"mcpRediscoverTooltip": "Re-run discovery",
"mcpAddTooltip": "Add MCP server",
"mcpRemoveTooltip": "Remove server",
"mcpToolsCount": "{n} {n, plural, =1{tool} other{tools}}",
"@mcpToolsCount": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"n8nEndpointsCount": "{n} {n, plural, =1{endpoint} other{endpoints}}",
"@n8nEndpointsCount": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"n8nWorkflowsCount": "{n} {n, plural, =1{workflow} other{workflows}}",
"@n8nWorkflowsCount": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"n8nRediscoverTooltip": "Re-run discovery",
"n8nAddTooltip": "Add n8n endpoint",
"n8nRemoveTooltip": "Remove endpoint",
"addMcpTitle": "Add MCP server",
"addMcpIntro": "Tools the server advertises via `tools/list` appear in the Store as `mcp.<name>.<tool>` capabilities.",
"addMcpSuggestionsLabel": "Suggested servers — click to pre-fill",
"addMcpNameLabel": "Name (no dots)",
"addMcpNameHint": "filesystem",
"addMcpEndpointLabel": "Endpoint",
"addMcpEndpointHint": "http://127.0.0.1:3001/mcp",
"addMcpApiKeyLabel": "API key env var (optional)",
"addMcpApiKeyHint": "MCP_FILESYSTEM_TOKEN",
"addMcpNotesLabel": "Notes (optional)",
"addMcpAddButton": "Add + discover",
"addN8nTitle": "Add n8n endpoint",
"addN8nIntro": "Active workflows surface in the Store as `n8n.<name>.<workflow_slug>` capabilities.",
"addN8nNameLabel": "Name (no dots)",
"addN8nNameHint": "ops",
"addN8nBaseUrlLabel": "Base URL (without /api/v1)",
"addN8nBaseUrlHint": "https://n8n.example.com",
"addN8nApiKeyLabel": "API key env var (optional)",
"addN8nApiKeyHint": "N8N_OPS_KEY",
"addN8nNotesLabel": "Notes (optional)",
"addN8nAddButton": "Add + discover",
"addedMcpToast": "Added MCP server \"{name}\".",
"@addedMcpToast": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"addedN8nToast": "Added n8n endpoint \"{name}\".",
"@addedN8nToast": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"addFailedToast": "Add failed: {error}",
"@addFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"removeFailedToast": "Remove failed: {error}",
"@removeFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"refreshFailedToast": "Refresh failed: {error}",
"@refreshFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"channelsHeader": "CHANNELS",
"channelsActive": "active",
"channelsRunning": "running",
"channelsStopped": "stopped",
"channelsConnect": "Connect Studio to this channel",
"channelsSwitch": "Make this the active channel",
"channelsEnableAutostart": "Enable autostart at login",
"channelsDisableAutostart": "Disable autostart",
"storeSearchHint": "Search modules — name, tagline, tag, capability…",
"storeAskHint": "What do you need? Try \"a module that reads tabular data\" or just type a keyword.",
"storeAskSubmit": "Search",
"storeAskAi": "Ask the AI",
"storeAskClear": "Clear question",
"storeAskAiThinking": "Looking through modules…",
"storeAskAiUnavailable": "Configure a System AI in Settings to ask questions in plain language.",
"storeAskNoMatches": "No matches yet — refine the question or browse the grid below.",
"storeAskAnswerLabel": "AI suggestion",
"storeAskAnswerWhy": "Why this matches",
"storeAskMatchPill": "match",
"storeFilterLabel": "Filter",
"storeFilterActiveCount": "{n} active",
"@storeFilterActiveCount": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"storeFilterReset": "Reset filters",
"storeFilterApply": "Done",
"storeFilterStatusGroup": "Status",
"storeFilterSourceGroup": "Source",
"storeFilterInstalledGroup": "Show only installed",
"storeFeatured": "FEATURED",
"storeFeaturedHint": "curated picks · click for details",
"storeNoMatches": "No matches",
"storeNoMatchesHint": "Adjust the filters or clear the search to see all entries.",
"storeClearFilters": "Clear filters",
"storeStatusAll": "All",
"storeStatusPublished": "stable",
"storeStatusAlpha": "experimental",
"storeStatusPlanned": "coming soon",
"storeInstalledOnly": "Installed",
"storeCategoryLabel": "Category",
"storeCategoryAll": "All categories",
"storeCategoryBridge": "Connectors",
"storeCategoryDebug": "Sample modules",
"storeCategoryText": "Text",
"storeCategoryLlm": "AI models",
"storeCategorySystem": "System",
"storeCategoryAuth": "Authentication",
"storeCategoryStorage": "Storage",
"storeCategoryChannel": "Channels",
"storeCategoryWeb": "Web",
"storeCategoryOrchestrator": "Orchestration",
"storeNResults": "{n} result{n, plural, =1{} other{s}}",
"@storeNResults": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"storeReloadTooltip": "Reload",
"storeTodayBadge": "TODAY",
"storeTodayDeck": "From the F∆I editor",
"storeTodayDismissTooltip": "Hide for this session",
"storePillInstalled": "installed",
"storePillUpdate": "update",
"storeUpdateButton": "Update to {version}",
"@storeUpdateButton": {
"placeholders": {
"version": {
"type": "String"
}
}
},
"storeUpdateTooltip": "Installed {installed} — store has v{best}",
"@storeUpdateTooltip": {
"placeholders": {
"installed": {
"type": "String"
},
"best": {
"type": "String"
}
}
},
"storeNoTagline": "(no tagline)",
"storeUninstallTitle": "Uninstall module?",
"storeUninstallBody": "Removes {name} from this hub. Flows that reference it will fail at the next run.",
"@storeUninstallBody": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"storeInstalledToast": "{name} v{version} installed.",
"@storeInstalledToast": {
"placeholders": {
"name": {
"type": "String"
},
"version": {
"type": "String"
}
}
},
"storeInstallFailedToast": "Install failed: {error}",
"@storeInstallFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"storeUninstalledToast": "{name} v{version} uninstalled.",
"@storeUninstalledToast": {
"placeholders": {
"name": {
"type": "String"
},
"version": {
"type": "String"
}
}
},
"storeUninstallFailedToast": "Uninstall failed: {error}",
"@storeUninstallFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"storeOpenBrowserFailed": "Could not open browser: {error}",
"@storeOpenBrowserFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"storeSectionTags": "Tags",
"storeSectionRequiredCapabilities": "Required capabilities",
"storeSectionRequiredHostServices": "Required host services",
"storeSectionScreenshots": "Screenshots",
"storeSectionDocumentation": "Documentation",
"storeSectionSource": "Source",
"storeSectionPermissions": "Declared permissions",
"storeSectionDirectory": "Module directory",
"storeSectionPermissionsNone": "(none — pure-computation module)",
"storeInstallingButton": "Installing…",
"storeNotInstallable": "Not installable",
"storeNotInstallableTooltip": "Status \"{status}\" — install path not yet wired.",
"@storeNotInstallableTooltip": {
"placeholders": {
"status": {
"type": "String"
}
}
},
"storeInstallProgressTitle": "Installing {name}",
"@storeInstallProgressTitle": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"storeInstallProgressBody": "Fetching, verifying, unpacking…",
"storeLoadDocs": "Load documentation",
"storeDocsHint": "README rendered inline; uses the hub's registry token when needed.",
"storeDocsFetching": "Fetching README…",
"storeOpenRepoButton": "Open repository in browser",
"storeDocsErrorNotFound": "This module is not in the hub's store index.",
"storeDocsErrorNoDocs": "No repository URL is recorded for this module.",
"storeDocsErrorAuth": "The registry requires authentication to fetch this README. Set FAI_REGISTRY_TOKEN in the daemon's environment and restart the hub.",
"storeDocsErrorNetwork": "Network error while fetching the README. {detail}",
"@storeDocsErrorNetwork": {
"placeholders": {
"detail": {
"type": "String"
}
}
},
"storeDocsErrorParse": "README is not valid UTF-8.",
"storeDocsErrorGeneric": "Could not load README.",
"storeSourceLabel": "Source",
"storeSourceAll": "All sources",
"storeSourceNative": "Native",
"storeSourceMcp": "MCP",
"storeSourceN8n": "n8n",
"storeProvenanceNative": "native",
"storeProvenanceMcp": "mcp · {provider}",
"@storeProvenanceMcp": {
"placeholders": {
"provider": {
"type": "String"
}
}
},
"storeProvenanceN8n": "n8n · {provider}",
"@storeProvenanceN8n": {
"placeholders": {
"provider": {
"type": "String"
}
}
},
"storeRecommendedTitle": "Add a public source — one click",
"storeRecommendedBody": "Curated MCP servers reachable over HTTPS. No subprocess, no API key, no Node. Federated capabilities appear in the store immediately.",
"storeRecommendedAddTooltip": "Add and discover",
"storeRecommendedAdding": "Adding…",
"storeRecommendedDeepWikiTagline": "GitHub repo documentation search (AI-powered)",
"storeRecommendedSemgrepTagline": "Security scanning for code vulnerabilities",
"storeProviderAddedToast": "Added {name} — {n} federated {n, plural, =1{capability} other{capabilities}}.",
"@storeProviderAddedToast": {
"placeholders": {
"name": {
"type": "String"
},
"n": {
"type": "int"
}
}
},
"storeProviderAddedZeroToast": "{name} registered, but the server returned no capabilities yet. Open Settings → MCP Clients to retry discovery or check the server.",
"@storeProviderAddedZeroToast": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"storeProviderAddFailed": "Could not add {name}: {error}",
"@storeProviderAddFailed": {
"placeholders": {
"name": {
"type": "String"
},
"error": {
"type": "String"
}
}
},
"auditTitle": "Audit",
"auditNoEvents": "No events yet",
"auditNoEventsHint": "Run a flow to populate the audit stream.\nEvents appear here within seconds.",
"auditFilterAll": "all",
"auditFilterFlow": "flow",
"auditFilterStep": "step",
"auditFilterModule": "module",
"auditClearLogTooltip": "Clear log (local/dev channels only)",
"auditClearedToast": "Cleared {n} events on channel \"{channel}\". Chain reseeded with marker.",
"@auditClearedToast": {
"placeholders": {
"n": {
"type": "int"
},
"channel": {
"type": "String"
}
}
},
"auditClearFailed": "Clear failed: {detail}",
"@auditClearFailed": {
"placeholders": {
"detail": {
"type": "String"
}
}
},
"auditExplain": "Explain",
"auditReask": "Re-ask",
"auditAsking": "Asking…",
"auditSystemAi": "SYSTEM AI",
"auditCachedPill": "cached",
"auditOriginalLatency": "orig {ms} ms",
"@auditOriginalLatency": {
"placeholders": {
"ms": {
"type": "int"
}
}
},
"auditLatency": "{ms} ms",
"@auditLatency": {
"placeholders": {
"ms": {
"type": "int"
}
}
},
"auditRegenerateTooltip": "Regenerate — skip cache, ask the model again",
"auditLiveStatus": "live · polling 2s · {n} {n, plural, =1{event} other{events}}",
"@auditLiveStatus": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"auditDisconnected": "disconnected · {error}",
"@auditDisconnected": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"auditHashChainVerified": "hash chain verified",
"auditDetailHeader": "DETAIL",
"auditAskingFull": "Asking the configured System AI…",
"auditFixLabel": "FIX",
"auditCachedTooltipKnown": "Served from the local cache. Originally generated on {at}{hits}.",
"@auditCachedTooltipKnown": {
"placeholders": {
"at": {
"type": "String"
},
"hits": {
"type": "String"
}
}
},
"auditCachedTooltipUnknown": "Served from the local cache. Originally generated at unknown time{hits}.",
"@auditCachedTooltipUnknown": {
"placeholders": {
"hits": {
"type": "String"
}
}
},
"auditCachedTooltipHits": " · {n} hits",
"@auditCachedTooltipHits": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"auditConfigureSystemAi": "Configure System AI in Settings (Cmd+,)",
"auditClearDialogTitle": "Clear audit log?",
"auditClearDialogBody": "Wipes every audit event on the active channel and seeds a fresh chain.reset marker carrying reviewer + reason. Refused on beta / production. Irreversible.",
"auditClearReviewerLabel": "Reviewer",
"auditClearReasonLabel": "Reason (recorded in chain.reset marker)",
"auditClearReasonHelper": "Required — auditors will read this.",
"auditClearLogButton": "Clear log",
"modulesTitle": "Modules",
"modulesNoneTitle": "No modules yet",
"modulesNoneHint": "Run `fai install <capability-name>` or check ~/.fai/modules/.",
"modulesReloadTooltip": "Reload",
"modulesRecentActivity": "RECENT ACTIVITY",
"modulesRecentActivityHint": "last {n} install/uninstall events from the audit log",
"@modulesRecentActivityHint": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"modulesActivityInstalled": "installed",
"modulesActivityUninstalled": "uninstalled",
"modulesCapabilitiesLabel": "Capabilities",
"modulesUninstallTitle": "Uninstall module?",
"modulesUninstallBody": "Removes {name} v{version} from this hub. Flows that reference it will fail at the next run. A `module.uninstalled` audit event is recorded.",
"@modulesUninstallBody": {
"placeholders": {
"name": {
"type": "String"
},
"version": {
"type": "String"
}
}
},
"modulesUninstalledToast": "Uninstalled {name} v{version}.",
"@modulesUninstalledToast": {
"placeholders": {
"name": {
"type": "String"
},
"version": {
"type": "String"
}
}
},
"modulesUninstallFailed": "Uninstall failed: {error}",
"@modulesUninstallFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"modulesUninstalling": "Uninstalling…",
"moduleSheetFailedToLoad": "Failed to load: {error}",
"@moduleSheetFailedToLoad": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"moduleSheetCapabilities": "Capabilities",
"moduleSheetPermissions": "Declared permissions",
"moduleSheetNoPermissions": "(none — pure-computation module)",
"flowsTitle": "Flows",
"flowsReloadTooltip": "Reload",
"flowsNoneTitle": "No saved flows",
"flowsNoneHint": "Save a flow with `fai admin flows save <name> <flow.yaml>` and it shows up here.",
"flowsRunDialogTitle": "Run {name}",
"@flowsRunDialogTitle": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"flowsRunDialogBody": "One field per declared input. Pick a file for bytes-shaped inputs; type plain text for the rest. The Run button enables when every required input is set.",
"flowsLoadingDefinition": "Loading inputs…",
"flowsDefinitionFailed": "Could not load flow definition",
"flowsNoInputs": "This flow declares no inputs. Click Run to start.",
"flowsTypeBytesPick": "Choose file…",
"flowsTypeBytesChange": "Change file",
"flowsTypeBytesNoFile": "No file selected",
"flowsTypeBytesSize": "{n} bytes",
"@flowsTypeBytesSize": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"flowsRunErrorTitle": "Flow run failed",
"flowsFileReadFailed": "Could not read \"{path}\": {error}",
"@flowsFileReadFailed": {
"placeholders": {
"path": {
"type": "String"
},
"error": {
"type": "String"
}
}
},
"flowsMissingModulesLabel": "Needs:",
"flowsRunDisabledTooltip": "Install the missing modules first.",
"flowsInstallAllButton": "Install all ({n})",
"@flowsInstallAllButton": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"flowsInstallPillTooltip": "Click to install",
"flowsInstallDepsTitle": "Install dependencies",
"flowsInstallDepsBody": "Walking through the missing modules in order. Existing installs are left alone.",
"flowsInstallStatusPending": "Pending",
"flowsInstallStatusInstalling": "Installing…",
"flowsInstallStatusDone": "Installed v{version}",
"@flowsInstallStatusDone": {
"placeholders": {
"version": {
"type": "String"
}
}
},
"flowsInstallStatusFailed": "Failed",
"flowsInstallStatusFailedDetail": "{error}",
"@flowsInstallStatusFailedDetail": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"flowsInstallDepsAllDone": "All dependencies installed.",
"flowsInstallDepsAnyFailed": "{ok} installed, {failed} failed.",
"@flowsInstallDepsAnyFailed": {
"placeholders": {
"ok": {
"type": "int"
},
"failed": {
"type": "int"
}
}
},
"flowsInstallAuthWallButton": "Add registry token",
"flowsOpenInEditorTooltip": "Open in Studio's flow editor",
"flowsOpenInEditorFailed": "Could not open file: {error}",
"@flowsOpenInEditorFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"registryCredentialsHeader": "REGISTRY CREDENTIALS",
"registryCredentialsBlurb": "Token used to download .fai modules from a registry behind a signin wall (Forgejo, GitHub-private). Stored at ~/.fai/registry-token, mode 0600. The FAI_REGISTRY_TOKEN env var still wins when set.",
"registryTokenStatusConfigured": "Configured ({chars} chars)",
"@registryTokenStatusConfigured": {
"placeholders": {
"chars": {
"type": "int"
}
}
},
"registryTokenStatusNotSet": "Not set",
"registryTokenFieldLabel": "Token",
"registryTokenFieldHint": "Paste your Forgejo or GitHub personal access token",
"registryTokenSaveButton": "Save",
"registryTokenClearButton": "Clear",
"registryTokenStorageHint": "Saved locally to ~/.fai/registry-token. Never sent to a remote service.",
"registryTokenSavedToast": "Registry token saved.",
"registryTokenClearedToast": "Registry token cleared.",
"registryTokenSaveFailedToast": "Could not save: {error}",
"@registryTokenSaveFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"hubAuthTokenHeader": "HUB AUTHENTICATION",
"hubAuthTokenBlurb": "Bearer token used to authenticate Studio against a hub that has auth.tokens: configured (RBAC Level 2). Stored at ~/.fai/hub-auth-token, mode 0600. Studio sends it as Authorization: Bearer on every gRPC call.",
"hubAuthTokenStatusConfigured": "Configured ({chars} chars)",
"@hubAuthTokenStatusConfigured": {
"placeholders": {
"chars": {
"type": "int"
}
}
},
"hubAuthTokenStatusNotSet": "Not set (anonymous)",
"hubAuthTokenFieldLabel": "Token",
"hubAuthTokenFieldHint": "Paste a token from the hub operator's auth.tokens entry",
"hubAuthTokenSaveButton": "Save",
"hubAuthTokenClearButton": "Clear",
"hubAuthTokenStorageHint": "Saved locally to ~/.fai/hub-auth-token. Studio reconnects after save so the new token takes effect immediately.",
"hubAuthTokenSavedToast": "Hub auth token saved.",
"hubAuthTokenClearedToast": "Hub auth token cleared.",
"hubAuthTokenSaveFailedToast": "Could not save: {error}",
"@hubAuthTokenSaveFailedToast": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"storeAdvisoryVersionTooltip": "Federated upstream service — version is advisory; the upstream may break compatibility without bumping it.",
"uninstallVersionPickerTitle": "Pick a version to uninstall",
"uninstallVersionPickerBody": "Several versions of `{module}` are installed side-by-side. Select the exact version to remove — the others stay in place.",
"@uninstallVersionPickerBody": {
"placeholders": {
"module": {
"type": "String"
}
}
},
"uninstallVersionPickerContinue": "Continue",
"defaultScopeHeader": "DEFAULT SCOPE",
"defaultScopeBlurb": "Ordered list of publisher segments the hub consults when a flow names a capability without an explicit `<provider>/` prefix. First match wins — promote the segments your team uses most to the top. Catalog-known publishers appear as chips; arbitrary entries are accepted for private segments.",
"defaultScopeAddLabel": "Add publisher segment",
"defaultScopeAddHint": "e.g. acme.team",
"defaultScopeAddButton": "Add",
"defaultScopeSuggestions": "Catalog suggestions:",
"defaultScopeSavedToast": "Default scope updated.",
"defaultScopeLoadFailed": "Could not load default scope.",
"defaultScopeNonEmptyError": "Default scope cannot be empty — keep at least one segment.",
"maintenanceHeader": "HUB MAINTENANCE",
"maintenanceResetBlurb": "Wipe operator state and start over with a clean hub. Stops every running daemon, atomically backs ~/.fai/ up, then recreates it with the binary, channel state, MCP / n8n / system-AI config, and registry token preserved. Restore by moving the backup directory back.",
"maintenanceKeepModulesTitle": "Keep installed modules",
"maintenanceKeepModulesSubtitle": "Default behaviour wipes ~/.fai/modules/ so a fresh install can verify the module-fetch path end-to-end.",
"maintenanceKeepDataTitle": "Keep audit log + saved flows",
"maintenanceKeepDataSubtitle": "Default behaviour wipes ~/.fai/data/ so the audit chain restarts from a fresh genesis and the bundled sample flows re-import on first daemon start.",
"maintenanceResetButton": "Reset hub state",
"maintenanceResetInProgress": "Resetting…",
"maintenanceResetConfirmTitle": "Reset hub state?",
"maintenanceResetConfirmBody": "This stops every daemon, moves ~/.fai/ to a timestamped backup, and starts fresh. The backup is fully restorable. Continue?",
"maintenanceResetConfirmButton": "Reset",
"welcomeChecklistAllSetTitle": "You're set up.",
"welcomeChecklistAllSetBody": "Three threads to pull on next:",
"welcomeChecklistNextAuditTitle": "Read the audit log",
"welcomeChecklistNextAuditBody": "Every install, flow run, and approval lives in the hash-chained log. Open the Audit tab to see what your hub has been up to.",
"welcomeChecklistNextAuditButton": "Open Audit",
"welcomeChecklistNextTodayTitle": "Set up the daily Today story",
"welcomeChecklistNextTodayBody": "Run tools/today/propose.sh on a cron and the editorial card on the store auto-fills with operator-curated narratives.",
"welcomeChecklistNextTodayButton": "Open Today docs",
"welcomeChecklistNextModuleTitle": "Build your own module",
"welcomeChecklistNextModuleBody": "Generate a Rust+WASM scaffold with `fai new module <name>`. The module-sdk handles the WIT plumbing; you write a typed invoke.",
"welcomeChecklistNextModuleButton": "Read the docs",
"auditGroupToday": "TODAY",
"auditGroupYesterday": "YESTERDAY",
"auditGroupThisWeek": "EARLIER THIS WEEK",
"auditGroupOlder": "OLDER",
"auditEventViewFlowRun": "View flow run",
"auditFlowRunDialogTitle": "Flow run · {flow}",
"@auditFlowRunDialogTitle": {
"placeholders": {
"flow": {
"type": "String"
}
}
},
"auditFlowRunDialogSubtitle": "{n} {n, plural, =1{event} other{events}} for execution {execution}",
"@auditFlowRunDialogSubtitle": {
"placeholders": {
"n": {
"type": "int"
},
"execution": {
"type": "String"
}
}
},
"approvalsSelectAll": "Select all",
"approvalsClearSelection": "Clear",
"approvalsBatchSelected": "{n} selected",
"@approvalsBatchSelected": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"approvalsBatchApprove": "Approve all",
"approvalsBatchReject": "Reject all",
"approvalsBatchApproveDoneToast": "{n} approvals approved.",
"@approvalsBatchApproveDoneToast": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"approvalsBatchRejectDoneToast": "{n} approvals rejected.",
"@approvalsBatchRejectDoneToast": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"approvalsBatchPartialFailure": "{ok} done, {failed} failed.",
"@approvalsBatchPartialFailure": {
"placeholders": {
"ok": {
"type": "int"
},
"failed": {
"type": "int"
}
}
},
"flowsRunButton": "Run",
"flowsRunningTitle": "Running {name}",
"@flowsRunningTitle": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"flowsResultTitle": "{name} — result",
"@flowsResultTitle": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"flowsErrorTitle": "{name} — failed",
"@flowsErrorTitle": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"flowsRunning": "Flow running…",
"flowsNoOutputs": "Flow completed with no declared outputs.",
"errGeneric": "Something went wrong.",
"errInvalidArgument": "Invalid input.",
"errInvalidArgumentHint": "Check the form values and try again.",
"errNotFound": "Not found.",
"errNotFoundHint": "The item you asked for isn't here — it may have been removed or never existed.",
"errAlreadyExists": "Already exists.",
"errPermissionDenied": "Permission denied.",
"errPermissionDeniedHint": "The hub's operator policy blocks this action. Check `~/.fai/config.yaml`.",
"errFailedPrecondition": "Setup issue blocked this.",
"errFailedPreconditionHint": "The hub couldn't proceed because something it needs isn't ready. The detail below explains what.",
"errInternal": "Unexpected internal error.",
"errInternalHint": "Check the hub logs at `~/.fai/logs/`. If this repeats, please report it.",
"errUnavailable": "Hub not reachable.",
"errUnavailableHint": "Make sure `fai serve` (or `fai daemon start`) is running and the daemon endpoint matches Studio's settings.",
"errUnauthenticated": "Authentication required.",
"errUnauthenticatedHint": "Set `FAI_REGISTRY_TOKEN` or sign in through Settings before retrying.",
"errCopyDetail": "Copy detail",
"errDetailCopied": "Detail copied to clipboard.",
"flowsOutputUnknown": "Output payload variant not recognised.",
"flowsOutputBytesUnknownMime": "binary",
"flowsOutputSaveAs": "Save as…",
"flowsOutputSaveAsTitle": "Save flow output",
"flowsOutputSavedAt": "Saved to {path}",
"@flowsOutputSavedAt": {
"placeholders": {
"path": {
"type": "String"
}
}
},
"flowsOutputSaveFailed": "Save failed: {error}",
"@flowsOutputSaveFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"flowsOutputOpen": "Open",
"flowsOutputOpenFailed": "Open failed: {error}",
"@flowsOutputOpenFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"approvalsTitle": "Approvals",
"approvalsTabPending": "Pending",
"approvalsTabHistory": "History",
"approvalsInboxZero": "Inbox zero",
"approvalsInboxHint": "All caught up. New `system.approval@^0` steps land here automatically.",
"approvalsReloadTooltip": "Reload",
"approvalsPillPending": "pending",
"approvalsPillApproved": "approved",
"approvalsPillRejected": "rejected",
"approvalsPillExpired": "expired",
"approvalsPayloadPreview": "PAYLOAD PREVIEW",
"approvalsApproveButton": "Approve",
"approvalsRejectButton": "Reject",
"approvalsRejectDialogTitle": "Reject approval",
"approvalsRejectReasonLabel": "Reason (recorded in audit log)",
"approvalsApprovedToast": "approved · {flow} {step}",
"@approvalsApprovedToast": {
"placeholders": {
"flow": {
"type": "String"
},
"step": {
"type": "String"
}
}
},
"approvalsRejectedToast": "rejected · {flow} {step}",
"@approvalsRejectedToast": {
"placeholders": {
"flow": {
"type": "String"
},
"step": {
"type": "String"
}
}
},
"approvalsApproveFailed": "approve failed: {error}",
"@approvalsApproveFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"approvalsRejectFailed": "reject failed: {error}",
"@approvalsRejectFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"approvalsHistoryEmpty": "No history yet",
"approvalsHistoryEmptyHint": "Decided approvals (approved / rejected / expired) appear here.\nThe audit log keeps the full hash-chained record.",
"approvalsDialogDecided": "decided",
"approvalsDialogCreated": "created",
"approvalsDialogReason": "reason",
"approvalsDialogPrompt": "PROMPT",
"approvalsExpiresIn": "{minutes}m",
"@approvalsExpiresIn": {
"placeholders": {
"minutes": {
"type": "int"
}
}
},
"approvalsExpiresInHours": "{hours}h",
"@approvalsExpiresInHours": {
"placeholders": {
"hours": {
"type": "int"
}
}
},
"doctorTitle": "Doctor",
"doctorSummaryModules": "Modules",
"doctorSummaryApprovals": "Approvals",
"doctorSummaryAudit": "Audit",
"doctorSummaryServices": "Services",
"doctorSummaryCapabilities": "{n} capabilities",
"@doctorSummaryCapabilities": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"doctorSummaryPending": "pending",
"doctorSummaryChain": "{verified}/{total} chain",
"@doctorSummaryChain": {
"placeholders": {
"verified": {
"type": "int"
},
"total": {
"type": "int"
}
}
},
"doctorSummaryDeclared": "declared",
"doctorModulesPanelSummary": "{n} modules · {m} capabilities",
"@doctorModulesPanelSummary": {
"placeholders": {
"n": {
"type": "int"
},
"m": {
"type": "int"
}
}
},
"doctorApprovalsNone": "No pending approvals",
"doctorApprovalsCount": "{n, plural, =1{1 approval awaiting review} other{{n} approvals awaiting review}}",
"@doctorApprovalsCount": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"doctorApprovalsAttentionPill": "attention",
"doctorServicesEmpty": "No host services declared",
"doctorServicesEmptyHint": "add to ~/.fai/config.yaml under services:",
"doctorPillLoaded": "loaded",
"doctorPillEmpty": "empty",
"doctorRecheckTooltip": "Re-check",
"doctorEventLogSection": "Event log",
"doctorModulesApprovalsSection": "Modules & approvals",
"doctorHostServicesSection": "Host services",
"doctorDaemonFilesSection": "Daemon files",
"doctorDaemonControlSection": "Daemon control",
"doctorChainIntact": "Hash chain intact",
"doctorChainIntactDetail": "{n} events · prev_event_sha256 verified end-to-end",
"@doctorChainIntactDetail": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"doctorChainTampered": "Tampering detected",
"doctorChainTamperedDetail": "{verified} of {total} verified before mismatch at {id}",
"@doctorChainTamperedDetail": {
"placeholders": {
"verified": {
"type": "int"
},
"total": {
"type": "int"
},
"id": {
"type": "String"
}
}
},
"doctorChainPillOk": "WORM-1",
"doctorChainPillTamper": "TAMPER",
"doctorVerifyNow": "Verify now",
"doctorRestart": "Restart",
"doctorStart": "Start",
"doctorStop": "Stop",
"doctorStatusAction": "Status",
"doctorRunningOn": "Running on {name}: {endpoint}",
"@doctorRunningOn": {
"placeholders": {
"name": {
"type": "String"
},
"endpoint": {
"type": "String"
}
}
},
"doctorStoppedOn": "{name} daemon stopped",
"@doctorStoppedOn": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"doctorStatusUnknown": "Daemon status: …",
"doctorPillRunning": "running",
"doctorPillStopped": "stopped",
"doctorDaemonControlHint": "Studio shells out to the platform binary — mirrors `fai daemon …` exactly so the CLI and UI stay in lockstep.",
"doctorDaemonControlWorking": "Working…",
"doctorPathLog": "Log",
"doctorPathConfig": "Config",
"doctorPathDb": "Audit DB",
"doctorPathModules": "Modules dir",
"doctorPathFlows": "Flows dir",
"doctorPathPid": "PID file",
"doctorPathsEmpty": "Daemon did not report file paths. Update the running hub via `fai daemon restart`.",
"doctorOpenError": "Could not open: {detail}",
"@doctorOpenError": {
"placeholders": {
"detail": {
"type": "String"
}
}
},
"doctorUpdateAvailable": "Update available — {version}",
"@doctorUpdateAvailable": {
"placeholders": {
"version": {
"type": "String"
}
}
},
"doctorUpdateBody": "Channel {channel} now offers {version}. Apply via the button — Studio shells out to `fai update apply --channel {channel}`.",
"@doctorUpdateBody": {
"placeholders": {
"channel": {
"type": "String"
},
"version": {
"type": "String"
}
}
},
"doctorUpdateUnreachable": "Release host unreachable",
"doctorUpdateUnreachableBody": "Could not contact the release feed for {channel}.",
"@doctorUpdateUnreachableBody": {
"placeholders": {
"channel": {
"type": "String"
}
}
},
"doctorReleaseNotes": "notes: {url}",
"@doctorReleaseNotes": {
"placeholders": {
"url": {
"type": "String"
}
}
},
"doctorPillNew": "new",
"doctorPillOffline": "offline",
"doctorApplyUpdate": "Apply update",
"doctorApplying": "Applying…",
"doctorApplyDone": "Update applied. Restart Studio to see the new daemon version.",
"mcpHeader": "MCP CLIENTS",
"mcpHint": "External MCP servers federate their tools as `mcp.<server>.<tool>` capabilities. Configure once, see them in the Store.",
"mcpEmpty": "No MCP servers configured. Click + to add one.",
"n8nHeader": "N8N ENDPOINTS",
"n8nHint": "Active n8n workflows surface as `n8n.<endpoint>.<slug>` capabilities. Configure once, see them in the Store.",
"n8nEmpty": "No n8n endpoints configured. Click + to add one.",
"hubUnreachable": "Hub unreachable",
"hubUnreachableHint": "Start the hub with `fai serve`.",
"languageEnglish": "English",
"languageGerman": "Deutsch",
"searchHint": "Jump anywhere — modules, store, flows, pages…",
"searchIndexing": "Indexing…",
"searchNoMatches": "No matches.",
"searchHintNavigate": "↑↓ navigate",
"searchHintOpen": "enter open",
"searchHintClose": "esc close",
"searchGroupPages": "Pages",
"searchGroupModules": "Modules",
"searchGroupStore": "Store",
"searchGroupFlows": "Flows",
"searchSettingsLabel": "Settings",
"searchPageHint": "page · ⌘{n}",
"@searchPageHint": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"searchSettingsHint": "hub endpoint, channels, system AI · ⌘;",
"searchInstalledModuleHint": "installed module · v{version}",
"@searchInstalledModuleHint": {
"placeholders": {
"version": {
"type": "String"
}
}
},
"searchStoreUncategorized": "uncategorized",
"searchStoreHintWithTagline": "store · {tagline}",
"@searchStoreHintWithTagline": {
"placeholders": {
"tagline": {
"type": "String"
}
}
},
"searchStoreHintWithCategory": "store · {category}",
"@searchStoreHintWithCategory": {
"placeholders": {
"category": {
"type": "String"
}
}
},
"searchSavedFlowHint": "saved flow",
"systemAiTitle": "System AI",
"systemAiIntro": "The hub-internal LLM the platform itself uses for inline failure explanations and operator help. Off by default; configure here. See docs/architecture/system-ai.md for what crosses the wire.",
"systemAiProviderLabel": "Provider",
"systemAiEndpointLabel": "Endpoint URL (up to /v1)",
"systemAiApiKeyRequired": "API key env var (required)",
"systemAiApiKeyOptional": "API key env var (optional)",
"systemAiApiKeyDisclaimer": "Studio never reads or stores the key value — only its env-var name. The hub reads `${name}` at request time.",
"@systemAiApiKeyDisclaimer": {
"placeholders": {
"name": {
"type": "String"
}
}
},
"systemAiTestConnection": "Test connection",
"systemAiTesting": "Testing…",
"systemAiSave": "Save",
"systemAiPrivacyHeader": "PRIVACY MODE",
"systemAiPrivacyOffLabel": "Off",
"systemAiPrivacyOffDesc": "Feature disabled. No requests leave the hub.",
"systemAiPrivacyRedactedLabel": "Redacted",
"systemAiPrivacyRedactedDesc": "Only event_type / error / module names. KRITIS-friendly default.",
"systemAiPrivacyFullLabel": "Full",
"systemAiPrivacyFullDesc": "Includes the audit detail JSON (hash-only — no raw payloads).",
"systemAiConnectionOk": "Connection ok",
"systemAiConnectionFailed": "Connection failed",
"systemAiReplyPrefix": "Reply: {text}",
"@systemAiReplyPrefix": {
"placeholders": {
"text": {
"type": "String"
}
}
},
"systemAiModelLabel": "Model (required)",
"systemAiModelHintFallback": "model identifier the provider expects",
"systemAiModelHelperBase": "Required: pick from the list (Refresh) or type one.",
"systemAiModelHelperOllama": "Required: pick from the list (Refresh) or type one. Use Pull to download from Ollama.",
"systemAiRefresh": "Refresh",
"systemAiPull": "Pull",
"systemAiPulling": "Pulling…",
"systemAiCouldNotListModels": "Could not list models: {error}",
"@systemAiCouldNotListModels": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"systemAiNoModelsOllama": "No models on the Ollama server yet. Type one above and click Pull.",
"systemAiNoModelsGeneric": "Provider returned no models.",
"systemAiSuitabilityRecommended": "recommended",
"systemAiSuitabilityBalanced": "balanced",
"systemAiSuitabilitySmall": "small — quality may be limited",
"systemAiSuitabilityLarge": "large — slower",
"systemAiSuitabilityHuge": "huge — likely too slow on a laptop",
"systemAiSuitabilityUnknown": "size unknown",
"systemAiHwDetected": "Detected: {summary}",
"@systemAiHwDetected": {
"placeholders": {
"summary": {
"type": "String"
}
}
},
"systemAiHwReviewed": " · curation reviewed {date}",
"@systemAiHwReviewed": {
"placeholders": {
"date": {
"type": "String"
}
}
},
"systemAiLegendRecommended": "recommended for this hardware{tier}",
"@systemAiLegendRecommended": {
"placeholders": {
"tier": {
"type": "String"
}
}
},
"systemAiLegendBalanced": "balanced (4-8B)",
"systemAiLegendSmallLarge": "small <3B / large 9-15B / above hardware",
"systemAiLegendHuge": "huge >15B",
"systemAiLegendUnknown": "size unknown",
"systemAiCacheRow": "Cache: {n} cached {n, plural, =1{explanation} other{explanations}}. Identical prompts hit the cache; switching model or privacy mode flushes automatically.",
"@systemAiCacheRow": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"systemAiCacheClear": "Clear",
"systemAiCacheClearedToast": "Cleared {n} cached System-AI explanations.",
"@systemAiCacheClearedToast": {
"placeholders": {
"n": {
"type": "int"
}
}
},
"systemAiCacheClearFailed": "Cache clear failed: {error}",
"@systemAiCacheClearFailed": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"systemAiPullEmptyError": "Type a model id (e.g. gemma3:4b) first.",
"systemAiPullFailedError": "Pull failed: {error}",
"@systemAiPullFailedError": {
"placeholders": {
"error": {
"type": "String"
}
}
},
"storeProvenanceTemporal": "temporal · {provider}",
"@storeProvenanceTemporal": {
"placeholders": {
"provider": {
"type": "String"
}
}
},
"storeSourceTemporal": "Temporal",
"navFlowEditor": "Editor",
"flowEditorBackTooltip": "Back",
"flowEditorNew": "New flow",
"flowEditorSave": "Save",
"flowEditorRun": "Run",
"flowEditorRefresh": "Refresh file list",
"flowEditorRunOutput": "RUN OUTPUT",
"flowEditorEmptyTitle": "No flow open",
"flowEditorEmptyBody": "Pick one from the left, or click New flow to start a fresh one.",
"flowEditorListEmptyTitle": "No saved flows",
"flowEditorListEmptyBody": "Click New flow to scaffold one from a template.",
"flowEditorDiscardTitle": "Discard unsaved changes?",
"flowEditorDiscardBody": "Switching files will throw away the edits you haven't saved.",
"flowEditorDiscardKeep": "Keep editing",
"flowEditorDiscardThrow": "Throw away",
"flowEditorNewDialogTitle": "New flow",
"flowEditorNewDialogLabel": "Flow name",
"flowEditorNewDialogHelper": "lowercase letters, digits, hyphen, underscore",
"flowEditorNewDialogCancel": "Cancel",
"flowEditorNewDialogCreate": "Create",
"flowEditorNewTemplateComment": "Generated by Studio's Flow editor. Edit, save, run.",
"@flowEditorNewTemplateComment": {
"placeholders": {
"name": {"type": "String"}
}
},
"flowEditorAlreadyExists": "A flow named \"{name}\" already exists.",
"@flowEditorAlreadyExists": {
"placeholders": {
"name": {"type": "String"}
}
},
"buttonView": "View",
"logViewerTitle": "{title} — last {count} lines",
"@logViewerTitle": {
"placeholders": {
"title": {"type": "String"},
"count": {"type": "int"}
}
},
"logViewerEmpty": "Log file is empty or does not exist yet.",
"logViewerCopyAll": "Copy all",
"logViewerOpenExternal": "Open in default editor",
"logViewerLineCount": "{count, plural, =1{1 line} other{{count} lines}}",
"@logViewerLineCount": {
"placeholders": {
"count": {"type": "int"}
}
},
"doctorPathStudioErrors": "Studio errors",
"settingsCategoryGeneral": "General",
"settingsCategoryAppearance": "Appearance",
"settingsCategoryAi": "System AI",
"settingsCategoryIntegrations": "Integrations",
"settingsCategorySecurity": "Security",
"settingsCategoryMaintenance": "Maintenance",
"settingsAiPanelTitle": "System AI",
"settingsAiPanelBody": "Operator-managed LLM endpoint used by Studio for the AI helpers (system-ai-edit, install-suggest, doctor-summary). No flow ever calls this; modules speak to their own LLM.",
"settingsIntegrationsPanelTitle": "Integrations",
"settingsIntegrationsPanelBody": "External tool servers the hub federates capabilities from. MCP servers expose tool-shaped endpoints; n8n endpoints expose hosted workflows.",
"settingsSecurityPanelTitle": "Security & credentials",
"settingsSecurityPanelBody": "Tokens the hub holds on the operator's behalf. Stored in ~/.fai/ with mode 0600; never sent in telemetry.",
"settingsMaintenancePanelTitle": "Maintenance",
"settingsMaintenancePanelBody": "Destructive operations gated behind explicit confirm dialogs. Use when re-pilot-testing or debugging.",
"tooltipMoveUp": "Move up",
"tooltipMoveDown": "Move down",
"tooltipRemove": "Remove",
"daemonActionEnableAutostart": "enable autostart",
"daemonActionDisableAutostart": "disable autostart",
"daemonActionRestart": "daemon restart",
"daemonActionStart": "daemon start",
"daemonActionStop": "daemon stop",
"daemonActionStatus": "daemon status",
"daemonActionResultOk": "OK · {label}",
"@daemonActionResultOk": {
"placeholders": {
"label": {"type": "String"}
}
},
"daemonActionResultFailed": "Failed · {label}",
"@daemonActionResultFailed": {
"placeholders": {
"label": {"type": "String"}
}
},
"addSourceTitle": "Add module source",
"addSourceIntro": "`{capability}` is not in the public store. Point the hub at a `.fai` bundle URL or a local bundle path; the hub downloads, verifies (sha256 + signature) and installs it.",
"@addSourceIntro": {
"placeholders": {
"capability": {"type": "String"}
}
},
"addSourceField": "URL or path to .fai bundle",
"addSourceHint": "https://git.flemming.ai/your-org/your-module/releases/download/v0.1.0/foo-0.1.0.fai",
"addSourceHowItWorksTitle": "How private modules work",
"addSourceHowItWorksBody": "A module is a directory with a module.yaml + the WASM artifact. To share it: pack it (`fai pack <dir>`) and host the resulting `.fai` bundle anywhere (your own Forgejo / GitHub / S3). The hub installs by URL and verifies the signature against its trust store.\n\nDeveloping locally? Use the CLI — Studio cannot install from an unpacked directory (yet):",
"addSourceCliExample": "fai install --link /path/to/module",
"addSourceInstallButton": "Install",
"addSourceCancel": "Cancel",
"installFailed": "Install failed: {error}",
"@installFailed": {
"placeholders": {
"error": {"type": "String"}
}
},
"welcomeHubDownTitle": "The hub isn't running yet",
"welcomeHubDownBody": "Studio talks to a local hub — the engine that loads modules and runs flows. It isn't reachable right now. Start it to begin.",
"welcomeHubDownStart": "Start hub",
"welcomeHubDownStarting": "Starting…",
"welcomeHubDownDocsLink": "Can't start it? Read the getting-started guide",
"welcomeHubDownEndpoint": "Endpoint: {endpoint}",
"@welcomeHubDownEndpoint": {
"placeholders": {
"endpoint": {"type": "String"}
}
},
"daemonStartRequested": "Daemon start requested. Reconnecting…",
"daemonStartFailed": "Could not start daemon: {detail}",
"@daemonStartFailed": {
"placeholders": {
"detail": {"type": "String"}
}
},
"faiBinaryNotFound": "Could not find the `fai` program on this machine.",
"faiBinaryNotFoundHint": "Install the F∆I platform, or point Studio at an existing `fai` binary.",
"faiBinaryLocateButton": "Locate `fai` binary…",
"faiBinaryInstallDocsButton": "Open install guide",
"faiBinaryPickerTitle": "Select the `fai` binary",
"faiBinarySetOk": "Using `fai` binary at {path}",
"@faiBinarySetOk": {
"placeholders": {
"path": {"type": "String"}
}
},
"sysAiFixParse": "The provider sent a response in an unexpected format. Providers that aren't OpenAI-compatible may need a translation proxy.",
"sysAiFixUnknown": "Unexpected failure ({kind}). See the System AI documentation.",
"@sysAiFixUnknown": {
"placeholders": {
"kind": {"type": "String"}
}
},
"sysAiFixDisabled": "Configure System AI in Settings (Cmd+,) → System AI panel.",
"sysAiFixEnvMissing": "The API-key environment variable is empty. Set it in your shell, then restart the daemon.",
"sysAiFixNetwork": "The hub can't reach the configured endpoint. Is your provider running?",
"sysAiFixHttp": "The provider returned a non-2xx status. Verify the endpoint, model name, and API key.",
"sysAiFixEmptyResponse": "The provider answered with no content. Try a different model or rephrase the prompt.",
"channelSwitchOk": "Switched active channel to \"{name}\". Daemon restarted.",
"@channelSwitchOk": {
"placeholders": {
"name": {"type": "String"}
}
},
"channelSwitchFailed": "Channel switch failed: {detail}",
"@channelSwitchFailed": {
"placeholders": {
"detail": {"type": "String"}
}
},
"providerDescOllama": "Local `ollama serve`. Models stay on your machine. No API key needed.",
"providerDescOpenai": "OpenAI hosted API. Requires an API key. Data leaves your machine.",
"providerDescLmstudio": "Local LM Studio server. Models stay on your machine. No API key needed.",
"providerDescVllm": "Self-hosted vLLM or any other OpenAI-compatible server. Endpoint required.",
"providerDescCustom": "Anything else that speaks the OpenAI-compatible chat-completions wire (LiteLLM proxy, internal mirror, …).",
"welcomeDocLoadFailedBody": "Could not load the bundled doc \"{slug}\" ({locale}).\nTried: {attempted}\nUnderlying: {underlying}\nThis usually means the Studio build on disk predates the doc bundle. Rebuild Studio or open the online copy.",
"@welcomeDocLoadFailedBody": {
"placeholders": {
"slug": {"type": "String"},
"locale": {"type": "String"},
"attempted": {"type": "String"},
"underlying": {"type": "String"}
}
},
"hubUnreachableBanner": "Can't reach {endpoint} — open Settings",
"@hubUnreachableBanner": {
"placeholders": {
"endpoint": {"type": "String"}
}
},
"hubUnreachableOpenSettings": "Open Settings"
}