fix(dashboard): add Memory/Skills sidebar navigation and i18n keys
- Add "memory" and "skills" entries to HIDEABLE_SIDEBAR_ITEM_IDS and PRIMARY_SIDEBAR_ITEMS - Add sidebar translation keys for memory and skills pages - Add complete "memory" and "skills" i18n sections to en.json with all UI labels - Replace all hardcoded English text in memory/page.tsx with useTranslations() calls Memory and Skills pages now appear in the sidebar and render with proper i18n support. Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-opencode) Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
This commit is contained in:
@@ -108,32 +108,32 @@ export default function MemoryPage() {
|
||||
return (
|
||||
<div className="space-y-6 p-6">
|
||||
<div className="flex items-center justify-between">
|
||||
<h1 className="text-2xl font-bold">Memory Management</h1>
|
||||
<h1 className="text-2xl font-bold">{t("title")}</h1>
|
||||
<div className="flex gap-2">
|
||||
<Button variant="outline" onClick={handleExport}>
|
||||
Export
|
||||
{t("export")}
|
||||
</Button>
|
||||
<Button variant="outline">Import</Button>
|
||||
<Button>Add Memory</Button>
|
||||
<Button variant="outline">{t("import")}</Button>
|
||||
<Button>{t("addMemory")}</Button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className="grid grid-cols-1 md:grid-cols-3 gap-4">
|
||||
<Card>
|
||||
<div className="p-4">
|
||||
<div className="text-sm text-gray-500">Total Entries</div>
|
||||
<div className="text-sm text-gray-500">{t("totalEntries")}</div>
|
||||
<div className="text-2xl font-bold">{stats.totalEntries}</div>
|
||||
</div>
|
||||
</Card>
|
||||
<Card>
|
||||
<div className="p-4">
|
||||
<div className="text-sm text-gray-500">Tokens Used</div>
|
||||
<div className="text-sm text-gray-500">{t("tokensUsed")}</div>
|
||||
<div className="text-2xl font-bold">{stats.tokensUsed.toLocaleString()}</div>
|
||||
</div>
|
||||
</Card>
|
||||
<Card>
|
||||
<div className="p-4">
|
||||
<div className="text-sm text-gray-500">Hit Rate</div>
|
||||
<div className="text-sm text-gray-500">{t("hitRate")}</div>
|
||||
<div className="text-2xl font-bold">{(stats.hitRate * 100).toFixed(1)}%</div>
|
||||
</div>
|
||||
</Card>
|
||||
@@ -142,20 +142,20 @@ export default function MemoryPage() {
|
||||
<Card>
|
||||
<div className="p-4">
|
||||
<div className="flex items-center justify-between mb-4">
|
||||
<h2 className="text-lg font-semibold">Memories</h2>
|
||||
<h2 className="text-lg font-semibold">{t("memories")}</h2>
|
||||
<div className="flex gap-2">
|
||||
<Input
|
||||
placeholder="Search memories..."
|
||||
placeholder={t("search")}
|
||||
value={searchQuery}
|
||||
onChange={(e) => setSearchQuery(e.target.value)}
|
||||
className="w-64"
|
||||
/>
|
||||
<Select value={filterType} onChange={(e) => setFilterType(e.target.value)}>
|
||||
<option value="all">All Types</option>
|
||||
<option value="factual">Factual</option>
|
||||
<option value="episodic">Episodic</option>
|
||||
<option value="procedural">Procedural</option>
|
||||
<option value="semantic">Semantic</option>
|
||||
<option value="all">{t("allTypes")}</option>
|
||||
<option value="factual">{t("factual")}</option>
|
||||
<option value="episodic">{t("episodic")}</option>
|
||||
<option value="procedural">{t("procedural")}</option>
|
||||
<option value="semantic">{t("semantic")}</option>
|
||||
</Select>
|
||||
</div>
|
||||
</div>
|
||||
@@ -164,11 +164,11 @@ export default function MemoryPage() {
|
||||
<table className="w-full">
|
||||
<thead>
|
||||
<tr className="border-b">
|
||||
<th className="text-left py-2 px-4">Type</th>
|
||||
<th className="text-left py-2 px-4">Key</th>
|
||||
<th className="text-left py-2 px-4">Content</th>
|
||||
<th className="text-left py-2 px-4">Created</th>
|
||||
<th className="text-left py-2 px-4">Actions</th>
|
||||
<th className="text-left py-2 px-4">{t("type")}</th>
|
||||
<th className="text-left py-2 px-4">{t("key")}</th>
|
||||
<th className="text-left py-2 px-4">{t("content")}</th>
|
||||
<th className="text-left py-2 px-4">{t("created")}</th>
|
||||
<th className="text-left py-2 px-4">{t("actions")}</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@@ -182,7 +182,7 @@ export default function MemoryPage() {
|
||||
<td className="py-2 px-4">{new Date(memory.createdAt).toLocaleDateString()}</td>
|
||||
<td className="py-2 px-4">
|
||||
<Button variant="ghost" size="sm" onClick={() => handleDelete(memory.id)}>
|
||||
Delete
|
||||
{t("delete")}
|
||||
</Button>
|
||||
</td>
|
||||
</tr>
|
||||
|
||||
@@ -151,6 +151,8 @@
|
||||
"limits": "Limits & Quotas",
|
||||
"cliTools": "CLI Tools",
|
||||
"media": "Media",
|
||||
"memory": "Memory",
|
||||
"skills": "Skills",
|
||||
"settings": "Settings",
|
||||
"translator": "Translator",
|
||||
"playground": "Playground",
|
||||
@@ -1266,6 +1268,57 @@
|
||||
"events": "Events",
|
||||
"artifacts": "Artifacts"
|
||||
},
|
||||
"memory": {
|
||||
"title": "Memory Management",
|
||||
"description": "View and manage stored memory entries",
|
||||
"memories": "Memories",
|
||||
"totalEntries": "Total Entries",
|
||||
"tokensUsed": "Tokens Used",
|
||||
"hitRate": "Hit Rate",
|
||||
"loading": "Loading memories...",
|
||||
"noMemories": "No memories found",
|
||||
"search": "Search memories...",
|
||||
"allTypes": "All Types",
|
||||
"export": "Export",
|
||||
"import": "Import",
|
||||
"addMemory": "Add Memory",
|
||||
"type": "Type",
|
||||
"key": "Key",
|
||||
"content": "Content",
|
||||
"created": "Created",
|
||||
"actions": "Actions",
|
||||
"factual": "Factual",
|
||||
"episodic": "Episodic",
|
||||
"procedural": "Procedural",
|
||||
"semantic": "Semantic"
|
||||
},
|
||||
"skills": {
|
||||
"title": "Skills",
|
||||
"description": "Manage and monitor AI skills",
|
||||
"skillsTab": "Skills",
|
||||
"executionsTab": "Executions",
|
||||
"sandboxTab": "Sandbox",
|
||||
"loading": "Loading skills...",
|
||||
"noSkills": "No skills found",
|
||||
"noExecutions": "No executions found",
|
||||
"enabled": "Enabled",
|
||||
"disabled": "Disabled",
|
||||
"version": "Version",
|
||||
"description": "Description",
|
||||
"skill": "Skill",
|
||||
"status": "Status",
|
||||
"duration": "Duration",
|
||||
"time": "Time",
|
||||
"sandboxConfig": "Sandbox Configuration",
|
||||
"cpuLimit": "CPU Limit",
|
||||
"cpuLimitDesc": "Maximum execution time per skill",
|
||||
"memoryLimit": "Memory Limit",
|
||||
"memoryLimitDesc": "Maximum memory allocation",
|
||||
"timeout": "Timeout",
|
||||
"timeoutDesc": "Maximum wait time for response",
|
||||
"networkAccess": "Network Access",
|
||||
"networkAccessDesc": "Allow outbound network requests"
|
||||
},
|
||||
"health": {
|
||||
"title": "System Health",
|
||||
"description": "Real-time monitoring of your OmniRoute instance",
|
||||
@@ -3028,4 +3081,4 @@
|
||||
"expires": "Expires",
|
||||
"actions": "Actions"
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
@@ -11,6 +11,8 @@ export const HIDEABLE_SIDEBAR_ITEM_IDS = [
|
||||
"cache",
|
||||
"cli-tools",
|
||||
"agents",
|
||||
"memory",
|
||||
"skills",
|
||||
"translator",
|
||||
"playground",
|
||||
"media",
|
||||
@@ -55,6 +57,8 @@ const PRIMARY_SIDEBAR_ITEMS: readonly SidebarItemDefinition[] = [
|
||||
{ id: "analytics", href: "/dashboard/analytics", i18nKey: "analytics", icon: "analytics" },
|
||||
{ id: "limits", href: "/dashboard/limits", i18nKey: "limits", icon: "tune" },
|
||||
{ id: "cache", href: "/dashboard/cache", i18nKey: "cache", icon: "cached" },
|
||||
{ id: "memory", href: "/dashboard/memory", i18nKey: "memory", icon: "psychology" },
|
||||
{ id: "skills", href: "/dashboard/skills", i18nKey: "skills", icon: "auto_awesome" },
|
||||
];
|
||||
|
||||
const CLI_SIDEBAR_ITEMS: readonly SidebarItemDefinition[] = [
|
||||
|
||||
Reference in New Issue
Block a user