import { IPaymentMethod,IInvoiceClient,IProduct,IInvoice,GroupWithAddress } from "@/shared/types/invoice";
import  {axiosInstance, endpoints } from "@/utils/axios";
import axios from 'axios';



// add payment mode
const addPaymentUrl = endpoints.payment_mode.add;
export async function createPaymentMode(paymentModeData: IPaymentMethod) {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
      throw new Error('Agency ID not found');
  }
  
  const paymentModeWithAgency = {
      ...paymentModeData,
      agencyId: agencyId
  };
  
  return await axiosInstance.post(addPaymentUrl, paymentModeWithAgency);
}



//list all payment mode

const listPaymentUrl = endpoints.payment_mode.list;
export async function getPaymentModes () {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
    throw new Error('Agency ID not found');
  }
    try{
        const response = await axiosInstance.get(listPaymentUrl+`/${agencyId}`);
        return response.data;
    }catch (error) {
        throw error;
      }
};

// add invoice client
const addInvoiceClientUrl = endpoints.invoice_client.add;
export async function createInvoiceClient(invoiceClientData: IInvoiceClient) {

        const response = await axiosInstance.post(addInvoiceClientUrl, invoiceClientData);
        return response.data;

}

// list invoice client
const listInvoiceClientUrl = endpoints.invoice_client.list;
export async function listInvoiceClient() {
    try {
      const response = await axiosInstance.get(listInvoiceClientUrl);
      return response.data;
    } catch (error) {
      console.error('Error fetching invoice clients:', error);
      throw error;
    }
};

// add product/service
const addProductUrl = endpoints.product.add;
export async function createProduct(productData: IProduct) {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
      throw new Error('Agency ID not found');
  }
  
  const productWithAgency = {
      ...productData,
      agencyId: agencyId
  };
  
  return await axiosInstance.post(addProductUrl, productWithAgency);
}


//list all product/service
const listProductUrl = endpoints.product.list;
export async function getProducts() {
    const agencyId = localStorage.getItem('selectedAgency');
    try {
        const response = await axiosInstance.get(`${listProductUrl}/${agencyId}`);
        return response.data;
    } catch (error) {
        throw error;
    }
}

//list Invoices
export const getInvoicesByAgencyId = async (agencyId: number | null) => {

  try {
    const response = await axiosInstance.get(endpoints.invoice.list+`/${agencyId}`);
    return response.data;
  } catch (error) {
    console.error('Failed to fetch invoices', error);
    throw error;
  }
};

// Find invoice by Id
const invoiceByIdUrl = endpoints.invoice.details;
export const fetchInvoiceById = async (id: string): Promise<IInvoice> => {
  try {
    const response = await axiosInstance.get(`${invoiceByIdUrl}/${id}`);
    return response.data;
  } catch (error) {
    console.error('Error fetching invoice:', error);
    throw new Error('Failed to fetch invoice');
  }
};




// Download signature
const signatureDownloadUrl = endpoints.signature.download;
export const downloadSignature = async (fileName: string): Promise<string> => {
  try {
    const response = await axiosInstance.get(`${signatureDownloadUrl}?fileName=${encodeURIComponent(fileName)}`, {
      responseType: 'blob',
    });
    return URL.createObjectURL(new Blob([response.data]));
  } catch (error) {
    console.error('Error downloading file:', error);
    throw new Error('Failed to download signature');
  }
};

// Update Invoice

const invoiceUpdatedUrl = endpoints.invoice.update;
export async function updateInvoice(id: number, invoice: IInvoice): Promise<IInvoice> {
  try {
    const response = await axiosInstance.put(`${invoiceUpdatedUrl}/${id}`, invoice, {
      headers: {
        'Content-Type': 'application/json',
      },
    });

    return response.data;
  } catch (error: any) {

    throw new Error(`Error updating invoice: ${error.response?.status} - ${error.message}`);
  }
}






const groupUrl = endpoints.user.group;
export const getGroupWithAddress = async (groupId:number) => {
  const token = localStorage.getItem('token');
  if (!token) {
    throw new Error('No authentication token found');
  }
  try {
    const response = await axiosInstance.get(`${groupUrl}/${groupId}/address`, {
      headers: {
        Authorization: `Bearer ${token}`,
      },
    });
    console.log(response.data);
    return response.data;
  } catch (error) {
    console.error('Error fetching group:', error);
    throw error;
  }
};
const createInvoiceUrl = endpoints.invoice.add;
export const createInvoice = async (data: Partial<IInvoice>): Promise<IInvoice> => {
  try {
    const response = await axiosInstance.post(`${createInvoiceUrl}`, data);
    return response.data;
  } catch (error) {
    console.error('Error creating invoice:', error);
    throw error;
  }
};

export const MAX_FILE_SIZE = 5 * 1024 * 1024; // 5MB
export const ALLOWED_TYPES = ['image/png', 'image/jpeg', 'application/pdf'];
export const uploadFile = async (file: File): Promise<string> => {
  if (!ALLOWED_TYPES.includes(file.type)) {
      throw new Error('Seuls les fichiers PNG, JPG, JPEG et PDF sont acceptés.');
  }

  if (file.size > MAX_FILE_SIZE) {
      throw new Error('Le fichier est trop grand. La taille maximale est de 5MB.');
  }

  try {
      const formData = new FormData();
      formData.append('signatureFile', file);

      const response = await axiosInstance.post(endpoints.signature.upload, formData, {
          headers: {
              'Content-Type': 'multipart/form-data',
          },
      });
      return response.data;
  } catch (error) {
      console.error('Erreur lors de l\'upload:', error);
      throw error;
  }
}



export const deleteInvoice = async (id: string) => {
  try {
    const response = await axiosInstance.delete(`${endpoints.invoice.delete}/${id}`);
    return response.data;
  } catch (error) {
    console.error("Error deleting invoice:", error);
    throw error;
  }
};

export const deleteInvoices = async (ids: string[]) => {
  try {
    const response = await axiosInstance.delete(endpoints.invoice.delete_list, {
      data: ids,
    });
    return response.data;
  } catch (error) {
    console.error("Error deleting invoices:", error);
    throw error;
  }
};
// get invoice analytic


export interface InvoiceAnalyticsSummary {
  totalInvoices: number;
  totalAmount: number;
  paid: InvoiceAnalyticsDTO;
  pending: InvoiceAnalyticsDTO;
  overdue: InvoiceAnalyticsDTO;
  draft: InvoiceAnalyticsDTO;
}

export interface InvoiceAnalyticsDTO {
  status: string;
  count: number;
  total: number;
}

export interface ChartLineAreaData {
  labels: string[];
  series: {
    name: string;
    data: number[];
  }[];
}

export interface ChartDonutData {
  series: {
    label: string;
    value: number;
  }[];
}

export interface ChartPieData {
  series: {
    label: string;
    value: number;
  }[];
}

export interface ClientInvoiceDistribution {
  clients: string[];
  series: {
    name: string;
    data: number[];
  }[];
}

export const getInvoiceAnalyticsSummary = async (currency: string): Promise<InvoiceAnalyticsSummary> => {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
    throw new Error('Agency ID not found');
  }
  const response = await axiosInstance.get(`${endpoints.invoice.analytic}/summary`, {
    params: { currency, agencyId }
  });
  return response.data;
};

export const getInvoiceDistribution = async (startDate: string, endDate: string, currency: string): Promise<ChartLineAreaData> => {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
    throw new Error('Agency ID not found');
  }
  const response = await axiosInstance.get(`${endpoints.invoice.analytic}/distribution`, {
    params: { startDate, endDate, currency, agencyId }
  });
  return response.data;
};

export const getTotalRevenueByPaymentMode = async (currency: string): Promise<ChartDonutData> => {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
    throw new Error('Agency ID not found');
  }
  const response = await axiosInstance.get(`${endpoints.invoice.analytic}/payment-mode-revenue`, {
    params: { currency, agencyId }
  });
  return response.data;
};


export const getInvoiceDistributionByStatus = async (currency: string): Promise<ChartPieData> => {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
    throw new Error('Agency ID not found');
  }
  const response = await axiosInstance.get(`${endpoints.invoice.analytic}/status-distribution`, {
    params: { currency, agencyId }
  });
  return response.data;
};

export const getClientInvoiceDistribution = async (currency: string): Promise<ClientInvoiceDistribution> => {
  const agencyId = localStorage.getItem('selectedAgency');
  if (!agencyId) {
    throw new Error('Agency ID not found');
  }
  const response = await axiosInstance.get(`${endpoints.invoice.analytic}/client-distribution`, {
    params: { currency, agencyId }
  });
  return response.data;
};