2026-08-20 06:20:16 +07:00
|
|
|
<script setup lang="ts">
|
|
|
|
|
/** FR-10 UI — หน้าหลัก: card รายการ template ที่ active ให้เลือกสร้างเอกสาร */
|
|
|
|
|
import type { TemplateListItem } from '~/types/api'
|
|
|
|
|
|
|
|
|
|
const { apiJson } = useApi()
|
|
|
|
|
|
|
|
|
|
const templates = ref<TemplateListItem[]>([])
|
|
|
|
|
const loading = ref(true)
|
|
|
|
|
const error = ref<string | null>(null)
|
|
|
|
|
|
|
|
|
|
onMounted(async () => {
|
|
|
|
|
try {
|
|
|
|
|
templates.value = (await apiJson<TemplateListItem[]>('/api/templates')) ?? []
|
|
|
|
|
} catch (err) {
|
|
|
|
|
error.value = err instanceof Error ? err.message : 'โหลดรายการ template ไม่สำเร็จ'
|
|
|
|
|
} finally {
|
|
|
|
|
loading.value = false
|
|
|
|
|
}
|
|
|
|
|
})
|
|
|
|
|
</script>
|
|
|
|
|
|
2026-08-18 12:52:40 +07:00
|
|
|
<template>
|
2026-08-20 06:20:16 +07:00
|
|
|
<AuthGate>
|
|
|
|
|
<section class="space-y-5">
|
|
|
|
|
<div>
|
|
|
|
|
<h1 class="text-2xl font-bold">สร้างเอกสารจาก template</h1>
|
|
|
|
|
<p class="mt-1 text-sm text-slate-600 dark:text-slate-300">
|
|
|
|
|
เลือก template กรอกค่า fields แล้วดาวน์โหลด .docx ที่เป็น <strong>version 1</strong> พร้อม metadata
|
|
|
|
|
ไว้เปิดต่อใน Word พร้อม add-in
|
|
|
|
|
</p>
|
|
|
|
|
</div>
|
|
|
|
|
|
|
|
|
|
<div v-if="loading" class="flex items-center gap-3 py-10 text-sm text-slate-500 dark:text-slate-400">
|
|
|
|
|
<span
|
|
|
|
|
class="h-4 w-4 animate-spin rounded-full border-2 border-slate-300 border-t-slate-600 dark:border-slate-600 dark:border-t-slate-300"
|
|
|
|
|
/>
|
|
|
|
|
กำลังโหลดรายการ template…
|
|
|
|
|
</div>
|
|
|
|
|
|
|
|
|
|
<AlertBox v-else-if="error" type="error">{{ error }}</AlertBox>
|
|
|
|
|
|
|
|
|
|
<div
|
|
|
|
|
v-else-if="templates.length === 0"
|
|
|
|
|
class="rounded-lg border border-dashed border-slate-300 p-8 text-center text-sm text-slate-500 dark:border-slate-600 dark:text-slate-400"
|
|
|
|
|
>
|
|
|
|
|
ยังไม่มี template — ไปที่
|
|
|
|
|
<NuxtLink to="/templates/new" class="font-medium text-sky-600 hover:underline dark:text-sky-400">
|
|
|
|
|
สร้าง template ตัวแรก
|
|
|
|
|
</NuxtLink>
|
|
|
|
|
</div>
|
|
|
|
|
|
|
|
|
|
<div v-else class="grid gap-4 sm:grid-cols-2">
|
2026-08-20 11:15:04 +07:00
|
|
|
<div
|
2026-08-20 06:20:16 +07:00
|
|
|
v-for="t in templates"
|
|
|
|
|
:key="t.id"
|
2026-08-20 11:15:04 +07:00
|
|
|
class="flex flex-col rounded-lg border border-slate-200 bg-white p-5 transition hover:border-sky-400 hover:shadow-sm dark:border-slate-700 dark:bg-slate-800 dark:hover:border-sky-500"
|
2026-08-20 06:20:16 +07:00
|
|
|
>
|
2026-08-20 11:15:04 +07:00
|
|
|
<NuxtLink :to="`/documents/create/${t.id}`" class="flex-1">
|
|
|
|
|
<h2 class="font-semibold">{{ t.name }}</h2>
|
|
|
|
|
<p class="mt-1 line-clamp-2 min-h-10 text-sm text-slate-600 dark:text-slate-300">
|
|
|
|
|
{{ t.description ?? '—' }}
|
|
|
|
|
</p>
|
|
|
|
|
<p class="mt-3 text-xs text-slate-500 dark:text-slate-400">
|
|
|
|
|
{{ t.fieldCount }} fields · อัปเดต {{ formatDateTime(t.updatedAt) }}
|
|
|
|
|
</p>
|
|
|
|
|
</NuxtLink>
|
|
|
|
|
<div class="mt-3 flex gap-4 border-t border-slate-100 pt-3 text-xs dark:border-slate-700">
|
|
|
|
|
<NuxtLink
|
|
|
|
|
:to="`/documents/create/${t.id}`"
|
|
|
|
|
class="font-medium text-sky-600 hover:underline dark:text-sky-400"
|
|
|
|
|
>
|
|
|
|
|
สร้างเอกสาร →
|
|
|
|
|
</NuxtLink>
|
|
|
|
|
<NuxtLink
|
|
|
|
|
:to="`/templates/${t.id}/documents`"
|
|
|
|
|
class="text-slate-500 hover:text-sky-600 hover:underline dark:text-slate-400 dark:hover:text-sky-400"
|
|
|
|
|
>
|
|
|
|
|
ดูเอกสารที่สร้างแล้ว
|
|
|
|
|
</NuxtLink>
|
|
|
|
|
</div>
|
|
|
|
|
</div>
|
2026-08-20 06:20:16 +07:00
|
|
|
</div>
|
|
|
|
|
</section>
|
|
|
|
|
</AuthGate>
|
2026-08-18 12:52:40 +07:00
|
|
|
</template>
|