import { api, type ApiEnvelope, unwrapApiData } from '@/lib/api'
import { type PageResult } from '@/features/admin/api'
import {
  type CatalogProduct,
  type SourceType,
} from '@/features/catalog/api'

export type PaymentStatus =
  | 'unpaid'
  | 'paying'
  | 'paid'
  | 'pay_failed'
  | 'closed'
  | 'refunding'
  | 'refunded'
  | 'partial_refunded'

export type FulfillmentStatus =
  | 'pending'
  | 'submitting'
  | 'submitted'
  | 'processing'
  | 'completed'
  | 'failed'
  | 'canceled'

export type CourseQueryResultItem = {
  courseId: string | null
  courseName: string
  raw: Record<string, unknown> | null
}

export type CourseQueryResult = {
  product: Pick<
    CatalogProduct,
    | 'id'
    | 'name'
    | 'sourceType'
    | 'provider'
    | 'remoteCategoryId'
    | 'remoteCourseId'
    | 'price'
  >
  query: {
    platform: string
    school: string
    account: string
  }
  courses: CourseQueryResultItem[]
  raw: unknown
}

export type OrderItem = {
  id: string
  orderId: string
  productId: string
  productName: string
  sourceType: SourceType
  externalProductId: string | null
  provider: string | null
  unitPrice: string
  quantity: number
  totalAmount: string
  payload: Record<string, unknown> | null
  encryptedPayload: Record<string, unknown> | null
  createdAt: string
}

export type OrderFulfillment = {
  id: string
  orderId: string
  orderItemId: string
  fulfillmentType: 'third_party_api' | 'local_only' | 'manual'
  status: FulfillmentStatus
  provider: string | null
  externalOrderNo: string | null
  requestPayload: Record<string, unknown> | null
  responsePayload: unknown | null
  errorMessage: string | null
  submittedAt: string | null
  completedAt: string | null
  createdAt: string
  updatedAt: string
}

export type OrderAction = {
  id: string
  orderId: string
  action: string
  sourceType: SourceType
  provider: string | null
  status: 'success' | 'failed'
  operatorId: string | null
  requestPayload: Record<string, unknown> | null
  responsePayload: unknown | null
  errorMessage: string | null
  remark: string | null
  createdAt: string
}

export type OrderDetail = {
  id: string
  orderNo: string
  userId: string
  sourceType: SourceType
  provider: string | null
  totalAmount: string
  payableAmount: string
  paidAmount: string
  paymentStatus: PaymentStatus
  fulfillmentStatus: FulfillmentStatus
  remark: string | null
  paidAt: string | null
  closedAt: string | null
  createdAt: string
  updatedAt: string
  items: OrderItem[]
  fulfillments?: OrderFulfillment[]
  actions?: OrderAction[]
}

export type CreateOrderPayload = {
  productId: string
  quantity: number
  orderPayload: Record<string, unknown>
  selectedCourse?: {
    courseName: string
    courseId: string | null
    raw: Record<string, unknown> | null
  } | null
  expand?: Record<string, unknown> | null
  remark?: string | null
}

export function queryThirdPartyCourses(data: {
  productId: string
  school: string
  account: string
  password: string
  expand?: Record<string, unknown> | null
}) {
  return api
    .post<CourseQueryResult | ApiEnvelope<CourseQueryResult>>(
      '/api/admin/orders/course-query',
      data
    )
    .then((response) => unwrapApiData(response.data))
}

export function createOrder(data: CreateOrderPayload) {
  return api
    .post<OrderDetail | ApiEnvelope<OrderDetail>>('/api/admin/orders', data)
    .then((response) => unwrapApiData(response.data))
}

export function listOrders(params: {
  page: number
  pageSize: number
  keyword?: string
  sourceType?: string
  paymentStatus?: string
  fulfillmentStatus?: string
}) {
  return api
    .get<PageResult<OrderDetail> | ApiEnvelope<PageResult<OrderDetail>>>(
      '/api/admin/orders',
      { params }
    )
    .then((response) => unwrapApiData(response.data))
}

export function getOrderDetail(idOrNo: string) {
  return api
    .get<OrderDetail | ApiEnvelope<OrderDetail>>(
      `/api/admin/orders/${idOrNo}`
    )
    .then((response) => unwrapApiData(response.data))
}

export function markOrderPaid(idOrNo: string) {
  return api
    .patch<OrderDetail | ApiEnvelope<OrderDetail>>(
      `/api/admin/orders/${idOrNo}/mark-paid`
    )
    .then((response) => unwrapApiData(response.data))
}

export type ThirdPartyOrderAction =
  | 'budan'
  | 'gaimi'
  | 'stop'
  | 'priority'
  | 'convert'
  | 'update-time'
  | 'update-cycle'

export type ThirdPartyOrderActionPayload = {
  externalOrderNo?: string | null
  username?: string | null
  newPwd?: string | null
  remark?: string | string[] | null
  city?: string | null
  tag?: string | null
  config?: Record<string, unknown> | string | null
  autoReset?: boolean | number | string | null
  convertToClassId?: string | number | null
  time?: string | number | null
  cycle?: string | number | null
}

export function refreshThirdPartyOrder(
  idOrNo: string,
  data: ThirdPartyOrderActionPayload
) {
  return api
    .post<OrderDetail | ApiEnvelope<OrderDetail>>(
      `/api/admin/orders/${idOrNo}/third-party/refresh`,
      data
    )
    .then((response) => unwrapApiData(response.data))
}

export function runThirdPartyOrderAction(
  idOrNo: string,
  action: ThirdPartyOrderAction,
  data: ThirdPartyOrderActionPayload
) {
  return api
    .post<OrderDetail | ApiEnvelope<OrderDetail>>(
      `/api/admin/orders/${idOrNo}/third-party/${action}`,
      data
    )
    .then((response) => unwrapApiData(response.data))
}

export type LocalOrderAction =
  | 'process'
  | 'complete'
  | 'cancel'
  | 'close'
  | 'remark'

export function runLocalOrderAction(
  idOrNo: string,
  action: LocalOrderAction,
  data: { remark?: string | null }
) {
  return api
    .patch<OrderDetail | ApiEnvelope<OrderDetail>>(
      `/api/admin/orders/${idOrNo}/local/${action}`,
      data
    )
    .then((response) => unwrapApiData(response.data))
}
