import { computed, ref } from 'vue'
import { defineStore } from 'pinia'
import { useMyTask } from '@/composables/useMyTask'
import { DEFAULT_PAGE_SIZE } from '@/types/pagination'
import { taskDueInfo, taskStatusLabel } from '@/shared/utils/format'
import type { ApiMember } from '@/types/repo'
import type { ApiMyTaskRow, MyTaskListQuery } from '@/types/my-task'
import type {
  MyTaskGroup,
  MyTaskRow,
  TaskStatus,
  User as UserView,
} from '@/mock/relay.mock'

// API 멤버 → 화면용 User(이니셜/색상 파생)
function toUserView(m: ApiMember): UserView {
  return {
    id: m.id,
    name: m.name,
    role: m.role ?? '',
    avatarUrl: m.avatarUrl,
  }
}

// 상태 그룹 순서/라벨 — 담당 뷰와 지시 뷰가 다르다(시안 기준)
const ASSIGNED_ORDER: TaskStatus[] = ['changes', 'prog', 'todo', 'review', 'done']
const ISSUED_ORDER: TaskStatus[] = ['review', 'prog', 'changes', 'todo', 'done']
const ASSIGNED_LABEL: Record<TaskStatus, string> = {
  changes: '수정 요청',
  prog: '진행 중',
  todo: '할 일',
  review: '승인 대기',
  done: '완료',
}
const ISSUED_LABEL: Record<TaskStatus, string> = {
  changes: '수정 요청함',
  prog: '진행 중',
  todo: '할 일',
  review: '승인 대기',
  done: '완료',
}

// API 행 → 담당 뷰 행 (누가 지시했는지 표시)
function toAssignedRow(api: ApiMyTaskRow): MyTaskRow {
  const due = taskDueInfo(api.dueDate, api.status === 'done')
  const [, total] = api.checklist
  const isDone = api.status === 'done'
  return {
    id: api.id,
    projectId: api.projectId,
    title: api.title,
    status: api.status,
    projectName: api.projectName,
    checklist: total > 0 ? api.checklist : undefined,
    metaText: `지시 · ${api.issuer?.name ?? '알 수 없음'}`,
    dueLabel: isDone ? due.listLabel : due.dateLabel || undefined,
    dday: due.dday || undefined,
    ddayLevel: due.ddayLevel || undefined,
    overdue: due.overdue || undefined,
    statusLabel: taskStatusLabel(api.status),
    done: isDone || undefined,
  }
}

// API 행 → 지시 뷰 행 (담당자 미니 아바타 + 승인 대기 강조)
function toIssuedRow(api: ApiMyTaskRow): MyTaskRow {
  const due = taskDueInfo(api.dueDate, api.status === 'done')
  const [, total] = api.checklist
  const isDone = api.status === 'done'
  const isReview = api.status === 'review'
  const names = api.assignees.map((a) => a.name).join(', ') || '미지정'
  return {
    id: api.id,
    projectId: api.projectId,
    title: api.title,
    status: api.status,
    projectName: api.projectName,
    checklist: total > 0 ? api.checklist : undefined,
    assignees: api.assignees.map(toUserView),
    metaText: api.status === 'changes' ? `${names}에게 수정 요청` : names,
    metaAttn: isReview || undefined,
    dueLabel: isDone ? due.listLabel : due.dateLabel || undefined,
    dday: due.dday || undefined,
    ddayLevel: due.ddayLevel || undefined,
    overdue: due.overdue || undefined,
    statusLabel: isReview ? undefined : taskStatusLabel(api.status),
    reviewBtn: isReview || undefined,
    done: isDone || undefined,
  }
}

// 행 배열 → 상태 그룹 배열(순서·라벨 적용, 빈 그룹 제외)
function groupRows(
  rows: MyTaskRow[],
  order: TaskStatus[],
  labelMap: Record<TaskStatus, string>,
  issued: boolean,
): MyTaskGroup[] {
  const groups: MyTaskGroup[] = []
  for (const key of order) {
    const groupRows = rows.filter((row) => row.status === key)
    if (groupRows.length === 0) continue
    const group: MyTaskGroup = { key, label: labelMap[key], rows: groupRows }
    // 지시 뷰의 승인 대기 그룹은 강조(내 승인 필요)
    if (issued && key === 'review') {
      group.attn = true
      group.action = '· 내 승인 필요'
    }
    groups.push(group)
  }
  return groups
}

// 내 업무 스토어 — 담당/지시 두 뷰(상태 그룹) + 더보기 페이지네이션
// 원시 행을 누적하고 그룹핑은 computed 로 파생(더보기 시 같은 그룹에 자연스럽게 합쳐짐)
export const useMyTaskStore = defineStore('myTask', () => {
  const assignedRaw = ref<ApiMyTaskRow[]>([])
  const issuedRaw = ref<ApiMyTaskRow[]>([])
  const assignedTotal = ref(0)
  const issuedTotal = ref(0)
  const assignedPage = ref(0)
  const issuedPage = ref(0)
  const loading = ref(false)
  const loadingMore = ref(false)
  // 검색/프로젝트/정렬 조건 — 더보기에서 같은 조건으로 다음 페이지를 잇기 위해 보관
  const query = ref<MyTaskListQuery>({})

  const myTaskApi = useMyTask()

  const assigned = computed(() =>
    groupRows(assignedRaw.value.map(toAssignedRow), ASSIGNED_ORDER, ASSIGNED_LABEL, false),
  )
  const issued = computed(() =>
    groupRows(issuedRaw.value.map(toIssuedRow), ISSUED_ORDER, ISSUED_LABEL, true),
  )
  const assignedHasMore = computed(() => assignedRaw.value.length < assignedTotal.value)
  const issuedHasMore = computed(() => issuedRaw.value.length < issuedTotal.value)

  // 첫 페이지(리셋) — 담당/지시 동시 조회. 검색/프로젝트/정렬 조건 적용
  async function fetchAll(q: MyTaskListQuery = {}): Promise<void> {
    query.value = q
    loading.value = true
    try {
      const [a, i] = await Promise.all([
        myTaskApi.assigned(1, DEFAULT_PAGE_SIZE, query.value),
        myTaskApi.issued(1, DEFAULT_PAGE_SIZE, query.value),
      ])
      assignedRaw.value = a.items
      assignedTotal.value = a.total
      assignedPage.value = 1
      issuedRaw.value = i.items
      issuedTotal.value = i.total
      issuedPage.value = 1
    } finally {
      loading.value = false
    }
  }

  // 담당 뷰 다음 페이지(더보기)
  async function loadMoreAssigned(): Promise<void> {
    if (loadingMore.value || !assignedHasMore.value) return
    loadingMore.value = true
    try {
      const a = await myTaskApi.assigned(assignedPage.value + 1, DEFAULT_PAGE_SIZE, query.value)
      assignedRaw.value.push(...a.items)
      assignedTotal.value = a.total
      assignedPage.value += 1
    } finally {
      loadingMore.value = false
    }
  }

  // 지시 뷰 다음 페이지(더보기)
  async function loadMoreIssued(): Promise<void> {
    if (loadingMore.value || !issuedHasMore.value) return
    loadingMore.value = true
    try {
      const i = await myTaskApi.issued(issuedPage.value + 1, DEFAULT_PAGE_SIZE, query.value)
      issuedRaw.value.push(...i.items)
      issuedTotal.value = i.total
      issuedPage.value += 1
    } finally {
      loadingMore.value = false
    }
  }

  return {
    assigned,
    issued,
    loading,
    loadingMore,
    assignedHasMore,
    issuedHasMore,
    fetchAll,
    loadMoreAssigned,
    loadMoreIssued,
  }
})
