mirror of
https://github.com/memohai/Memoh.git
synced 2026-04-25 07:00:48 +09:00
chore: add husky hook
This commit is contained in:
@@ -0,0 +1,7 @@
|
||||
#!/usr/bin/env sh
|
||||
|
||||
export PATH="$HOME/.local/share/mise/shims:$HOME/.local/bin:$HOME/.npm-global/bin:/opt/homebrew/bin:/usr/local/bin:$PATH"
|
||||
|
||||
pnpm lint:fix || true
|
||||
|
||||
pnpm web:build
|
||||
+6
-4
@@ -9,14 +9,15 @@
|
||||
"docs:dev": "pnpm --filter @memoh/docs dev",
|
||||
"docs:build": "pnpm --filter @memoh/docs build",
|
||||
"docs:preview": "pnpm --filter @memoh/docs preview",
|
||||
"agent:dev": "go run ./agent-go/cmd/agent_gateway",
|
||||
"agent:build": "go build ./agent-go/cmd/agent_gateway",
|
||||
"agent:start": "go run ./agent-go/cmd/agent_gateway",
|
||||
"agent:dev": "pnpm --filter @memoh/agent-gateway dev",
|
||||
"agent:build": "pnpm --filter @memoh/agent-gateway build",
|
||||
"agent:start": "pnpm --filter @memoh/agent-gateway start",
|
||||
"release": "bumpp --all",
|
||||
"generate-sdk": "openapi-ts",
|
||||
"lint": "eslint .",
|
||||
"lint:fix": "eslint . --fix",
|
||||
"test": "vitest"
|
||||
"test": "vitest",
|
||||
"prepare": "husky"
|
||||
},
|
||||
"keywords": [],
|
||||
"author": "",
|
||||
@@ -27,6 +28,7 @@
|
||||
"bumpp": "^10.4.1",
|
||||
"eslint": "^9.39.2",
|
||||
"eslint-plugin-vue": "^10.6.2",
|
||||
"husky": "^9.1.7",
|
||||
"typescript": "^5.9.3",
|
||||
"typescript-eslint": "^8.52.0",
|
||||
"vitest": "^4.0.16",
|
||||
|
||||
@@ -4,7 +4,9 @@
|
||||
<div class="w-64 shrink-0 flex flex-col border rounded-lg overflow-hidden bg-card max-h-full">
|
||||
<div class="p-3 border-b space-y-3 shrink-0">
|
||||
<div class="flex items-center justify-between">
|
||||
<h4 class="text-sm font-medium">{{ $t('bots.memory.files') }}</h4>
|
||||
<h4 class="text-sm font-medium">
|
||||
{{ $t('bots.memory.files') }}
|
||||
</h4>
|
||||
<div class="flex items-center gap-1">
|
||||
<Button
|
||||
variant="ghost"
|
||||
@@ -152,7 +154,10 @@
|
||||
:disabled="actionLoading || !isDirty"
|
||||
@click="handleSave"
|
||||
>
|
||||
<Spinner v-if="actionLoading" class="mr-1.5 size-3" />
|
||||
<Spinner
|
||||
v-if="actionLoading"
|
||||
class="mr-1.5 size-3"
|
||||
/>
|
||||
{{ $t('common.save') }}
|
||||
</Button>
|
||||
</div>
|
||||
@@ -169,12 +174,16 @@
|
||||
<!-- Charts Section -->
|
||||
<div class="h-[240px] border-t flex flex-col bg-muted/5 shrink-0">
|
||||
<div class="px-3 py-1.5 border-b bg-muted/10 flex items-center justify-between shrink-0">
|
||||
<h5 class="text-[10px] font-bold uppercase tracking-wider text-muted-foreground/70">Vector Manifold</h5>
|
||||
<h5 class="text-[10px] font-bold uppercase tracking-wider text-muted-foreground/70">
|
||||
Vector Manifold
|
||||
</h5>
|
||||
</div>
|
||||
<div class="flex-1 flex min-h-0 divide-x overflow-hidden">
|
||||
<!-- Top K Buckets (Bar Chart) -->
|
||||
<div class="flex-1 flex flex-col p-3 min-w-0">
|
||||
<p class="text-[9px] font-semibold text-muted-foreground/60 mb-2 uppercase shrink-0">Top-K Bucket</p>
|
||||
<p class="text-[9px] font-semibold text-muted-foreground/60 mb-2 uppercase shrink-0">
|
||||
Top-K Bucket
|
||||
</p>
|
||||
<div class="flex-1 flex items-end gap-0.5 relative group min-h-0 pt-2 pb-4">
|
||||
<div
|
||||
v-for="(bucket, idx) in selectedMemory.top_k_buckets"
|
||||
@@ -187,7 +196,9 @@
|
||||
>
|
||||
<!-- Tooltip for Bar -->
|
||||
<div class="absolute z-20 bottom-full left-1/2 -translate-x-1/2 mb-1 bg-popover border text-popover-foreground px-2 py-1 rounded shadow-lg text-[10px] hidden group-hover/bar:block whitespace-nowrap pointer-events-none">
|
||||
<p class="font-bold text-primary">Index: {{ bucket.index }}</p>
|
||||
<p class="font-bold text-primary">
|
||||
Index: {{ bucket.index }}
|
||||
</p>
|
||||
<p>Value: {{ bucket.value.toFixed(6) }}</p>
|
||||
</div>
|
||||
</div>
|
||||
@@ -201,11 +212,25 @@
|
||||
|
||||
<!-- CDF Curve (Line Chart) -->
|
||||
<div class="flex-1 flex flex-col p-3 min-w-0">
|
||||
<p class="text-[9px] font-semibold text-muted-foreground/60 mb-2 uppercase shrink-0">Energy Gradient (CDF)</p>
|
||||
<p class="text-[9px] font-semibold text-muted-foreground/60 mb-2 uppercase shrink-0">
|
||||
Energy Gradient (CDF)
|
||||
</p>
|
||||
<div class="flex-1 relative min-h-0 pt-2 pb-4 group/cdf">
|
||||
<svg class="w-full h-full overflow-visible" viewBox="0 0 100 100" preserveAspectRatio="none">
|
||||
<svg
|
||||
class="w-full h-full overflow-visible"
|
||||
viewBox="0 0 100 100"
|
||||
preserveAspectRatio="none"
|
||||
>
|
||||
<!-- Grid lines -->
|
||||
<line x1="0" y1="50" x2="100" y2="50" stroke="currentColor" class="text-muted-foreground/5" stroke-width="0.5" />
|
||||
<line
|
||||
x1="0"
|
||||
y1="50"
|
||||
x2="100"
|
||||
y2="50"
|
||||
stroke="currentColor"
|
||||
class="text-muted-foreground/5"
|
||||
stroke-width="0.5"
|
||||
/>
|
||||
|
||||
<!-- Area under curve -->
|
||||
<path
|
||||
@@ -273,8 +298,12 @@
|
||||
transform: 'translate(-50%, -140%)'
|
||||
}"
|
||||
>
|
||||
<p class="font-bold text-primary">K: {{ hoveredCdfPoint.k }}</p>
|
||||
<p class="font-mono">P: {{ hoveredCdfPoint.cumulative.toFixed(6) }}</p>
|
||||
<p class="font-bold text-primary">
|
||||
K: {{ hoveredCdfPoint.k }}
|
||||
</p>
|
||||
<p class="font-mono">
|
||||
P: {{ hoveredCdfPoint.cumulative.toFixed(6) }}
|
||||
</p>
|
||||
</div>
|
||||
|
||||
<!-- Axis labels -->
|
||||
@@ -301,7 +330,9 @@
|
||||
class="size-6 opacity-20"
|
||||
/>
|
||||
</div>
|
||||
<h3 class="text-sm font-medium text-foreground">{{ $t('bots.memory.title') }}</h3>
|
||||
<h3 class="text-sm font-medium text-foreground">
|
||||
{{ $t('bots.memory.title') }}
|
||||
</h3>
|
||||
<p class="text-xs mt-1 max-w-[240px]">
|
||||
Select a file from the sidebar to view or edit, or create a new one to persist long-term information for your bot.
|
||||
</p>
|
||||
@@ -403,7 +434,10 @@
|
||||
:disabled="actionLoading || !newMemoryContent.trim()"
|
||||
@click="handleCreateMemory"
|
||||
>
|
||||
<Spinner v-if="actionLoading" class="mr-1.5 size-3" />
|
||||
<Spinner
|
||||
v-if="actionLoading"
|
||||
class="mr-1.5 size-3"
|
||||
/>
|
||||
{{ $t('common.confirm') }}
|
||||
</Button>
|
||||
</DialogFooter>
|
||||
@@ -432,7 +466,10 @@
|
||||
class="flex items-start gap-3 p-3 rounded-md border cursor-pointer hover:bg-muted/50 transition-colors"
|
||||
:class="{ 'bg-muted border-primary': compactRatio === '0.8' }"
|
||||
>
|
||||
<RadioGroupItem value="0.8" class="mt-1" />
|
||||
<RadioGroupItem
|
||||
value="0.8"
|
||||
class="mt-1"
|
||||
/>
|
||||
<div class="min-w-0">
|
||||
<p class="text-sm font-medium">{{ $t('bots.memory.compactRatioLight') }}</p>
|
||||
<p class="text-xs text-muted-foreground">{{ $t('bots.memory.compactRatioLightDesc') }}</p>
|
||||
@@ -442,7 +479,10 @@
|
||||
class="flex items-start gap-3 p-3 rounded-md border cursor-pointer hover:bg-muted/50 transition-colors"
|
||||
:class="{ 'bg-muted border-primary': compactRatio === '0.5' }"
|
||||
>
|
||||
<RadioGroupItem value="0.5" class="mt-1" />
|
||||
<RadioGroupItem
|
||||
value="0.5"
|
||||
class="mt-1"
|
||||
/>
|
||||
<div class="min-w-0">
|
||||
<p class="text-sm font-medium">{{ $t('bots.memory.compactRatioMedium') }}</p>
|
||||
<p class="text-xs text-muted-foreground">{{ $t('bots.memory.compactRatioMediumDesc') }}</p>
|
||||
@@ -452,7 +492,10 @@
|
||||
class="flex items-start gap-3 p-3 rounded-md border cursor-pointer hover:bg-muted/50 transition-colors"
|
||||
:class="{ 'bg-muted border-primary': compactRatio === '0.3' }"
|
||||
>
|
||||
<RadioGroupItem value="0.3" class="mt-1" />
|
||||
<RadioGroupItem
|
||||
value="0.3"
|
||||
class="mt-1"
|
||||
/>
|
||||
<div class="min-w-0">
|
||||
<p class="text-sm font-medium">{{ $t('bots.memory.compactRatioAggressive') }}</p>
|
||||
<p class="text-xs text-muted-foreground">{{ $t('bots.memory.compactRatioAggressiveDesc') }}</p>
|
||||
@@ -468,7 +511,10 @@
|
||||
type="date"
|
||||
class="w-full"
|
||||
/>
|
||||
<p v-if="compactDecayDays > 0" class="text-[10px] text-muted-foreground">
|
||||
<p
|
||||
v-if="compactDecayDays > 0"
|
||||
class="text-[10px] text-muted-foreground"
|
||||
>
|
||||
Calculated: {{ compactDecayDays }} days old
|
||||
</p>
|
||||
</div>
|
||||
@@ -485,7 +531,10 @@
|
||||
:disabled="compactLoading"
|
||||
@click="handleCompact"
|
||||
>
|
||||
<Spinner v-if="compactLoading" class="mr-1.5 size-3" />
|
||||
<Spinner
|
||||
v-if="compactLoading"
|
||||
class="mr-1.5 size-3"
|
||||
/>
|
||||
{{ $t('common.confirm') }}
|
||||
</Button>
|
||||
</DialogFooter>
|
||||
@@ -870,7 +919,7 @@ function generateSmoothPath(data: any[], closePath: boolean = false) {
|
||||
}
|
||||
|
||||
if (closePath) {
|
||||
d += ` L 100,100 L 0,100 Z`
|
||||
d += ' L 100,100 L 0,100 Z'
|
||||
}
|
||||
|
||||
return d
|
||||
|
||||
@@ -125,7 +125,10 @@
|
||||
variant="destructive"
|
||||
:disabled="deleteLoading"
|
||||
>
|
||||
<Spinner v-if="deleteLoading" class="mr-1.5" />
|
||||
<Spinner
|
||||
v-if="deleteLoading"
|
||||
class="mr-1.5"
|
||||
/>
|
||||
{{ $t('bots.settings.deleteBot') }}
|
||||
</Button>
|
||||
</template>
|
||||
|
||||
@@ -138,7 +138,9 @@
|
||||
<div class="rounded-md border p-4">
|
||||
<div class="flex items-center justify-between gap-2">
|
||||
<div>
|
||||
<p class="text-sm font-medium">{{ $t('bots.checks.title') }}</p>
|
||||
<p class="text-sm font-medium">
|
||||
{{ $t('bots.checks.title') }}
|
||||
</p>
|
||||
<p class="text-sm text-muted-foreground">
|
||||
{{ $t('bots.checks.subtitle') }}
|
||||
</p>
|
||||
@@ -191,7 +193,9 @@
|
||||
>
|
||||
<div class="flex items-center justify-between gap-2">
|
||||
<div class="min-w-0">
|
||||
<p class="font-mono text-xs">{{ checkTitleLabel(item) }}</p>
|
||||
<p class="font-mono text-xs">
|
||||
{{ checkTitleLabel(item) }}
|
||||
</p>
|
||||
<p
|
||||
v-if="item.subtitle"
|
||||
class="mt-0.5 text-xs text-muted-foreground"
|
||||
@@ -206,7 +210,9 @@
|
||||
{{ checkStatusLabel(item.status) }}
|
||||
</Badge>
|
||||
</div>
|
||||
<p class="mt-2 text-sm">{{ item.summary }}</p>
|
||||
<p class="mt-2 text-sm">
|
||||
{{ item.summary }}
|
||||
</p>
|
||||
<p
|
||||
v-if="item.detail"
|
||||
class="mt-1 text-xs text-muted-foreground break-all"
|
||||
@@ -335,39 +341,65 @@
|
||||
<div class="rounded-md border p-4">
|
||||
<dl class="grid grid-cols-1 gap-3 text-sm sm:grid-cols-2">
|
||||
<div class="space-y-1">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.id') }}</dt>
|
||||
<dd class="font-mono break-all">{{ containerInfo.container_id }}</dd>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.id') }}
|
||||
</dt>
|
||||
<dd class="font-mono break-all">
|
||||
{{ containerInfo.container_id }}
|
||||
</dd>
|
||||
</div>
|
||||
<div class="space-y-1">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.status') }}</dt>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.status') }}
|
||||
</dt>
|
||||
<dd>{{ containerStatusText }}</dd>
|
||||
</div>
|
||||
<div class="space-y-1">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.task') }}</dt>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.task') }}
|
||||
</dt>
|
||||
<dd>{{ containerTaskText }}</dd>
|
||||
</div>
|
||||
<div class="space-y-1">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.namespace') }}</dt>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.namespace') }}
|
||||
</dt>
|
||||
<dd>{{ containerInfo.namespace }}</dd>
|
||||
</div>
|
||||
<div class="space-y-1 sm:col-span-2">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.image') }}</dt>
|
||||
<dd class="break-all">{{ containerInfo.image }}</dd>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.image') }}
|
||||
</dt>
|
||||
<dd class="break-all">
|
||||
{{ containerInfo.image }}
|
||||
</dd>
|
||||
</div>
|
||||
<div class="space-y-1 sm:col-span-2">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.hostPath') }}</dt>
|
||||
<dd class="break-all">{{ containerInfo.host_path || '-' }}</dd>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.hostPath') }}
|
||||
</dt>
|
||||
<dd class="break-all">
|
||||
{{ containerInfo.host_path || '-' }}
|
||||
</dd>
|
||||
</div>
|
||||
<div class="space-y-1 sm:col-span-2">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.containerPath') }}</dt>
|
||||
<dd class="break-all">{{ containerInfo.container_path }}</dd>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.containerPath') }}
|
||||
</dt>
|
||||
<dd class="break-all">
|
||||
{{ containerInfo.container_path }}
|
||||
</dd>
|
||||
</div>
|
||||
<div class="space-y-1">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.createdAt') }}</dt>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.createdAt') }}
|
||||
</dt>
|
||||
<dd>{{ formatDate(containerInfo.created_at) }}</dd>
|
||||
</div>
|
||||
<div class="space-y-1">
|
||||
<dt class="text-muted-foreground">{{ $t('bots.container.fields.updatedAt') }}</dt>
|
||||
<dt class="text-muted-foreground">
|
||||
{{ $t('bots.container.fields.updatedAt') }}
|
||||
</dt>
|
||||
<dd>{{ formatDate(containerInfo.updated_at) }}</dd>
|
||||
</div>
|
||||
</dl>
|
||||
@@ -414,10 +446,18 @@
|
||||
<table class="w-full text-sm">
|
||||
<thead class="bg-muted/50 text-left">
|
||||
<tr>
|
||||
<th class="px-3 py-2 font-medium">{{ $t('bots.container.snapshotColumns.name') }}</th>
|
||||
<th class="px-3 py-2 font-medium">{{ $t('bots.container.snapshotColumns.kind') }}</th>
|
||||
<th class="px-3 py-2 font-medium">{{ $t('bots.container.snapshotColumns.parent') }}</th>
|
||||
<th class="px-3 py-2 font-medium">{{ $t('bots.container.snapshotColumns.createdAt') }}</th>
|
||||
<th class="px-3 py-2 font-medium">
|
||||
{{ $t('bots.container.snapshotColumns.name') }}
|
||||
</th>
|
||||
<th class="px-3 py-2 font-medium">
|
||||
{{ $t('bots.container.snapshotColumns.kind') }}
|
||||
</th>
|
||||
<th class="px-3 py-2 font-medium">
|
||||
{{ $t('bots.container.snapshotColumns.parent') }}
|
||||
</th>
|
||||
<th class="px-3 py-2 font-medium">
|
||||
{{ $t('bots.container.snapshotColumns.createdAt') }}
|
||||
</th>
|
||||
</tr>
|
||||
</thead>
|
||||
<tbody>
|
||||
@@ -426,10 +466,18 @@
|
||||
:key="`${item.snapshotter}:${item.name}`"
|
||||
class="border-t"
|
||||
>
|
||||
<td class="px-3 py-2 font-mono text-xs break-all">{{ item.name }}</td>
|
||||
<td class="px-3 py-2">{{ item.kind }}</td>
|
||||
<td class="px-3 py-2 break-all">{{ item.parent || '-' }}</td>
|
||||
<td class="px-3 py-2">{{ formatDate(item.created_at) }}</td>
|
||||
<td class="px-3 py-2 font-mono text-xs break-all">
|
||||
{{ item.name }}
|
||||
</td>
|
||||
<td class="px-3 py-2">
|
||||
{{ item.kind }}
|
||||
</td>
|
||||
<td class="px-3 py-2 break-all">
|
||||
{{ item.parent || '-' }}
|
||||
</td>
|
||||
<td class="px-3 py-2">
|
||||
{{ formatDate(item.created_at) }}
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
</table>
|
||||
|
||||
@@ -17,7 +17,7 @@
|
||||
:alt="String(att.name ?? 'image')"
|
||||
class="w-full h-full object-contain pointer-events-none"
|
||||
loading="lazy"
|
||||
/>
|
||||
>
|
||||
<video
|
||||
v-else
|
||||
:src="getUrl(att)"
|
||||
|
||||
@@ -6,8 +6,12 @@
|
||||
class="flex-1 flex items-center justify-center text-muted-foreground"
|
||||
>
|
||||
<div class="text-center">
|
||||
<p class="text-lg">{{ $t('chat.selectBot') }}</p>
|
||||
<p class="text-sm mt-1">{{ $t('chat.selectBotHint') }}</p>
|
||||
<p class="text-lg">
|
||||
{{ $t('chat.selectBot') }}
|
||||
</p>
|
||||
<p class="text-sm mt-1">
|
||||
{{ $t('chat.selectBotHint') }}
|
||||
</p>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -108,7 +112,10 @@
|
||||
class="ml-1 text-muted-foreground hover:text-foreground"
|
||||
@click="pendingFiles.splice(i, 1)"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'xmark']" class="size-3" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'xmark']"
|
||||
class="size-3"
|
||||
/>
|
||||
</button>
|
||||
</div>
|
||||
</div>
|
||||
@@ -128,7 +135,7 @@
|
||||
multiple
|
||||
accept="image/*,audio/*,video/*,.pdf,.doc,.docx,.xls,.xlsx,.ppt,.pptx,.txt,.csv,.zip"
|
||||
@change="handleFileSelect"
|
||||
/>
|
||||
>
|
||||
<div class="absolute right-2 bottom-2 flex items-center gap-1">
|
||||
<Button
|
||||
v-if="!streaming"
|
||||
@@ -137,7 +144,10 @@
|
||||
:disabled="!currentBotId || activeChatReadOnly"
|
||||
@click="fileInput?.click()"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'paperclip']" class="size-3.5" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'paperclip']"
|
||||
class="size-3.5"
|
||||
/>
|
||||
</Button>
|
||||
<Button
|
||||
v-if="!streaming"
|
||||
@@ -145,7 +155,10 @@
|
||||
:disabled="(!inputText.trim() && !pendingFiles.length) || !currentBotId || activeChatReadOnly"
|
||||
@click="handleSend"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'paper-plane']" class="size-3.5" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'paper-plane']"
|
||||
class="size-3.5"
|
||||
/>
|
||||
</Button>
|
||||
<Button
|
||||
v-else
|
||||
@@ -153,7 +166,10 @@
|
||||
variant="destructive"
|
||||
@click="chatStore.abort()"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'spinner']" class="size-3.5 animate-spin" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'spinner']"
|
||||
class="size-3.5 animate-spin"
|
||||
/>
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
@@ -12,7 +12,10 @@
|
||||
aria-label="Close"
|
||||
@click="close"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'xmark']" class="size-6" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'xmark']"
|
||||
class="size-6"
|
||||
/>
|
||||
</button>
|
||||
|
||||
<!-- Prev -->
|
||||
@@ -22,7 +25,10 @@
|
||||
aria-label="Previous"
|
||||
@click.stop="prev"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'chevron-left']" class="size-6" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'chevron-left']"
|
||||
class="size-6"
|
||||
/>
|
||||
</button>
|
||||
|
||||
<!-- Next -->
|
||||
@@ -32,7 +38,10 @@
|
||||
aria-label="Next"
|
||||
@click.stop="next"
|
||||
>
|
||||
<FontAwesomeIcon :icon="['fas', 'chevron-right']" class="size-6" />
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'chevron-right']"
|
||||
class="size-6"
|
||||
/>
|
||||
</button>
|
||||
|
||||
<!-- Media content -->
|
||||
@@ -44,7 +53,7 @@
|
||||
class="max-w-full max-h-[90vh] object-contain select-none"
|
||||
draggable="false"
|
||||
@click.stop
|
||||
/>
|
||||
>
|
||||
<video
|
||||
v-else-if="currentItem?.type === 'video'"
|
||||
:src="currentItem.src"
|
||||
|
||||
@@ -27,8 +27,11 @@
|
||||
</div>
|
||||
|
||||
<!-- Input (collapsible) -->
|
||||
<Collapsible v-if="block.input" v-model:open="inputOpen">
|
||||
<CollapsibleTrigger class="flex items-center gap-1.5 px-3 py-1.5 text-xs text-muted-foreground hover:text-foreground cursor-pointer w-full">
|
||||
<Collapsible
|
||||
v-if="block.input"
|
||||
v-model:open="inputOpen"
|
||||
>
|
||||
<CollapsibleTrigger class="flex items-center gap-1.5 px-3 py-1.5 text-xs text-muted-foreground hover:text-foreground cursor-pointer w-full">
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'chevron-right']"
|
||||
class="size-2.5 transition-transform"
|
||||
@@ -42,8 +45,11 @@
|
||||
</Collapsible>
|
||||
|
||||
<!-- Result (collapsible) -->
|
||||
<Collapsible v-if="block.done && block.result != null" v-model:open="resultOpen">
|
||||
<CollapsibleTrigger class="flex items-center gap-1.5 px-3 py-1.5 text-xs text-muted-foreground hover:text-foreground cursor-pointer w-full border-t border-muted">
|
||||
<Collapsible
|
||||
v-if="block.done && block.result != null"
|
||||
v-model:open="resultOpen"
|
||||
>
|
||||
<CollapsibleTrigger class="flex items-center gap-1.5 px-3 py-1.5 text-xs text-muted-foreground hover:text-foreground cursor-pointer w-full border-t border-muted">
|
||||
<FontAwesomeIcon
|
||||
:icon="['fas', 'chevron-right']"
|
||||
class="size-2.5 transition-transform"
|
||||
|
||||
@@ -10,8 +10,12 @@
|
||||
</SelectTrigger>
|
||||
<SelectContent>
|
||||
<SelectGroup>
|
||||
<SelectItem value="en">English</SelectItem>
|
||||
<SelectItem value="zh">中文</SelectItem>
|
||||
<SelectItem value="en">
|
||||
English
|
||||
</SelectItem>
|
||||
<SelectItem value="zh">
|
||||
中文
|
||||
</SelectItem>
|
||||
</SelectGroup>
|
||||
</SelectContent>
|
||||
</Select>
|
||||
@@ -20,8 +24,14 @@
|
||||
size="icon"
|
||||
@click="toggleTheme"
|
||||
>
|
||||
<Sun v-if="theme === 'dark'" class="size-5" />
|
||||
<Moon v-else class="size-5" />
|
||||
<Sun
|
||||
v-if="theme === 'dark'"
|
||||
class="size-5"
|
||||
/>
|
||||
<Moon
|
||||
v-else
|
||||
class="size-5"
|
||||
/>
|
||||
</Button>
|
||||
</div>
|
||||
<section class="w-full max-w-sm flex flex-col gap-10 ">
|
||||
|
||||
@@ -2,7 +2,10 @@
|
||||
<div class="space-y-4">
|
||||
<div class="space-y-2">
|
||||
<Label>API Key</Label>
|
||||
<Input v-model="localConfig.api_key" type="password" />
|
||||
<Input
|
||||
v-model="localConfig.api_key"
|
||||
type="password"
|
||||
/>
|
||||
</div>
|
||||
<div class="space-y-2">
|
||||
<Label>Base URL</Label>
|
||||
@@ -10,7 +13,11 @@
|
||||
</div>
|
||||
<div class="space-y-2">
|
||||
<Label>Timeout (seconds)</Label>
|
||||
<Input v-model.number="localConfig.timeout_seconds" type="number" :min="1" />
|
||||
<Input
|
||||
v-model.number="localConfig.timeout_seconds"
|
||||
type="number"
|
||||
:min="1"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
Generated
+29
@@ -30,6 +30,9 @@ importers:
|
||||
eslint-plugin-vue:
|
||||
specifier: ^10.6.2
|
||||
version: 10.6.2(@typescript-eslint/parser@8.52.0(eslint@9.39.2(jiti@2.6.1))(typescript@5.9.3))(eslint@9.39.2(jiti@2.6.1))(vue-eslint-parser@10.2.0(eslint@9.39.2(jiti@2.6.1)))
|
||||
husky:
|
||||
specifier: ^9.1.7
|
||||
version: 9.1.7
|
||||
typescript:
|
||||
specifier: ^5.9.3
|
||||
version: 5.9.3
|
||||
@@ -1743,56 +1746,67 @@ packages:
|
||||
resolution: {integrity: sha512-EHMUcDwhtdRGlXZsGSIuXSYwD5kOT9NVnx9sqzYiwAc91wfYOE1g1djOEDseZJKKqtHAHGwnGPQu3kytmfaXLQ==}
|
||||
cpu: [arm]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-arm-musleabihf@4.54.0':
|
||||
resolution: {integrity: sha512-+pBrqEjaakN2ySv5RVrj/qLytYhPKEUwk+e3SFU5jTLHIcAtqh2rLrd/OkbNuHJpsBgxsD8ccJt5ga/SeG0JmA==}
|
||||
cpu: [arm]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
'@rollup/rollup-linux-arm64-gnu@4.54.0':
|
||||
resolution: {integrity: sha512-NSqc7rE9wuUaRBsBp5ckQ5CVz5aIRKCwsoa6WMF7G01sX3/qHUw/z4pv+D+ahL1EIKy6Enpcnz1RY8pf7bjwng==}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-arm64-musl@4.54.0':
|
||||
resolution: {integrity: sha512-gr5vDbg3Bakga5kbdpqx81m2n9IX8M6gIMlQQIXiLTNeQW6CucvuInJ91EuCJ/JYvc+rcLLsDFcfAD1K7fMofg==}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
'@rollup/rollup-linux-loong64-gnu@4.54.0':
|
||||
resolution: {integrity: sha512-gsrtB1NA3ZYj2vq0Rzkylo9ylCtW/PhpLEivlgWe0bpgtX5+9j9EZa0wtZiCjgu6zmSeZWyI/e2YRX1URozpIw==}
|
||||
cpu: [loong64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-ppc64-gnu@4.54.0':
|
||||
resolution: {integrity: sha512-y3qNOfTBStmFNq+t4s7Tmc9hW2ENtPg8FeUD/VShI7rKxNW7O4fFeaYbMsd3tpFlIg1Q8IapFgy7Q9i2BqeBvA==}
|
||||
cpu: [ppc64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-riscv64-gnu@4.54.0':
|
||||
resolution: {integrity: sha512-89sepv7h2lIVPsFma8iwmccN7Yjjtgz0Rj/Ou6fEqg3HDhpCa+Et+YSufy27i6b0Wav69Qv4WBNl3Rs6pwhebQ==}
|
||||
cpu: [riscv64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-riscv64-musl@4.54.0':
|
||||
resolution: {integrity: sha512-ZcU77ieh0M2Q8Ur7D5X7KvK+UxbXeDHwiOt/CPSBTI1fBmeDMivW0dPkdqkT4rOgDjrDDBUed9x4EgraIKoR2A==}
|
||||
cpu: [riscv64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
'@rollup/rollup-linux-s390x-gnu@4.54.0':
|
||||
resolution: {integrity: sha512-2AdWy5RdDF5+4YfG/YesGDDtbyJlC9LHmL6rZw6FurBJ5n4vFGupsOBGfwMRjBYH7qRQowT8D/U4LoSvVwOhSQ==}
|
||||
cpu: [s390x]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-x64-gnu@4.54.0':
|
||||
resolution: {integrity: sha512-WGt5J8Ij/rvyqpFexxk3ffKqqbLf9AqrTBbWDk7ApGUzaIs6V+s2s84kAxklFwmMF/vBNGrVdYgbblCOFFezMQ==}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@rollup/rollup-linux-x64-musl@4.54.0':
|
||||
resolution: {integrity: sha512-JzQmb38ATzHjxlPHuTH6tE7ojnMKM2kYNzt44LO/jJi8BpceEC8QuXYA908n8r3CNuG/B3BV8VR3Hi1rYtmPiw==}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
'@rollup/rollup-openharmony-arm64@4.54.0':
|
||||
resolution: {integrity: sha512-huT3fd0iC7jigGh7n3q/+lfPcXxBi+om/Rs3yiFxjvSxbSB6aohDFXbWvlspaqjeOh+hx7DDHS+5Es5qRkWkZg==}
|
||||
@@ -1941,24 +1955,28 @@ packages:
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@tailwindcss/oxide-linux-arm64-musl@4.1.18':
|
||||
resolution: {integrity: sha512-1px92582HkPQlaaCkdRcio71p8bc8i/ap5807tPRDK/uw953cauQBT8c5tVGkOwrHMfc2Yh6UuxaH4vtTjGvHg==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
'@tailwindcss/oxide-linux-x64-gnu@4.1.18':
|
||||
resolution: {integrity: sha512-v3gyT0ivkfBLoZGF9LyHmts0Isc8jHZyVcbzio6Wpzifg/+5ZJpDiRiUhDLkcr7f/r38SWNe7ucxmGW3j3Kb/g==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
'@tailwindcss/oxide-linux-x64-musl@4.1.18':
|
||||
resolution: {integrity: sha512-bhJ2y2OQNlcRwwgOAGMY0xTFStt4/wyU6pvI6LSuZpRgKQwxTec0/3Scu91O8ir7qCR3AuepQKLU/kX99FouqQ==}
|
||||
engines: {node: '>= 10'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
'@tailwindcss/oxide-wasm32-wasi@4.1.18':
|
||||
resolution: {integrity: sha512-LffYTvPjODiP6PT16oNeUQJzNVyJl1cjIebq/rWWBF+3eDst5JGEFSc5cWxyRCJ0Mxl+KyIkqRxk1XPEs9x8TA==}
|
||||
@@ -3439,6 +3457,11 @@ packages:
|
||||
resolution: {integrity: sha512-vK9P5/iUfdl95AI+JVyUuIcVtd4ofvtrOr3HNtM2yxC9bnMbEdp3x01OhQNnjb8IJYi38VlTE3mBXwcfvywuSw==}
|
||||
engines: {node: '>= 14'}
|
||||
|
||||
husky@9.1.7:
|
||||
resolution: {integrity: sha512-5gs5ytaNjBrh5Ow3zrvdUUY+0VxIuWVL4i9irt6friV+BqdCfmV11CQTWMiBYWHbXhco+J1kHfTOUkePhCDvMA==}
|
||||
engines: {node: '>=18'}
|
||||
hasBin: true
|
||||
|
||||
iconv-lite@0.6.3:
|
||||
resolution: {integrity: sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==}
|
||||
engines: {node: '>=0.10.0'}
|
||||
@@ -3686,24 +3709,28 @@ packages:
|
||||
engines: {node: '>= 12.0.0'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
lightningcss-linux-arm64-musl@1.30.2:
|
||||
resolution: {integrity: sha512-5Vh9dGeblpTxWHpOx8iauV02popZDsCYMPIgiuw97OJ5uaDsL86cnqSFs5LZkG3ghHoX5isLgWzMs+eD1YzrnA==}
|
||||
engines: {node: '>= 12.0.0'}
|
||||
cpu: [arm64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
lightningcss-linux-x64-gnu@1.30.2:
|
||||
resolution: {integrity: sha512-Cfd46gdmj1vQ+lR6VRTTadNHu6ALuw2pKR9lYq4FnhvgBc4zWY1EtZcAc6EffShbb1MFrIPfLDXD6Xprbnni4w==}
|
||||
engines: {node: '>= 12.0.0'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
libc: [glibc]
|
||||
|
||||
lightningcss-linux-x64-musl@1.30.2:
|
||||
resolution: {integrity: sha512-XJaLUUFXb6/QG2lGIW6aIk6jKdtjtcffUT0NKvIqhSBY3hh9Ch+1LCeH80dR9q9LBjG3ewbDjnumefsLsP6aiA==}
|
||||
engines: {node: '>= 12.0.0'}
|
||||
cpu: [x64]
|
||||
os: [linux]
|
||||
libc: [musl]
|
||||
|
||||
lightningcss-win32-arm64-msvc@1.30.2:
|
||||
resolution: {integrity: sha512-FZn+vaj7zLv//D/192WFFVA0RgHawIcHqLX9xuWiQt7P0PtdFEVaxgF9rjM/IRYHQXNnk61/H/gb2Ei+kUQ4xQ==}
|
||||
@@ -8329,6 +8356,8 @@ snapshots:
|
||||
transitivePeerDependencies:
|
||||
- supports-color
|
||||
|
||||
husky@9.1.7: {}
|
||||
|
||||
iconv-lite@0.6.3:
|
||||
dependencies:
|
||||
safer-buffer: 2.1.2
|
||||
|
||||
Reference in New Issue
Block a user