/**
 * 书签数据服务
 * 抽象所有 db.links 操作，便于后续替换为 API 调用
 */

import { db } from './db'

/**
 * 将 Date 对象转换为可序列化的格式
 */
function serializeDate(date) {
  if (!date) return null
  if (date instanceof Date) {
    return date.toISOString()
  }
  return date
}

/**
 * 将序列化的日期字符串转换为 Date 对象
 */
function deserializeDate(value) {
  if (!value) return null
  if (value instanceof Date) return value
  const parsed = new Date(value)
  return Number.isNaN(parsed.getTime()) ? null : parsed
}

/**
 * 序列化书签数据（用于存储）
 */
function serializeLink(link) {
  return {
    ...link,
    lastVisitTime: serializeDate(link.lastVisitTime),
    createdAt: serializeDate(link.createdAt),
    updatedAt: serializeDate(link.updatedAt),
  }
}

/**
 * 反序列化书签数据（从存储读取）
 */
function deserializeLink(record) {
  return {
    ...record,
    lastVisitTime: deserializeDate(record.lastVisitTime),
    createdAt: deserializeDate(record.createdAt) ?? new Date(),
    updatedAt: deserializeDate(record.updatedAt) ?? new Date(),
  }
}

/**
 * 获取所有书签（按 order 排序）
 * @returns {Promise<Array>} 书签数组
 */
async function getAllLinks() {
  const records = await db.links.orderBy('order').reverse().toArray()
  return records.map(deserializeLink)
}

/**
 * 根据 ID 获取书签
 * @param {string} id - 书签 ID
 * @returns {Promise<Object|null>} 书签对象或 null
 */
async function getLinkById(id) {
  const record = await db.links.get(id)
  return record ? deserializeLink(record) : null
}

/**
 * 添加书签
 * @param {Object} link - 书签对象
 * @returns {Promise<Object>} 添加的书签对象
 */
async function addLink(link) {
  const serialized = serializeLink(link)
  await db.links.put(serialized)
  return deserializeLink(serialized)
}

/**
 * 更新书签
 * @param {string} id - 书签 ID
 * @param {Object} updates - 更新数据
 * @returns {Promise<Object>} 更新后的书签对象
 */
async function updateLink(id, updates) {
  const existing = await db.links.get(id)
  if (!existing) {
    throw new Error(`未找到 ID 为 "${id}" 的书签`)
  }

  const updated = {
    ...existing,
    ...updates,
    id,
    updatedAt: new Date(),
  }

  const serialized = serializeLink(updated)
  await db.links.put(serialized)
  return deserializeLink(serialized)
}

/**
 * 删除书签
 * @param {string} id - 书签 ID
 * @returns {Promise<void>}
 */
async function deleteLink(id) {
  await db.links.delete(id)
}

/**
 * 记录访问
 * @param {string} id - 书签 ID
 * @returns {Promise<Object|null>} 更新后的书签对象或 null
 */
async function recordVisit(id) {
  const existing = await db.links.get(id)
  if (!existing) return null

  const now = new Date()
  const updated = {
    ...existing,
    visitCount: (existing.visitCount ?? 0) + 1,
    lastVisitTime: now,
    updatedAt: now,
  }

  const serialized = serializeLink(updated)
  await db.links.put(serialized)
  return deserializeLink(serialized)
}

/**
 * 批量导入书签
 * @param {Array} links - 书签数组
 * @param {Object} options - 选项
 * @param {boolean} options.replace - 是否替换现有数据
 * @returns {Promise<number>} 导入后的书签总数
 */
async function importLinks(links, { replace = false } = {}) {
  const serialized = links.map(serializeLink)

  await db.transaction('rw', db.links, async () => {
    if (replace) {
      await db.links.clear()
    }
    if (serialized.length > 0) {
      await db.links.bulkPut(serialized)
    }
  })

  const records = await db.links.orderBy('createdAt').reverse().toArray()
  return records.length
}

/**
 * 导出所有书签
 * @returns {Promise<Object>} 导出数据对象
 */
async function exportLinks() {
  const records = await db.links.orderBy('createdAt').reverse().toArray()
  const serialized = records.map((link) => ({
    ...link,
    lastVisitTime: serializeDate(link.lastVisitTime),
    createdAt: serializeDate(link.createdAt),
    updatedAt: serializeDate(link.updatedAt),
  }))

  return {
    version: '1.0',
    exportedAt: new Date().toISOString(),
    links: serialized,
  }
}

/**
 * 清空所有书签
 * @returns {Promise<void>}
 */
async function clearAll() {
  await db.links.clear()
}

/**
 * 批量更新排序值
 * @param {Array} updates - 更新数组，每个元素包含 { id, order, updatedAt }
 * @returns {Promise<void>}
 */
async function reorderLinks(updates) {
  await db.transaction('rw', db.links, async () => {
    for (const update of updates) {
      await db.links.update(update.id, {
        order: update.order,
        updatedAt: update.updatedAt,
      })
    }
  })
}

/**
 * 批量添加书签（用于浏览器书签导入）
 * @param {Array} links - 书签数组
 * @returns {Promise<void>}
 */
async function bulkAddLinks(links) {
  const serialized = links.map(serializeLink)
  await db.transaction('rw', db.links, async () => {
    await db.links.bulkPut(serialized)
  })
}

/**
 * 获取所有书签（按 createdAt 排序，用于导入后刷新）
 * @returns {Promise<Array>} 书签数组
 */
async function getAllLinksByCreated() {
  const records = await db.links.orderBy('createdAt').reverse().toArray()
  return records.map(deserializeLink)
}

// 导出服务对象
export const linkService = {
  getAllLinks,
  getLinkById,
  addLink,
  updateLink,
  deleteLink,
  recordVisit,
  importLinks,
  exportLinks,
  clearAll,
  reorderLinks,
  bulkAddLinks,
  getAllLinksByCreated,
}

