<script setup lang="ts">
import { ref, computed, onMounted } from 'vue'
import { useRouter } from 'vue-router'
import { NButton, NEmpty, NInput, NPagination, NDropdown, NSpace, NModal, NForm, NFormItem, NIcon, type FormRules } from 'naive-ui'
import { CloseOutline, SaveOutline, AddOutline } from '@vicons/ionicons5'
import { api } from '../../api/client'
import { useToast } from '../../composables/useToast'
import { useLiteraturePreview } from '../../composables/useLiteraturePreview'
import { usePagination } from '../../composables/usePagination'
import PageSkeleton from '../../components/common/PageSkeleton.vue'
import type { LiteratureItem, FolderItem } from '../../types'
import LiteratureCard from '../../components/literature/LiteratureCard.vue'
import LiteraturePreviewDrawer from '../../components/literature/LiteraturePreviewDrawer.vue'

const router = useRouter()
const toast = useToast()
const items = ref<LiteratureItem[]>([])
const folders = ref<FolderItem[]>([])
const sharedFolders = ref<FolderItem[]>([])
const loading = ref(true)
const foldersLoading = ref(true)
const searchQuery = ref('')
const selectedFolderId = ref<string | null>(null)
const selectedFolderType = ref<'personal' | 'shared' | null>(null)
const readingStatusFilter = ref('')
const showFolderModal = ref(false)
const editingFolder = ref<FolderItem | null>(null)
const folderForm = ref({ name: '', description: '', color: '#1890ff' })
const savingFolder = ref(false)
const folderFormRef = ref()
const folderRules: FormRules = {
  name: { required: true, message: '请输入文件夹名称', trigger: 'blur' },
}

const exportOptions = [
  { label: 'BibTeX', key: 'bibtex' },
  { label: 'RIS', key: 'ris' },
  { label: 'EndNote', key: 'endnote' },
  { label: 'CSV', key: 'csv' },
]

const { showPreview, previewPmid, openPreview: setPreviewPmid, closePreview } = useLiteraturePreview()
const { page, total, goToPage } = usePagination({
  fetchFn: async (p: number) => {
    loading.value = true
    try {
      if (selectedFolderType.value === 'shared' && selectedFolderId.value) {
        // 共享收藏夹：加载全团队文献
        const { data } = await api.get(`/teams/shared-folders/${selectedFolderId.value}/articles`, {
          params: { page: p, page_size: 20 }
        })
        items.value = (data.items || []).map((a: any) => ({
          pmid: a.pmid, title: a.title, journal: a.journal,
          pub_year: a.pub_year, authors: a.authors, doi: a.doi,
          tags: a.tags || [],
          _saved_by: a.saved_by,
          _saved_at: a.saved_at,
        }))
        total.value = data.total || 0
      } else {
        const params: Record<string, any> = { page: p, page_size: 20 }
        if (selectedFolderId.value) params.folder_id = selectedFolderId.value
        const { data } = await api.get('/literature/saved', { params })
        items.value = data.items || []
        total.value = data.total || 0
      }
    } catch (e) { toast.apiError(e, '加载收藏文献失败，请重试') }
    finally { loading.value = false }
  },
  pageSize: 20,
})

const savedPmids = computed(() => new Set(items.value.map(i => i.pmid)))

const filteredItems = computed(() => {
  const q = searchQuery.value.toLowerCase().trim()
  return items.value.filter((i: any) => {
    if (q && !(i.title || '').toLowerCase().includes(q) &&
        !(i.journal || '').toLowerCase().includes(q) &&
        !String(i.pmid || '').includes(q)) return false
    if (readingStatusFilter.value && i.reading_status !== readingStatusFilter.value) return false
    return true
  })
})

async function loadFolders() {
  foldersLoading.value = true
  try {
    const [personalRes, sharedRes] = await Promise.all([
      api.get('/settings/folders'),
      api.get('/teams/shared-folders'),
    ])
    folders.value = personalRes.data.items || []
    sharedFolders.value = sharedRes.data.folders || []
  } catch (e) { toast.apiError(e, '加载文件夹失败') }
  finally { foldersLoading.value = false }
}

onMounted(async () => {
  await Promise.all([loadFolders(), goToPage(1)])
})

function selectFolder(fid: string | null, type: 'personal' | 'shared' | null = null) {
  selectedFolderId.value = fid
  selectedFolderType.value = type
  goToPage(1)
}

function goDetail(item: LiteratureItem) { router.push(`/app/literature/${item.pmid}`) }

async function handleSave(item: LiteratureItem) {
  try {
    await api.delete(`/literature/${item.pmid}/save`)
    items.value = items.value.filter(i => i.pmid !== item.pmid)
    toast.success('已取消收藏')
  } catch (e) { toast.apiError(e, '取消收藏失败') }
}

function openNewFolder() {
  editingFolder.value = null
  folderForm.value = { name: '', description: '', color: '#1890ff' }
  showFolderModal.value = true
}

function openEditFolder(f: FolderItem) {
  editingFolder.value = f
  folderForm.value = { name: f.name, description: f.description || '', color: f.color }
  showFolderModal.value = true
}

async function saveFolder() {
  try {
    await folderFormRef.value?.validate()
  } catch {
    toast.warning('请填写文件夹名称')
    return
  }
  savingFolder.value = true
  try {
    if (editingFolder.value) {
      await api.put(`/settings/folders/${editingFolder.value.id}`, folderForm.value)
      toast.success('文件夹已更新')
    } else {
      await api.post('/settings/folders', folderForm.value)
      toast.success('文件夹已创建')
    }
    showFolderModal.value = false
    await loadFolders()
  } catch (e) { toast.apiError(e, '保存失败') }
  finally { savingFolder.value = false }
}

async function deleteFolder(f: FolderItem) {
  if (!confirm(`确认删除文件夹「${f.name}」？文献不会被删除，仅移出文件夹。`)) return
  try {
    await api.delete(`/settings/folders/${f.id}`)
    toast.success('文件夹已删除')
    if (selectedFolderId.value === f.id) selectFolder(null)
    await loadFolders()
  } catch (e) { toast.apiError(e, '删除失败') }
}

async function moveToFolder(item: LiteratureItem, fid: string | null) {
  try {
    await api.put(`/literature/${item.pmid}/folder`, { folder_id: fid })
    toast.success(fid ? '已移动到文件夹' : '已移出文件夹')
    if (selectedFolderId.value !== fid) {
      items.value = items.value.filter(i => i.pmid !== item.pmid)
    }
    await loadFolders() // 刷新左侧文件夹文献数
  } catch (e) { toast.apiError(e, '移动失败') }
}

function getFolderActions(item: LiteratureItem) {
  const options: any[] = [{ label: '移出文件夹', key: 'remove' }]
  options.push({ type: 'divider', key: 'd1' })
  options.push({ label: '📁 个人文件夹', type: 'group', key: 'personal' })
  for (const f of folders.value) {
    options.push({ label: f.name, key: f.id })
  }
  if (sharedFolders.value.length) {
    options.push({ type: 'divider', key: 'd2' })
    options.push({ label: '👥 团队共享', type: 'group', key: 'shared' })
    for (const f of sharedFolders.value) {
      options.push({ label: f.name, key: 'shared-' + f.id })
    }
  }
  return {
    options,
    onSelect: (key: string) => {
      if (key === 'remove') moveToFolder(item, null)
      else if (key.startsWith('shared-')) moveToFolder(item, key.replace('shared-', ''))
      else moveToFolder(item, key)
    }
  }
}

function getFolderName() {
  if (selectedFolderType.value === 'shared') {
    const f = sharedFolders.value.find(f => f.id === selectedFolderId.value)
    return f ? '👥 ' + f.name : '共享收藏'
  }
  const f = folders.value.find(f => f.id === selectedFolderId.value)
  return f ? f.name : '收藏'
}

async function handleBatchExport(fmt: string) {
  const pmids = items.value.map(i => i.pmid).filter(Boolean)
  if (!pmids.length) { toast.warning('没有可导出的文献'); return }
  try {
    const res = await api.post(`/literature/export/batch/${fmt}`, null, {
      params: { pmids },
      responseType: 'blob',
    })
    const extMap: Record<string, string> = { bibtex: 'bib', ris: 'ris', endnote: 'enw', csv: 'csv' }
    const url = window.URL.createObjectURL(new Blob([res.data]))
    const a = document.createElement('a')
    a.href = url
    a.download = `export.${extMap[fmt] || fmt}`
    a.click()
    window.URL.revokeObjectURL(url)
    toast.success(`已导出 ${pmids.length} 条文献`)
  } catch (e) { toast.apiError(e, '导出失败') }
}
</script>

<template>
  <div class="library-layout" style="display:flex;gap:16px;max-width:1400px;margin:0 auto;padding:24px">
    <!-- ======== 左侧文件夹栏 ======== -->
    <div class="folder-sidebar" style="width:220px;flex-shrink:0">
      <NButton size="small" block secondary @click="openNewFolder" style="margin-bottom:8px" class="sky-btn"><template #icon><NIcon size="14"><AddOutline /></NIcon></template>新建文件夹</NButton>
      <div style="display:flex;flex-direction:column;gap:2px;margin-bottom:12px">
        <div
          :style="{ padding:'8px 10px', borderRadius:'6px', cursor:'pointer', fontSize:'13px', display:'flex', justifyContent:'space-between', alignItems:'center',
                    background: !selectedFolderId ? 'var(--primary-color, #1890ff)' : 'transparent',
                    color: !selectedFolderId ? '#fff' : 'var(--text-primary, #333)' }"
          @click="selectFolder(null, null)"
        >
          <span>📂 全部文献</span>
          <span style="font-size:11px;opacity:0.7">{{ total }}</span>
        </div>
      </div>

      <!-- 个人文件夹 -->
      <div style="font-size:11px;font-weight:600;color:var(--text-muted);padding:4px 10px;margin-bottom:4px">个人文件夹</div>
      <div style="display:flex;flex-direction:column;gap:2px;margin-bottom:12px">
        <div v-for="f in folders" :key="f.id"
          :style="{ padding:'8px 10px', borderRadius:'6px', cursor:'pointer', fontSize:'13px', display:'flex', justifyContent:'space-between', alignItems:'center',
                    background: selectedFolderId === f.id && selectedFolderType === 'personal' ? 'var(--primary-color, #1890ff)' : 'transparent',
                    color: selectedFolderId === f.id && selectedFolderType === 'personal' ? '#fff' : 'var(--text-primary, #333)' }"
          @click="selectFolder(f.id, 'personal')"
        >
          <div style="display:flex;align-items:center;gap:6px">
            <span :style="{ width:'10px', height:'10px', borderRadius:'50%', background:f.color, display:'inline-block' }"></span>
            <span>{{ f.name }}</span>
          </div>
          <div style="display:flex;align-items:center;gap:4px">
            <span style="font-size:11px;opacity:0.7">{{ f.article_count }}</span>
            <NDropdown trigger="click" :options="[
              { label:'编辑', key:'edit' },
              { label:'删除', key:'delete' },
            ]" @select="(key: string) => {
              if (key === 'edit') openEditFolder(f);
              else if (key === 'delete') deleteFolder(f);
            }">
              <span style="cursor:pointer;font-size:14px;opacity:0.5;hover:opacity:1" @click.stop>⋮</span>
            </NDropdown>
          </div>
        </div>
      </div>

      <!-- 团队共享收藏夹 -->
      <div v-if="sharedFolders.length" style="border-top:1px solid var(--border-color);padding-top:8px">
        <div style="font-size:11px;font-weight:600;color:var(--text-muted);padding:4px 10px;margin-bottom:4px">👥 团队共享</div>
        <div style="display:flex;flex-direction:column;gap:2px">
          <div v-for="f in sharedFolders" :key="'s-'+f.id"
            :style="{ padding:'8px 10px', borderRadius:'6px', cursor:'pointer', fontSize:'13px', display:'flex', justifyContent:'space-between', alignItems:'center',
                      background: selectedFolderId === f.id && selectedFolderType === 'shared' ? 'var(--primary-color, #1890ff)' : 'transparent',
                      color: selectedFolderId === f.id && selectedFolderType === 'shared' ? '#fff' : 'var(--text-primary, #333)' }"
            @click="selectFolder(f.id, 'shared')"
          >
            <div style="display:flex;align-items:center;gap:6px">
              <span :style="{ width:'10px', height:'10px', borderRadius:'50%', background:f.color, display:'inline-block' }"></span>
              <span>{{ f.name }}</span>
            </div>
            <span style="font-size:11px;opacity:0.7">{{ f.article_count }}</span>
          </div>
        </div>
      </div>
    </div>

    <!-- ======== 右侧文献列表 ======== -->
    <div class="library-content" style="flex:1;min-width:0">
      <div class="library-header" style="display:flex;justify-content:space-between;align-items:center;margin-bottom:16px">
        <h2 style="margin:0">{{ selectedFolderId ? getFolderName() : '📁 我的收藏' }}</h2>
        <NSpace>
          <NDropdown :options="exportOptions" @select="handleBatchExport">
            <NButton size="small" class="sky-btn">📥 批量导出</NButton>
          </NDropdown>
        </NSpace>
      </div>
      <div style="margin-bottom:12px;display:flex;gap:8px;flex-wrap:wrap;align-items:center">
        <NInput v-model:value="searchQuery" placeholder="搜索标题、期刊、PMID…" clearable style="flex:1;min-width:180px" />
        <div style="display:flex;gap:4px;font-size:12px">
          <span v-for="opt in [{ value: '', label: '全部' }, { value: 'unread', label: '未读' }, { value: 'reading', label: '在读' }, { value: 'completed', label: '已读' }]" :key="opt.value"
                style="cursor:pointer;padding:2px 10px;border-radius:12px;transition:all .15s"
                :style="{
                  background: readingStatusFilter === opt.value ? 'var(--primary-color,#1890ff)' : 'var(--bg-hover)',
                  color: readingStatusFilter === opt.value ? '#fff' : 'var(--text-secondary)',
                }"
                @click="readingStatusFilter = opt.value">{{ opt.label }}</span>
        </div>
      </div>
      <PageSkeleton :loading="loading">
        <NEmpty v-if="!loading && !filteredItems.length" :description="searchQuery ? '未找到匹配的文献' : '还没有收藏文献。去文献速览看看吧！'" />
        <div v-for="item in filteredItems" :key="item.pmid" style="position:relative">
          <!-- 阅读状态徽标 -->
          <div v-if="item.reading_status && item.reading_status !== 'unread'"
               style="position:absolute;top:8px;left:8px;z-index:2;font-size:11px;padding:1px 8px;border-radius:10px;color:#fff"
               :style="{ background: item.reading_status === 'reading' ? '#f0a020' : '#18a058' }">
            {{ item.reading_status === 'reading' ? '📖 在读' : '✅ 已读' }}
          </div>
          <LiteratureCard
            :item="item"
            compact
            :showSave="selectedFolderType !== 'shared'"
            :savedPmids="savedPmids"
            @detail="goDetail"
            @preview="(item: LiteratureItem) => setPreviewPmid(item.pmid)"
            @save="handleSave"
          />
          <div style="position:absolute;top:8px;right:8px;display:flex;gap:4px;align-items:center">
            <span v-if="(item as any)._saved_by" style="font-size:11px;color:var(--text-muted);background:var(--bg-hover);padding:2px 8px;border-radius:4px">👤 {{ (item as any)._saved_by }}</span>
            <NDropdown v-if="folders.length + sharedFolders.length > 0 && selectedFolderType !== 'shared'" :options="getFolderActions(item).options" @select="(key: string) => getFolderActions(item).onSelect(key)">
              <NButton size="tiny" quaternary circle>📂</NButton>
            </NDropdown>
          </div>
        </div>
        <div v-if="total > 20" style="display:flex;justify-content:center;margin-top:24px">
          <NPagination :page="page" :page-size="20" :item-count="total" @update:page="goToPage" />
        </div>
      </PageSkeleton>
    </div>
  </div>

  <LiteraturePreviewDrawer
    :show="showPreview"
    :pmid="previewPmid"
    @close="closePreview"
    @goDetail="goDetail"
  />

  <!-- 新建/编辑文件夹弹窗 -->
  <NModal v-model:show="showFolderModal" :title="editingFolder ? '编辑文件夹' : '新建文件夹'" preset="card" class="folder-modal" style="width:400px">
    <NForm ref="folderFormRef" :model="folderForm" :rules="folderRules" label-placement="top">
      <NFormItem path="name" label="名称">
        <NInput v-model:value="folderForm.name" placeholder="文件夹名称" />
      </NFormItem>
      <NFormItem label="备注">
        <NInput v-model:value="folderForm.description" placeholder="备注（可选）" type="textarea" rows="2" />
      </NFormItem>
      <NFormItem label="颜色">
        <div style="display:flex;gap:8px;align-items:center">
          <input type="color" v-model="folderForm.color" style="width:40px;height:32px;border:none;cursor:pointer" />
          <span style="font-size:12px;color:var(--text-muted)">{{ folderForm.color }}</span>
        </div>
      </NFormItem>
      <NSpace>
        <NButton @click="showFolderModal = false" class="sky-btn"><template #icon><NIcon size="14"><CloseOutline /></NIcon></template>取消</NButton>
        <NButton type="primary" :loading="savingFolder" @click="saveFolder" class="sky-btn"><template #icon><NIcon size="14"><SaveOutline /></NIcon></template>保存</NButton>
      </NSpace>
    </NForm>
  </NModal>
</template>

<style scoped>
@media (max-width: 768px) {
  .library-layout {
    flex-direction: column;
    padding: 12px;
  }
  .folder-sidebar {
    width: 100% !important;
    flex-shrink: unset !important;
    margin-bottom: 12px;
  }
  .library-header {
    flex-direction: column;
    align-items: flex-start !important;
    gap: 8px;
  }
  .library-header h2 {
    font-size: 20px;
  }
  .folder-modal {
    width: calc(100vw - 32px) !important;
    max-width: 400px;
  }
}
</style>
