<template>
  <main class="min-h-screen bg-gray-50 px-4 py-8">
    <div class="mx-auto max-w-screen-xl space-y-6">
      <a-skeleton v-if="navPending" active :paragraph="{ rows: 8 }" />

      <a-result
        v-else-if="navError"
        status="error"
        title="页面加载失败"
        :sub-title="String(navError)"
      />

      <template v-else>
        <a-card class="shadow-sm">
          <template #title>
            <div class="flex flex-col gap-1">
              <div class="text-lg font-semibold text-gray-900">
                {{ parentTitle }}
              </div>
              <div v-if="parentDescription" class="text-sm text-gray-500">
                {{ parentDescription }}
              </div>
            </div>
          </template>

          <a-image
            v-if="parentBanner"
            :src="parentBanner"
            :preview="false"
            class="mb-5 w-full"
          />

          <a-layout class="bg-transparent">
            <a-layout-sider
              v-if="children.length"
              theme="light"
              :width="240"
              class="rounded-xl border border-black/5 bg-white overflow-hidden"
              breakpoint="lg"
              collapsed-width="0"
            >
              <a-menu
                mode="inline"
                :selected-keys="selectedKeys"
                @click="onMenuClick"
              >
                <a-menu-item v-for="n in children" :key="String(n.navigationId)">
                  {{ n.title || n.label || `栏目 ${n.navigationId}` }}
                </a-menu-item>
              </a-menu>
            </a-layout-sider>

            <a-layout-content :class="children.length ? 'pl-0 lg:pl-6 pt-6 lg:pt-0' : ''">
              <a-skeleton v-if="contentPending" active :paragraph="{ rows: 10 }" />

              <a-result
                v-else-if="contentError"
                status="error"
                title="内容加载失败"
                :sub-title="String(contentError)"
              />

              <template v-else>
                <div class="space-y-2">
                  <div class="text-2xl font-semibold text-gray-900">
                    {{ contentTitle }}
                  </div>
                  <div class="text-sm text-gray-500">
                    <span v-if="articleMeta?.createTime">发布时间：{{ articleMeta.createTime }}</span>
                    <span v-if="articleMeta?.author" class="ml-4">作者：{{ articleMeta.author }}</span>
                    <span v-if="articleMeta?.source" class="ml-4">来源：{{ articleMeta.source }}</span>
                  </div>
                </div>

                <a-alert
                  v-if="articleMeta?.overview"
                  type="info"
                  show-icon
                  class="my-5"
                  :message="String(articleMeta.overview)"
                />

                <a-image
                  v-if="articleMeta?.image"
                  :src="String(articleMeta.image)"
                  :preview="false"
                  class="mb-5 w-full"
                />

                <RichText :content="contentBody" />
              </template>
            </a-layout-content>
          </a-layout>
        </a-card>
      </template>
    </div>
  </main>
</template>

<script setup lang="ts">
import { getCmsArticle } from '@/api/cms/cmsArticle'
import { listCmsArticleContent } from '@/api/cms/cmsArticleContent'
import RichText from '@/components/RichText.vue'
import { usePageSeo } from '@/composables/usePageSeo'
import type { ApiEnvelope } from '~/types/api'
import type { CmsNavigation } from '@/api/cms/cmsNavigation/model'
import type { CmsArticle } from '@/api/cms/cmsArticle/model'

const route = useRoute()
const parentId = computed(() => {
  const raw = route.params.id
  const val = Array.isArray(raw) ? raw[0] : raw
  const n = Number(val)
  return Number.isFinite(n) ? n : NaN
})

const selectedNavId = computed(() => {
  const raw = route.query.nav
  const val = Array.isArray(raw) ? raw[0] : raw
  const n = Number(val)
  return Number.isFinite(n) ? n : NaN
})

function pickNavigationList(payload: unknown): CmsNavigation[] {
  if (Array.isArray(payload)) return payload as CmsNavigation[]
  const env = payload as ApiEnvelope<CmsNavigation[]>
  if (env && typeof env === 'object' && Array.isArray(env.data)) return env.data
  return []
}

const { data: navData, pending: navPending, error: navError } = useAsyncData(
  () => `cms-navigation-single-${parentId.value}`,
  async () => {
    if (!Number.isFinite(parentId.value)) throw new Error('无效的页面ID')
    // Single-page type: fetch navigation list by parentId.
    const res = await $fetch<unknown>('/api/cms-navigation', {
      query: { parentId: String(parentId.value) }
    })
    const children = pickNavigationList(res)
      .filter((n) => (n.hide ?? 0) !== 1)
      .slice()
      .sort((a, b) => (a.sortNumber ?? 0) - (b.sortNumber ?? 0))
    return { children }
  },
  { watch: [parentId] }
)

const children = computed<CmsNavigation[]>(() => navData.value?.children ?? [])

const activeNav = computed<CmsNavigation | null>(() => {
  const list = children.value
  if (!list.length) return null
  if (Number.isFinite(selectedNavId.value)) {
    const hit = list.find((n) => n.navigationId === selectedNavId.value)
    if (hit) return hit
  }
  return list[0]
})

// Keep URL stable so refresh/back works (default to first child).
if (import.meta.client) {
  watchEffect(() => {
    if (!children.value.length) return
    if (Number.isFinite(selectedNavId.value)) return
    const first = children.value[0]?.navigationId
    if (!first) return
    navigateTo({ path: route.path, query: { ...route.query, nav: String(first) } }, { replace: true })
  })
}

const selectedKeys = computed(() => {
  const key = activeNav.value?.navigationId
  return key ? [String(key)] : []
})

function onMenuClick(info: { key: string }) {
  navigateTo({ path: route.path, query: { ...route.query, nav: String(info.key) } })
}

async function loadSinglePageContent(nav: CmsNavigation): Promise<{
  title: string
  body: string
  article?: CmsArticle
}> {
  // Common pattern: navigation.itemId binds to an articleId for "single page" content.
  const articleId =
    (typeof nav.itemId === 'number' && Number.isFinite(nav.itemId) ? nav.itemId : 0) ||
    (typeof nav.pageId === 'number' && Number.isFinite(nav.pageId) ? nav.pageId : 0)

  if (articleId > 0) {
    const article = await getCmsArticle(articleId)
    let body = String(article.content || article.detail || '').trim()
    if (!body) {
      try {
        const list = await listCmsArticleContent({ articleId, limit: 1 })
        const hit = Array.isArray(list) ? list[0] : null
        if (hit?.content) body = String(hit.content).trim()
      } catch {
        // ignore
      }
    }
    return { title: article.title?.trim() || String(nav.title || '单页'), body, article }
  }

  // Fallback: show navigation meta as content when no binding exists.
  return {
    title: String(nav.title || '单页'),
    body: String(nav.comments || nav.meta || '').trim()
  }
}

const {
  data: contentData,
  pending: contentPending,
  error: contentError
} = useAsyncData(
  () => `cms-single-page-content-${parentId.value}-${activeNav.value?.navigationId ?? 'none'}`,
  async () => {
    if (!activeNav.value) return { title: '', body: '' }
    return loadSinglePageContent(activeNav.value)
  },
  { watch: [activeNav] }
)

const parentTitle = computed(() => children.value[0]?.parentName?.trim() || `页面 ${parentId.value}`)
const parentDescription = computed(() => '')
const parentBanner = computed(() => '')

const contentTitle = computed(() => contentData.value?.title?.trim() || '')
const contentBody = computed(() => contentData.value?.body || '')
const articleMeta = computed(() => contentData.value?.article)

watchEffect(() => {
  if (!Number.isFinite(parentId.value)) return
  usePageSeo({
    title: contentTitle.value || parentTitle.value,
    description:
      (articleMeta.value?.overview?.trim() || parentDescription.value || contentTitle.value || parentTitle.value),
    path: route.fullPath
  })
})
</script>
