'use client'

import { useAuthStore } from './auth-store'

const API_BASE = '/api'

class ApiClient {
  private getHeaders(): HeadersInit {
    const token = useAuthStore.getState().token
    const headers: HeadersInit = {
      'Content-Type': 'application/json',
    }
    if (token) {
      headers['Authorization'] = `Bearer ${token}`
    }
    return headers
  }

  private async request<T>(endpoint: string, options?: RequestInit): Promise<T> {
    const response = await fetch(`${API_BASE}${endpoint}`, {
      ...options,
      headers: {
        ...this.getHeaders(),
        ...options?.headers,
      },
    })

    if (!response.ok) {
      const error = await response.json().catch(() => ({ error: 'Error de conexión' }))
      throw new Error(error.error || `Error ${response.status}`)
    }

    return response.json()
  }

  // Auth
  async login(email: string, password: string) {
    return this.request<{ token: string; user: { id: string; email: string; name: string; company?: string | null; role: string } }>('/auth/login', {
      method: 'POST',
      body: JSON.stringify({ email, password }),
    })
  }

  async register(data: { email: string; password: string; name: string; phone?: string }) {
    return this.request<{ token: string; user: { id: string; email: string; name: string; role: string } }>('/auth/register', {
      method: 'POST',
      body: JSON.stringify(data),
    })
  }

  async getMe() {
    return this.request<{ user: { id: string; email: string; name: string; company?: string | null; role: string; phone?: string } }>('/auth/me')
  }

  async changePassword(currentPassword: string, newPassword: string) {
    return this.request('/auth/change-password', {
      method: 'POST',
      body: JSON.stringify({ currentPassword, newPassword }),
    })
  }

  // Reviews
  async getReviews(params?: Record<string, string>) {
    const query = params ? '?' + new URLSearchParams(params).toString() : ''
    return this.request<{ reviews: any[]; total: number; page: number; totalPages: number }>(`/reviews${query}`)
  }

  async getMyReviews(params?: Record<string, string>) {
    const query = params ? '?' + new URLSearchParams(params).toString() : ''
    return this.request<{ reviews: any[]; total: number; page: number; totalPages: number }>(`/reviews/my${query}`)
  }

  async getReview(id: string) {
    return this.request<{ review: any }>(`/reviews/${id}`)
  }

  async createReview(data: { rating: number; title: string; content: string; serviceDate: string; serviceType: string; subType?: string }, photos?: File[]) {
    if (photos && photos.length > 0) {
      const formData = new FormData()
      formData.append('rating', data.rating.toString())
      formData.append('title', data.title)
      formData.append('content', data.content)
      formData.append('serviceDate', data.serviceDate)
      formData.append('serviceType', data.serviceType)
      if (data.subType) formData.append('subType', data.subType)
      photos.forEach((photo) => formData.append('photos', photo))

      const token = useAuthStore.getState().token
      const response = await fetch(`${API_BASE}/reviews`, {
        method: 'POST',
        headers: {
          ...(token ? { Authorization: `Bearer ${token}` } : {}),
        },
        body: formData,
      })
      if (!response.ok) {
        const error = await response.json().catch(() => ({ error: 'Error de conexión' }))
        throw new Error(error.error || `Error ${response.status}`)
      }
      return response.json()
    }

    return this.request<{ review: any }>('/reviews', {
      method: 'POST',
      body: JSON.stringify(data),
    })
  }

  async respondToReview(id: string, data: { actionTaken: string; internalNote: string; responseToClient: string }) {
    return this.request(`/reviews/${id}/respond`, {
      method: 'PUT',
      body: JSON.stringify(data),
    })
  }

  async acknowledgeReview(id: string) {
    return this.request(`/reviews/${id}/acknowledge`, {
      method: 'PUT',
    })
  }

  async updateReviewStatus(id: string, status: string) {
    return this.request(`/reviews/${id}/status`, {
      method: 'PUT',
      body: JSON.stringify({ status }),
    })
  }

  async deleteReview(id: string) {
    return this.request(`/reviews/${id}`, {
      method: 'DELETE',
    })
  }

  async uploadPhotos(reviewId: string, photos: File[]) {
    const formData = new FormData()
    photos.forEach((photo) => formData.append('photos', photo))

    const token = useAuthStore.getState().token
    const response = await fetch(`${API_BASE}/reviews/${reviewId}/photos`, {
      method: 'POST',
      headers: {
        ...(token ? { Authorization: `Bearer ${token}` } : {}),
      },
      body: formData,
    })
    if (!response.ok) {
      const error = await response.json().catch(() => ({ error: 'Error de conexión' }))
      throw new Error(error.error || `Error ${response.status}`)
    }
    return response.json()
  }

  // Dashboard
  async getManagerDashboard() {
    return this.request<any>('/dashboard/manager')
  }

  async getSupervisorDashboard() {
    return this.request<any>('/dashboard/supervisor')
  }

  // Notifications
  async getNotifications(params?: Record<string, string>) {
    const query = params ? '?' + new URLSearchParams(params).toString() : ''
    return this.request<{ notifications: any[]; total: number }>(`/notifications${query}`)
  }

  async markNotificationRead(id: string) {
    return this.request(`/notifications/${id}/read`, { method: 'PUT' })
  }

  async markAllNotificationsRead() {
    return this.request('/notifications/read-all', { method: 'PUT' })
  }

  async getUnreadCount() {
    return this.request<{ count: number }>('/notifications/unread-count')
  }

  // Users/Customers
  async getCustomers(params?: Record<string, string>) {
    const query = params ? '?' + new URLSearchParams(params).toString() : ''
    return this.request<{ customers: any[]; total: number }>(`/users/customers${query}`)
  }

  async createCustomer(data: { email: string; name: string; company?: string; phone?: string; password: string }) {
    return this.request('/users/customers', {
      method: 'POST',
      body: JSON.stringify(data),
    })
  }

  async updateCustomer(id: string, data: { name?: string; phone?: string }) {
    return this.request(`/users/customers/${id}`, {
      method: 'PUT',
      body: JSON.stringify(data),
    })
  }

  async deactivateCustomer(id: string) {
    return this.request(`/users/customers/${id}`, { method: 'DELETE' })
  }

  async getSupervisors() {
    return this.request<{ supervisors: any[] }>('/users/supervisors')
  }

  async createSupervisor(data: { email: string; name: string; phone?: string; password: string }) {
    return this.request('/users/supervisors', {
      method: 'POST',
      body: JSON.stringify(data),
    })
  }

  // Reports
  async getReportSummary(params?: Record<string, string>) {
    const query = params ? '?' + new URLSearchParams(params).toString() : ''
    return this.request<any>(`/reports/summary${query}`)
  }

  async getReportBySupervisor() {
    return this.request<any>('/reports/by-supervisor')
  }

  async getReportRatings() {
    return this.request<any>('/reports/ratings')
  }

  // ========== ADMIN API ==========

  // Managers
  async getManagers() {
    return this.request<{ managers: any[] }>('/users/managers')
  }

  async createManager(data: { email: string; name: string; phone?: string; password: string }) {
    return this.request('/users/managers', { method: 'POST', body: JSON.stringify(data) })
  }

  async updateManager(id: string, data: { name?: string; email?: string; phone?: string; password?: string; isActive?: boolean }) {
    return this.request(`/users/managers/${id}`, { method: 'PUT', body: JSON.stringify(data) })
  }

  async toggleManager(id: string) {
    return this.request(`/users/managers/${id}`, { method: 'DELETE' })
  }

  // Admins
  async getAdmins() {
    return this.request<{ admins: any[] }>('/users/admins')
  }

  async createAdmin(data: { email: string; name: string; phone?: string; password: string }) {
    return this.request('/users/admins', { method: 'POST', body: JSON.stringify(data) })
  }

  async updateAdmin(id: string, data: { name?: string; email?: string; phone?: string; password?: string; isActive?: boolean }) {
    return this.request(`/users/admins/${id}`, { method: 'PUT', body: JSON.stringify(data) })
  }

  async toggleAdmin(id: string) {
    return this.request(`/users/admins/${id}`, { method: 'DELETE' })
  }

  // Supervisor management
  async getSupervisor(id: string) {
    return this.request<{ supervisor: any }>(`/users/supervisors/${id}`)
  }

  async updateSupervisor(id: string, data: { name?: string; email?: string; phone?: string; password?: string; isActive?: boolean }) {
    return this.request(`/users/supervisors/${id}`, { method: 'PUT', body: JSON.stringify(data) })
  }

  async toggleSupervisor(id: string) {
    return this.request(`/users/supervisors/${id}`, { method: 'DELETE' })
  }

  // Customer management (extended)
  async toggleCustomer(id: string) {
    return this.request(`/users/customers/${id}`, { method: 'DELETE' })
  }

  // Reset password (any user)
  async resetUserPassword(id: string, newPassword: string) {
    return this.request(`/users/${id}/reset-password`, { method: 'POST', body: JSON.stringify({ newPassword }) })
  }

  // Assign supervisor to customer
  async assignSupervisor(customerId: string, supervisorId: string | null) {
    return this.request(`/users/${customerId}/assign-supervisor`, { method: 'PUT', body: JSON.stringify({ supervisorId }) })
  }

  // Reassign review to different supervisor
  async reassignReview(reviewId: string, supervisorId: string) {
    return this.request(`/reviews/${reviewId}/reassign`, { method: 'PUT', body: JSON.stringify({ supervisorId }) })
  }

  // Bulk delete users
  async bulkDeleteUsers(userIds: string[]) {
    return this.request<{ deletedCount: number; errors: string[] }>('/admin/users/bulk-delete', {
      method: 'POST',
      body: JSON.stringify({ userIds }),
    })
  }

  // Cleanup tools
  async getCleanupOptions() {
    return this.request<{ cleanupOptions: any[] }>('/admin/cleanup')
  }

  async executeCleanup(action: string) {
    return this.request('/admin/cleanup', { method: 'POST', body: JSON.stringify({ action, confirm: true }) })
  }
}

export const api = new ApiClient()
