import apiClient from './apiClient';

export interface Banner {
  id: number;
  title: string;
  description?: string;
  image_url: string;
  link_url?: string;
  position: string;
  display_order: number;
  is_active: boolean;
  start_date?: string;
  end_date?: string;
  created_at: string;
  updated_at: string;
}

export interface BannerListResponse {
  success: boolean;
  status?: string;
  data: {
    banners: Banner[];
  };
  message?: string;
}

type CacheEntry = {
  timestamp: number;
  response: BannerListResponse;
};

const BANNER_CACHE_TTL_MS = 5 * 60 * 1000; 
const memoryCache = new Map<string, CacheEntry>();

const getCacheKey = (position?: string) =>
  position ? `banners:position:${position}` : 'banners:active';

const isCacheValid = (entry: CacheEntry | undefined) => {
  if (!entry) return false;
  return Date.now() - entry.timestamp < BANNER_CACHE_TTL_MS;
};

const loadFromStorage = (key: string): CacheEntry | undefined => {
  if (typeof window === 'undefined') return undefined;
  try {
    const raw = window.localStorage.getItem(key);
    if (!raw) return undefined;
    const parsed = JSON.parse(raw) as CacheEntry;
    return isCacheValid(parsed) ? parsed : undefined;
  } catch {
    return undefined;
  }
};

const saveToStorage = (key: string, entry: CacheEntry) => {
  if (typeof window === 'undefined') return;
  try {
    window.localStorage.setItem(key, JSON.stringify(entry));
  } catch {
    
  }
};

const getCachedOrFetch = async (
  key: string,
  fetcher: () => Promise<BannerListResponse>
): Promise<BannerListResponse> => {
  
  const inMemory = memoryCache.get(key);
  if (isCacheValid(inMemory)) {
    return inMemory!.response;
  }

  
  const fromStorage = loadFromStorage(key);
  if (fromStorage) {
    memoryCache.set(key, fromStorage);
    return fromStorage.response;
  }

  
  const response = await fetcher();
  const entry: CacheEntry = {
    timestamp: Date.now(),
    response,
  };
  memoryCache.set(key, entry);
  saveToStorage(key, entry);
  return response;
};

export const getBannersByPosition = async (
  position: string = 'home'
): Promise<BannerListResponse> => {
  const key = getCacheKey(position);
  return getCachedOrFetch(key, async () => {
    const response = await apiClient.get('/banners', {
      params: { position },
    });
    return response.data;
  });
};

export const getActiveBanners = async ():
  Promise<BannerListResponse> => {
  const key = getCacheKey();
  return getCachedOrFetch(key, async () => {
    const response = await apiClient.get('/banners');
    return response.data;
  });
};

export const getAllBanners = async (
  params?: { position?: string; page?: number; limit?: number }
): Promise<BannerListResponse> => {
  const response = await apiClient.get('/banners', { params });
  return response.data;
};

export const getBannerById = async (
  id: number
): Promise<{ success: boolean; data: { banner: Banner } }> => {
  const response = await apiClient.get(`/banners/${id}`);
  return response.data;
};

export const createBanner = async (
  data: {
    title: string;
    description?: string;
    image_url: string;
    link?: string;
    link_url?: string;
    position?: string;
    display_order?: number;
    start_date?: string;
    end_date?: string;
  }
): Promise<{ success: boolean; data: { banner: Banner }; message: string }> => {
  
  const requestData = {
    ...data,
    link: data.link_url || data.link,
  };
  delete requestData.link_url;
  const response = await apiClient.post('/banners', requestData);
  return response.data;
};

export const updateBanner = async (
  id: number,
  data: {
    title?: string;
    description?: string;
    image_url?: string;
    link?: string;
    link_url?: string;
    position?: string;
    display_order?: number;
    is_active?: boolean;
    start_date?: string;
    end_date?: string;
  }
): Promise<{ success: boolean; data: { banner: Banner }; message: string }> => {
  
  const requestData = {
    ...data,
    link: data.link_url || data.link,
  };
  delete requestData.link_url;
  const response = await apiClient.put(`/banners/${id}`, requestData);
  return response.data;
};

export const deleteBanner = async (
  id: number
): Promise<{ success: boolean; message: string }> => {
  const response = await apiClient.delete(`/banners/${id}`);
  return response.data;
};

export const uploadBannerImage = async (
  file: File
): Promise<{ success: boolean; data: { image_url: string; full_url: string }; message: string }> => {
  const formData = new FormData();
  formData.append('image', file);
  
  
  const response = await apiClient.post('/banners/upload', formData);
  return response.data;
};

export interface BannerService {
  getBannersByPosition: typeof getBannersByPosition;
  getActiveBanners: typeof getActiveBanners;
  getAllBanners: typeof getAllBanners;
  getBannerById: typeof getBannerById;
  createBanner: typeof createBanner;
  updateBanner: typeof updateBanner;
  deleteBanner: typeof deleteBanner;
  uploadBannerImage: typeof uploadBannerImage;
}

const bannerService: BannerService = {
  getBannersByPosition,
  getActiveBanners,
  getAllBanners,
  getBannerById,
  createBanner,
  updateBanner,
  deleteBanner,
  uploadBannerImage,
};

export default bannerService as BannerService;
