const CASE_STAGE_LABELS = {
  planning: '申请规划',
  approved_to_spend: '已批准支出',
  spending: '消费中',
  claiming: '填报中',
  reviewing: '审批中',
  paying: '付款中',
  accounting: '已付款 / 待入账',
  closed: '已结束',
  cancelled: '已取消'
}

const BUSINESS_STATUS_LABELS = {
  draft: '草稿',
  submitted: '已提交',
  returned: '已退回',
  approved: '已审批',
  pending_payment: '待付款',
  paid: '已付款',
  archived: '已归档',
  active: '进行中',
  closed: '已关闭',
  cancelled: '已取消'
}

const EVENT_PRESENTATION = {
  claim_draft_created: { label: '报销草稿已创建', icon: 'mdi mdi-file-plus-outline', tone: 'info' },
  claim_draft_updated: { label: '报销草稿已更新', icon: 'mdi mdi-file-edit-outline', tone: 'info' },
  historical_claim_imported: { label: '历史单据已纳入统一费用事件', icon: 'mdi mdi-history', tone: 'info' },
  application_submitted: { label: '费用申请已提交', icon: 'mdi mdi-send-outline', tone: 'info' },
  claim_submitted: { label: '报销单已提交', icon: 'mdi mdi-send-outline', tone: 'info' },
  approval_stage_completed: { label: '审批节点已完成', icon: 'mdi mdi-account-check-outline', tone: 'success' },
  application_approved: { label: '费用申请已审批', icon: 'mdi mdi-check-decagram-outline', tone: 'success' },
  claim_approved: { label: '报销单已审批', icon: 'mdi mdi-check-decagram-outline', tone: 'success' },
  application_returned: { label: '费用申请被退回', icon: 'mdi mdi-arrow-u-left-top', tone: 'warning' },
  claim_returned: { label: '报销单被退回', icon: 'mdi mdi-arrow-u-left-top', tone: 'warning' },
  reimbursement_draft_generated: { label: '报销草稿已自动生成', icon: 'mdi mdi-robot-outline', tone: 'success' },
  receipt_received: { label: '票据已进入费用事件', icon: 'mdi mdi-receipt-text-plus-outline', tone: 'info' },
  attachment_associated: { label: '票据已归集到报销草稿', icon: 'mdi mdi-file-link-outline', tone: 'success' },
  application_pre_review_completed: { label: '费用申请 AI 预审已完成', icon: 'mdi mdi-shield-search-outline', tone: 'success' },
  claim_pre_review_completed: { label: '报销单 AI 预审已完成', icon: 'mdi mdi-shield-search-outline', tone: 'success' },
  payment_completed: { label: '付款已完成', icon: 'mdi mdi-cash-check', tone: 'success' },
  application_archived: { label: '费用申请已归档', icon: 'mdi mdi-archive-check-outline', tone: 'success' }
}

const FALLBACK_EVENT_PRESENTATION = {
  label: '流程状态已更新',
  icon: 'mdi mdi-timeline-clock-outline',
  tone: 'info'
}

const EVENT_DATE_TIME_FORMATTER = new Intl.DateTimeFormat('zh-CN', {
  year: 'numeric',
  month: '2-digit',
  day: '2-digit',
  hour: '2-digit',
  minute: '2-digit',
  hour12: false
})

function compactText(value) {
  return String(value ?? '').trim()
}

function readField(source, snakeKey, camelKey) {
  return source?.[snakeKey] ?? source?.[camelKey]
}

function resolveStatusLabel(value) {
  const normalized = compactText(value)
  return BUSINESS_STATUS_LABELS[normalized] || normalized
}

function buildStateTransitionSummary(payload) {
  const previousStatus = resolveStatusLabel(readField(payload, 'previous_status', 'previousStatus'))
  const nextStatus = resolveStatusLabel(readField(payload, 'next_status', 'nextStatus'))
  const nextStage = compactText(readField(payload, 'next_approval_stage', 'nextApprovalStage'))
  const transition = previousStatus && nextStatus
    ? `${previousStatus} → ${nextStatus}`
    : nextStatus
      ? `状态更新为${nextStatus}`
      : ''

  if (transition && nextStage) {
    return `${transition} · 当前节点：${nextStage}`
  }

  return transition || (nextStage ? `当前节点：${nextStage}` : '')
}

function buildHistoricalClaimImportSummary(payload) {
  const currentStatus = resolveStatusLabel(readField(payload, 'next_status', 'nextStatus'))
  const currentStage = compactText(readField(payload, 'next_approval_stage', 'nextApprovalStage'))
  const currentStateParts = []

  if (currentStatus) {
    currentStateParts.push(`纳入时状态：${currentStatus}`)
  }
  if (currentStage) {
    currentStateParts.push(`纳入时节点：${currentStage}`)
  }

  const currentStateSummary = currentStateParts.length
    ? `${currentStateParts.join(' · ')}。`
    : ''

  return `系统已根据原单据建立费用事件档案。${currentStateSummary}导入前办理记录以原单据为准，后续动作将在此持续记录。`
}

function buildEventSummary(eventType, payload) {
  if (eventType === 'historical_claim_imported') {
    return buildHistoricalClaimImportSummary(payload)
  }

  const reason = compactText(payload?.reason)
  if (reason) {
    return reason
  }

  const opinion = compactText(payload?.opinion)
  if (opinion) {
    return opinion
  }

  if (eventType === 'reimbursement_draft_generated') {
    const applicationClaimNo = compactText(readField(payload, 'application_claim_no', 'applicationClaimNo'))
    if (applicationClaimNo) {
      return `已由费用申请 ${applicationClaimNo} 自动生成报销草稿。`
    }
  }

  if (eventType === 'receipt_received') {
    const fileName = compactText(readField(payload, 'file_name', 'fileName'))
    return fileName
      ? `${fileName} 已进入费用事件并完成票据识别。`
      : '票据已进入费用事件并完成识别。'
  }

  if (eventType === 'attachment_associated') {
    const claimNo = compactText(readField(payload, 'claim_no', 'claimNo'))
    return claimNo
      ? `票据已自动归集到报销草稿 ${claimNo}。`
      : '票据已自动归集到当前报销草稿。'
  }

  if (['application_pre_review_completed', 'claim_pre_review_completed'].includes(eventType)) {
    const message = compactText(payload?.message)
    if (message) {
      return message
    }
    const passed = readField(payload, 'passed', 'passed')
    const blockingCount = Number(readField(payload, 'blocking_risk_count', 'blockingRiskCount') || 0)
    return passed === false
      ? `AI 预审发现 ${blockingCount} 条重大风险，请处理后重新预审。`
      : 'AI 预审已通过，可以继续提交审批。'
  }

  if (eventType === 'application_archived') {
    const reimbursementClaimNo = compactText(readField(payload, 'reimbursement_claim_no', 'reimbursementClaimNo'))
    if (reimbursementClaimNo) {
      return `关联报销单 ${reimbursementClaimNo} 已付款，本费用申请已归档。`
    }
  }

  if (eventType === 'payment_completed') {
    const archivedApplications = readField(payload, 'archived_applications', 'archivedApplications')
    const archivedCount = Array.isArray(archivedApplications)
      ? archivedApplications.length
      : 0
    if (archivedCount > 0) {
      return `付款完成，并同步归档 ${archivedCount} 张关联费用申请。`
    }
  }

  return buildStateTransitionSummary(payload) || '业务状态已更新。'
}

function formatOccurredAt(value) {
  const normalized = compactText(value)
  if (!normalized) {
    return '时间待同步'
  }

  const date = new Date(normalized)
  if (Number.isNaN(date.getTime())) {
    return normalized
  }

  return EVENT_DATE_TIME_FORMATTER.format(date).replaceAll('/', '-')
}

function resolveActorLabel(event) {
  const actorId = compactText(readField(event, 'actor_id', 'actorId'))
  const actorType = compactText(readField(event, 'actor_type', 'actorType')).toLowerCase()
  if (actorType === 'system' || actorId.toLowerCase() === 'system') {
    return '系统'
  }

  return actorId || '操作人待同步'
}

function normalizeEvent(event, index) {
  const eventType = compactText(readField(event, 'event_type', 'eventType'))
  const presentation = EVENT_PRESENTATION[eventType] || FALLBACK_EVENT_PRESENTATION
  const occurredAt = readField(event, 'occurred_at', 'occurredAt')
  const timestamp = new Date(occurredAt || '').getTime()
  const payload = readField(event, 'payload_json', 'payloadJson') || {}
  const isFailedPreReview = (
    ['application_pre_review_completed', 'claim_pre_review_completed'].includes(eventType)
    && readField(payload, 'passed', 'passed') === false
  )

  return {
    id: compactText(event?.id) || `${eventType || 'event'}-${index}`,
    eventType,
    label: presentation.label,
    icon: presentation.icon,
    tone: isFailedPreReview ? 'warning' : presentation.tone,
    summary: buildEventSummary(eventType, payload),
    actorLabel: eventType === 'historical_claim_imported' ? '系统' : resolveActorLabel(event),
    occurredAt: compactText(occurredAt),
    occurredAtLabel: formatOccurredAt(occurredAt),
    sortTimestamp: Number.isNaN(timestamp) ? null : timestamp,
    sourceIndex: index
  }
}

export function buildExpenseCaseTimelineViewModel(payload = {}) {
  const events = Array.isArray(payload?.events)
    ? payload.events.map(normalizeEvent).sort((left, right) => {
        if (left.sortTimestamp !== null && right.sortTimestamp !== null) {
          return left.sortTimestamp - right.sortTimestamp || left.sourceIndex - right.sourceIndex
        }
        return left.sourceIndex - right.sourceIndex
      })
    : []

  return {
    caseId: compactText(payload?.id),
    caseNo: compactText(readField(payload, 'case_no', 'caseNo')),
    stage: compactText(readField(payload, 'current_stage', 'currentStage')),
    stageLabel: CASE_STAGE_LABELS[compactText(readField(payload, 'current_stage', 'currentStage'))] || '流程跟进中',
    status: compactText(payload?.status),
    statusLabel: resolveStatusLabel(payload?.status) || '状态待同步',
    linkCount: Array.isArray(payload?.links) ? payload.links.length : 0,
    events
  }
}

export function isExpenseCaseNotAvailableError(error) {
  return Number(error?.status) === 404
}
