import { nextTick } from 'vue'

import {
  buildAiDocumentQueryConditionSummary,
  buildAiDocumentQueryThinkingEvents,
  buildAiDocumentQueryMessage,
  filterAiDocumentQueryRecords,
  mergeAiDocumentQueryPayloads,
  resolveAiDocumentQueryIntent
} from '../../utils/aiDocumentQueryModel.js'
import {
  extractExpenseClaimItems,
  fetchApprovalExpenseClaims,
  fetchExpenseClaims
} from '../../services/reimbursements.js'

const AI_DOCUMENT_QUERY_STEP_DELAY_MS = 320

function waitForAiDocumentQueryStep() {
  return new Promise((resolve) => {
    globalThis.setTimeout(resolve, AI_DOCUMENT_QUERY_STEP_DELAY_MS)
  })
}

function completeAiDocumentQueryEvent(events, eventId, content = '') {
  return events.map((event) => (
    event.eventId === eventId
      ? {
          ...event,
          content: content || event.content,
          status: 'completed'
        }
      : event
  ))
}

function failAiDocumentQueryEvents(events) {
  return events.map((event) => ({
    ...event,
    status: event.status === 'completed' ? 'completed' : 'failed'
  }))
}

function resolveAiDocumentQueryFetchPendingText(intent = {}) {
  if (intent.source === 'approval') {
    return '等待调用待我审核单据接口。'
  }
  if (intent.source === 'mine') {
    return '等待调用我名下单据接口。'
  }
  return '等待同时调用我名下单据和待我审核单据接口。'
}

function resolveAiDocumentQueryFetchRunningText(intent = {}) {
  if (intent.source === 'approval') {
    return '正在查询待我审核的单据，接口范围为待办/待审单据列表。'
  }
  if (intent.source === 'mine') {
    return '正在查询我名下的单据，接口范围为当前用户本人单据列表。'
  }
  return '正在查询我可见的单据，接口范围包含我名下单据和待我审核单据列表。'
}

async function fetchAiDocumentQueryPayload(intent = {}) {
  const requestParams = { page: 1, pageSize: 100 }
  if (intent.source === 'approval') {
    return fetchApprovalExpenseClaims(requestParams)
  }
  if (intent.source === 'mine') {
    return fetchExpenseClaims(requestParams)
  }
  const [ownPayload, approvalPayload] = await Promise.all([
    fetchExpenseClaims(requestParams),
    fetchApprovalExpenseClaims(requestParams)
  ])
  return mergeAiDocumentQueryPayloads(
    ownPayload,
    {
      items: extractExpenseClaimItems(approvalPayload),
      querySource: 'approval'
    }
  )
}

export function useWorkbenchAiDocumentQueryFlow({
  conversationMessages,
  createInlineMessage,
  inlineConversationAutoScrollPinned,
  persistCurrentConversation,
  replaceInlineMessage,
  scrollInlineConversationToBottom
}) {
  async function updateAiDocumentQueryThinking(pendingMessage, thinkingEvents, streamStatus = 'streaming') {
    const message = conversationMessages.value.find((item) => item.id === pendingMessage.id) || pendingMessage
    message.stewardPlan = {
      ...(message.stewardPlan || {}),
      streamStatus,
      thinkingEvents
    }
    scrollInlineConversationToBottom({ force: inlineConversationAutoScrollPinned.value })
    await nextTick()
  }

  async function handleAiDocumentQueryIntent(prompt, pendingMessage, options = {}) {
    const intent = resolveAiDocumentQueryIntent(prompt)
    if (!intent) {
      return false
    }

    const conditionSummary = buildAiDocumentQueryConditionSummary(intent)
    let thinkingEvents = buildAiDocumentQueryThinkingEvents(intent, {
      commandFrame: options.commandFrame
    }).map((event) => (
      event.eventId === 'document-query-fetch'
        ? { ...event, content: resolveAiDocumentQueryFetchPendingText(intent) }
        : event
    ))
    await updateAiDocumentQueryThinking(pendingMessage, thinkingEvents)
    await waitForAiDocumentQueryStep()

    thinkingEvents = completeAiDocumentQueryEvent(thinkingEvents, 'document-query-parse')
    thinkingEvents = thinkingEvents.map((event) => (
      event.eventId === 'document-query-fetch'
        ? {
            ...event,
            content: resolveAiDocumentQueryFetchRunningText(intent),
            status: 'running'
          }
        : event
    ))
    await updateAiDocumentQueryThinking(pendingMessage, thinkingEvents)

    try {
      const payload = await fetchAiDocumentQueryPayload(intent)
      const rawCount = extractExpenseClaimItems(payload).length
      const filteredRecords = filterAiDocumentQueryRecords(payload, intent)
      thinkingEvents = completeAiDocumentQueryEvent(
        thinkingEvents,
        'document-query-fetch',
        `接口返回 ${rawCount} 张候选单据，开始按自然语言条件筛选。`
      )
      thinkingEvents = thinkingEvents.map((event) => (
        event.eventId === 'document-query-filter'
          ? {
              ...event,
              content: `按“${conditionSummary}”组合筛选，当前命中 ${filteredRecords.length} 张。`,
              status: 'running'
            }
          : event
      ))
      await updateAiDocumentQueryThinking(pendingMessage, thinkingEvents)
      await waitForAiDocumentQueryStep()

      const finalMessageText = buildAiDocumentQueryMessage(intent, payload, {
        commandFrame: options.commandFrame
      })
      thinkingEvents = completeAiDocumentQueryEvent(
        thinkingEvents,
        'document-query-filter',
        `筛选完成，命中 ${filteredRecords.length} 张单据，已生成卡片结果。`
      )
      replaceInlineMessage(
        pendingMessage.id,
        createInlineMessage('assistant', finalMessageText, {
          id: pendingMessage.id,
          stewardPlan: {
            streamStatus: 'completed',
            thinkingEvents
          },
          suggestedActions: []
        })
      )
    } catch (error) {
      const finalMessageText = error?.message || '查询单据时出现异常，请稍后再试。'
      replaceInlineMessage(
        pendingMessage.id,
        createInlineMessage('assistant', finalMessageText, {
          id: pendingMessage.id,
          stewardPlan: {
            streamStatus: 'failed',
            thinkingEvents: failAiDocumentQueryEvents(thinkingEvents)
          }
        })
      )
    }

    persistCurrentConversation()
    return true
  }

  return {
    handleAiDocumentQueryIntent
  }
}
