import { api } from '@/services/api'

export interface ExpenseCategory {
  id: number
  name: string
  slug: string
  status: string
}

export interface Expense {
  id: number
  category?: {
    id: number
    name: string
  } | null
  financial_account?: {
    id: number
    name: string
    type: string
  } | null
  expense_number: string
  expense_date: string
  description: string
  amount: string
  payment_method: string
  vendor: string | null
  reference: string | null
  notes: string | null
  status: string
}

export interface AccountingSummary {
  period: {
    start_date: string
    end_date: string
  }
  income: {
    invoice_payments: string
    pos_sales: string
    total: string
  }
  expenses: {
    count: number
    total: string
    by_category: Array<{
      category: string
      count: number
      total: string
    }>
  }
  net_profit: string
}

export interface ExpenseFilters {
  search?: string
  expense_category_id?: number
  financial_account_id?: number
  payment_method?: string
  status?: string
  date_from?: string
  date_to?: string
  page?: number
  per_page?: number
}

export interface PaginationMeta {
  current_page: number
  from: number | null
  last_page: number
  per_page: number
  to: number | null
  total: number
}

export interface Paginated<T> {
  data: T[]
  meta: PaginationMeta
}

export interface ExpensePayload {
  expense_category_id?: number | null
  financial_account_id?: number | null
  expense_date?: string
  description?: string
  amount?: number
  payment_method?: string
  vendor?: string | null
  reference?: string | null
  notes?: string | null
  status?: string
}

export interface FinancialAccount {
  id: number
  name: string
  type: string
  opening_balance: string
  current_balance: string
  status: string
}

export interface AccountTransaction {
  id: number
  financial_account?: {
    id: number
    name: string
    type: string
  }
  transaction_date: string
  type: string
  direction: string
  amount: string
  description: string
  reference: string | null
  notes: string | null
  source_type: string | null
  source_id: number | null
}

export interface TransactionFilters {
  financial_account_id?: number
  type?: string
  direction?: string
  date_from?: string
  date_to?: string
  page?: number
  per_page?: number
}

export interface TransactionPayload {
  financial_account_id: number
  transaction_date: string
  type: string
  direction: string
  amount: number
  description: string
  reference?: string | null
  notes?: string | null
}

export interface TransferPayload {
  from_account_id: number
  to_account_id: number
  transaction_date: string
  amount: number
  description: string
  reference?: string | null
  notes?: string | null
}

export interface ExpenseCategoryPayload {
  name?: string
  status?: string
}

export interface FinancialAccountPayload {
  name?: string
  type?: string
  opening_balance?: number
  status?: string
}

export const accountingService = {
  async summary(startDate: string, endDate: string) {
    const { data } = await api.get<{ data: AccountingSummary }>('/accounting/summary', {
      params: {
        start_date: startDate,
        end_date: endDate,
      },
    })

    return data.data
  },

  async categories(status = 'active') {
    const { data } = await api.get<{ data: ExpenseCategory[] }>('/accounting/expense-categories', {
      params: { status },
    })

    return data.data
  },

  async createCategory(payload: { name: string }) {
    const { data } = await api.post<{ data: ExpenseCategory }>('/accounting/expense-categories', payload)

    return data.data
  },

  async updateCategory(category: ExpenseCategory, payload: ExpenseCategoryPayload) {
    const { data } = await api.patch<{ data: ExpenseCategory }>(`/accounting/expense-categories/${category.id}`, payload)

    return data.data
  },

  async accounts(status = 'active') {
    const { data } = await api.get<{ data: FinancialAccount[] }>('/accounting/accounts', {
      params: { status },
    })

    return data.data
  },

  async createAccount(payload: { name: string; type?: string; opening_balance?: number; status?: string }) {
    const { data } = await api.post<{ data: FinancialAccount }>('/accounting/accounts', payload)

    return data.data
  },

  async updateAccount(account: FinancialAccount, payload: FinancialAccountPayload) {
    const { data } = await api.patch<{ data: FinancialAccount }>(`/accounting/accounts/${account.id}`, payload)

    return data.data
  },

  async transactions(filters: TransactionFilters = {}) {
    const { data } = await api.get<{ data: Paginated<AccountTransaction> }>('/accounting/transactions', {
      params: filters,
    })

    return data.data
  },

  async exportTransactionsCsv(filters: TransactionFilters = {}) {
    const { data } = await api.get<Blob>('/accounting/transactions/export/csv', {
      params: filters,
      responseType: 'blob',
    })

    return data
  },

  async createTransaction(payload: TransactionPayload) {
    const { data } = await api.post<{ data: AccountTransaction }>('/accounting/transactions', payload)

    return data.data
  },

  async createTransfer(payload: TransferPayload) {
    const { data } = await api.post<{ data: { reference: string; transactions: AccountTransaction[] } }>(
      '/accounting/transfers',
      payload,
    )

    return data.data
  },

  async expenses(filters: ExpenseFilters = {}) {
    const { data } = await api.get<{ data: Paginated<Expense> }>('/accounting/expenses', {
      params: filters,
    })

    return data.data
  },

  async exportExpensesCsv(filters: ExpenseFilters = {}) {
    const { data } = await api.get<Blob>('/accounting/expenses/export/csv', {
      params: filters,
      responseType: 'blob',
    })

    return data
  },

  async createExpense(payload: ExpensePayload) {
    const { data } = await api.post<{ data: Expense }>('/accounting/expenses', payload)

    return data.data
  },

  async updateExpense(expense: Expense, payload: ExpensePayload) {
    const { data } = await api.patch<{ data: Expense }>(`/accounting/expenses/${expense.id}`, payload)

    return data.data
  },
}
