const API_BASE_URL = import.meta.env.VITE_API_URL || 'http://localhost:3000/api/v1';

// Debug logging
console.log('API_BASE_URL:', API_BASE_URL);
console.log('VITE_API_URL env:', import.meta.env.VITE_API_URL);

// Helper function to get auth headers
function getAuthHeaders(): HeadersInit {
  const token = localStorage.getItem('token');
  const headers: HeadersInit = {
    'Content-Type': 'application/json',
  };
  
  if (token) {
    headers['Authorization'] = `Bearer ${token}`;
  }
  
  return headers;
}

// Enhanced fetch wrapper
async function authFetch(url: string, options: RequestInit = {}): Promise<Response> {
  const headers = getAuthHeaders();
  
  const response = await fetch(url, {
    ...options,
    headers: {
      ...headers,
      ...options.headers,
    },
  });
  
  // Handle 401 unauthorized
  if (response.status === 401) {
    localStorage.removeItem('token');
    localStorage.removeItem('user');
    window.location.href = '/auth';
  }
  
  return response;
}

export interface Article {
  id: string;
  title: string;
  content: string;
  excerpt: string | null;
  slug: string;
  featuredImage: string;
  imagePosition: 'top' | 'left' | 'right' | 'none';
  imageSize: 'small' | 'medium' | 'large';
  videoUrl: string;
  videoPosition: 'top' | 'inline' | 'bottom' | 'none';
  videoCaption: string;
  tags: string[];
  status: 'draft' | 'published' | 'archived';
  views: number;
  strapiId: string | null;
  authorId: string | null;
  categoryId: string | null;
  author?: {
    id: string;
    name: string;
    slug: string;
    bio: string | null;
    avatar: string | null;
  };
  category?: {
    id: string;
    name: string;
    slug: string;
    description: string | null;
  };
  createdAt: string;
  updatedAt: string;
  isHero?: boolean;
  isPinned?: boolean;
  facebookShares?: number;
  twitterShares?: number;
  whatsappShares?: number;
  telegramShares?: number;
  ogTitle?: string;
  ogDescription?: string;
  ogImage?: string;
  twitterTitle?: string;
  twitterDescription?: string;
  twitterImage?: string;
}

export interface ArticlesResponse {
  data: Article[];
  total: number;
  page?: number;
  limit?: number;
}

export interface FindArticlesParams {
  category?: string;
  author?: string;
  tag?: string;
  status?: string;
  search?: string;
  page?: number;
  limit?: number;
}

export interface CreateArticleDto {
  title: string;
  content: string;
  excerpt?: string;
  slug?: string;
  featuredImage?: string;
  tags?: string[];
  status?: 'draft' | 'published' | 'archived';
  strapiId?: string;
  authorId?: string;
  categoryId?: string;
  imagePosition?: 'top' | 'left' | 'right' | 'none';
  imageSize?: 'small' | 'medium' | 'large';
  videoUrl?: string;
  videoPosition?: 'top' | 'inline' | 'bottom' | 'none';
  videoCaption?: string;
}

export interface UpdateArticleDto {
  title?: string;
  content?: string;
  excerpt?: string;
  slug?: string;
  featuredImage?: string;
  tags?: string[];
  status?: 'draft' | 'published' | 'archived';
  strapiId?: string;
  authorId?: string;
  categoryId?: string;
  imagePosition?: 'top' | 'left' | 'right' | 'none';
  imageSize?: 'small' | 'medium' | 'large';
  videoUrl?: string;
  videoPosition?: 'top' | 'inline' | 'bottom' | 'none';
  videoCaption?: string;
  isHero?: boolean;
}

export async function fetchArticles(params: FindArticlesParams = {}): Promise<ArticlesResponse> {
  console.log('fetchArticles called with params:', params, 'API_BASE_URL:', API_BASE_URL);
  const searchParams = new URLSearchParams();

  // Convert parameters to proper types for URLSearchParams
  Object.entries(params).forEach(([key, value]) => {
    if (value !== undefined && value !== null) {
      if (typeof value === 'number') {
        searchParams.append(key, value.toString());
      } else {
        searchParams.append(key, String(value));
      }
    }
  });

  const url = `${API_BASE_URL}/articles?${searchParams}`;
  console.log('Fetching from:', url);

  const response = await authFetch(url);
  console.log('Response status:', response.status, 'ok:', response.ok);

  if (!response.ok) {
    throw new Error('Failed to fetch articles');
  }

  const data = await response.json();
  console.log('Response data:', data);
  return data;
}

export async function fetchArticleBySlug(slug: string): Promise<Article> {
  const response = await authFetch(`${API_BASE_URL}/articles/slug/${slug}`);
  if (!response.ok) {
    throw new Error('Failed to fetch article');
  }
  return response.json();
}

export async function fetchArticleById(id: string): Promise<Article> {
  const response = await authFetch(`${API_BASE_URL}/articles/${id}`);
  if (!response.ok) {
    throw new Error('Failed to fetch article');
  }
  return response.json();
}

export async function createArticle(dto: CreateArticleDto): Promise<Article> {
  const response = await authFetch(`${API_BASE_URL}/articles`, {
    method: 'POST',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to create article');
  }
  return response.json();
}

export async function updateArticle(id: string, dto: UpdateArticleDto): Promise<Article> {
  const response = await authFetch(`${API_BASE_URL}/articles/${id}`, {
    method: 'PUT',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to update article');
  }
  return response.json();
}

export async function deleteArticle(id: string): Promise<void> {
  const response = await authFetch(`${API_BASE_URL}/articles/${id}`, {
    method: 'DELETE',
  });
  if (!response.ok) {
    throw new Error('Failed to delete article');
  }
}

export async function archiveArticle(id: string): Promise<Article> {
  const response = await authFetch(`${API_BASE_URL}/articles/${id}/archive`, {
    method: 'PATCH',
  });
  if (!response.ok) {
    throw new Error('Failed to archive article');
  }
  return response.json();
}

export async function publishArticle(id: string, status: 'draft' | 'published' = 'published'): Promise<Article> {
  const response = await authFetch(`${API_BASE_URL}/articles/${id}/publish?status=${status}`, {
    method: 'PATCH',
  });
  if (!response.ok) {
    throw new Error('Failed to publish article');
  }
  return response.json();
}

// Live Blog Types
export interface LiveBlogUpdate {
  id: string;
  content: string;
  isPinned: boolean;
  authorId: string | null;
  scheduledAt: string | null;
  strapiId: string | null;
  author?: {
    id: string;
    name: string;
    slug: string;
    bio: string | null;
    avatar: string | null;
  };
  createdAt: string;
  updatedAt: string;
}

export interface LiveBlog {
  id: string;
  title: string;
  slug: string;
  description: string | null;
  status: 'draft' | 'live' | 'ended' | 'archived';
  isPinned: boolean;
  strapiId: string | null;
  authorId: string | null;
  categoryId: string | null;
  featuredImage: string;
  imagePosition: 'top' | 'left' | 'right' | 'none';
  imageSize: 'small' | 'medium' | 'large';
  videoUrl: string;
  videoPosition: 'top' | 'inline' | 'bottom' | 'none';
  videoCaption: string;
  viewCount: number;
  author?: {
    id: string;
    name: string;
    slug: string;
    bio: string | null;
    avatar: string | null;
  };
  category?: {
    id: string;
    name: string;
    slug: string;
    description: string | null;
  };
  updates?: LiveBlogUpdate[];
  createdAt: string;
  updatedAt: string;
}

export interface LiveBlogsResponse {
  data: LiveBlog[];
  total: number;
  page?: number;
  limit?: number;
}

export interface LiveBlogUpdatesResponse {
  data: LiveBlogUpdate[];
  total: number;
  page?: number;
  limit?: number;
}

export interface FindLiveBlogsParams {
  category?: string;
  author?: string;
  status?: string;
  search?: string;
  page?: number;
  limit?: number;
}

export interface CreateLiveBlogUpdateDto {
  content: string;
  isPinned?: boolean;
  authorId?: string;
  scheduledAt?: string;
  strapiId?: string;
}

export interface UpdateLiveBlogUpdateDto {
  content?: string;
  isPinned?: boolean;
  authorId?: string;
  scheduledAt?: string;
  strapiId?: string;
}

export interface CreateLiveBlogDto {
  title: string;
  slug?: string;
  description?: string;
  status?: 'draft' | 'live' | 'ended' | 'archived';
  authorId?: string;
  categoryId?: string;
  strapiId?: string;
}

export interface UpdateLiveBlogDto {
  title?: string;
  slug?: string;
  description?: string;
  status?: 'draft' | 'live' | 'ended' | 'archived';
  isPinned?: boolean;
  authorId?: string;
  categoryId?: string;
  strapiId?: string;
}

// Live Blog API Functions
export async function fetchLiveBlogs(params: FindLiveBlogsParams = {}): Promise<LiveBlogsResponse> {
  const searchParams = new URLSearchParams();
  
  Object.entries(params).forEach(([key, value]) => {
    if (value !== undefined && value !== null) {
      if (typeof value === 'number') {
        searchParams.append(key, value.toString());
      } else {
        searchParams.append(key, String(value));
      }
    }
  });

  const response = await authFetch(`${API_BASE_URL}/live-blogs?${searchParams}`);
  if (!response.ok) {
    throw new Error('Failed to fetch live blogs');
  }
  return response.json();
}

export async function fetchLiveBlogBySlug(slugOrId: string): Promise<LiveBlog> {
  const isUuid = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i.test(slugOrId);
  const endpoint = isUuid 
    ? `${API_BASE_URL}/live-blogs/${slugOrId}` 
    : `${API_BASE_URL}/live-blogs/slug/${slugOrId}`;
  const response = await authFetch(endpoint);
  if (!response.ok) {
    throw new Error('Failed to fetch live blog');
  }
  return response.json();
}

export async function fetchLiveBlogById(id: string): Promise<LiveBlog> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${id}`);
  if (!response.ok) {
    throw new Error('Failed to fetch live blog');
  }
  return response.json();
}

export async function fetchLiveBlogUpdates(
  liveBlogId: string,
  page = 1,
  limit = 50
): Promise<LiveBlogUpdatesResponse> {
  const response = await authFetch(
    `${API_BASE_URL}/live-blogs/${liveBlogId}/updates?page=${page}&limit=${limit}`
  );
  if (!response.ok) {
    throw new Error('Failed to fetch live blog updates');
  }
  return response.json();
}

export async function fetchRecentLiveBlogs(): Promise<LiveBlog[]> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/recent`);
  if (!response.ok) {
    throw new Error('Failed to fetch recent live blogs');
  }
  return response.json();
}

export async function fetchHeroArticle(): Promise<Article | null> {
  const response = await authFetch(`${API_BASE_URL}/articles/hero`);
  if (!response.ok) {
    throw new Error('Failed to fetch hero article');
  }
  const article = await response.json();
  return article || null;
}

export async function fetchLatestArticles(limit = 12): Promise<ArticlesResponse> {
  const response = await authFetch(`${API_BASE_URL}/articles?status=published&limit=${limit}`);
  if (!response.ok) {
    throw new Error('Failed to fetch latest articles');
  }
  return response.json();
}

export async function fetchPinnedLiveBlogs(): Promise<LiveBlog[]> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/featured`);
  if (!response.ok) {
    throw new Error('Failed to fetch pinned live blogs');
  }
  return response.json();
}

export async function fetchActiveLiveBlogs(): Promise<LiveBlog[]> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/active`);
  if (!response.ok) {
    throw new Error('Failed to fetch active live blogs');
  }
  return response.json();
}

// Admin functions
export async function createLiveBlogUpdate(
  liveBlogId: string,
  dto: CreateLiveBlogUpdateDto
): Promise<LiveBlogUpdate> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${liveBlogId}/updates`, {
    method: 'POST',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to create live blog update');
  }
  return response.json();
}

export async function updateLiveBlogUpdate(
  liveBlogId: string,
  updateId: string,
  dto: UpdateLiveBlogUpdateDto
): Promise<LiveBlogUpdate> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${liveBlogId}/updates/${updateId}`, {
    method: 'PUT',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to update live blog update');
  }
  return response.json();
}

export async function deleteLiveBlogUpdate(liveBlogId: string, updateId: string): Promise<void> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${liveBlogId}/updates/${updateId}`, {
    method: 'DELETE',
  });
  if (!response.ok) {
    throw new Error('Failed to delete live blog update');
  }
}

export async function createLiveBlog(dto: CreateLiveBlogDto): Promise<LiveBlog> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs`, {
    method: 'POST',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to create live blog');
  }
  return response.json();
}

export async function updateLiveBlog(id: string, dto: UpdateLiveBlogDto): Promise<LiveBlog> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${id}`, {
    method: 'PUT',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to update live blog');
  }
  return response.json();
}

export async function deleteLiveBlog(id: string): Promise<void> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${id}`, {
    method: 'DELETE',
  });
  if (!response.ok) {
    throw new Error('Failed to delete live blog');
  }
}

export async function archiveLiveBlog(id: string): Promise<LiveBlog> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${id}/archive`, {
    method: 'PATCH',
  });
  if (!response.ok) {
    throw new Error('Failed to archive live blog');
  }
  return response.json();
}

export async function publishLiveBlog(id: string, status: 'draft' | 'live' | 'ended' = 'draft'): Promise<LiveBlog> {
  const response = await authFetch(`${API_BASE_URL}/live-blogs/${id}/publish?status=${status}`, {
    method: 'PATCH',
  });
  if (!response.ok) {
    throw new Error('Failed to publish live blog');
  }
  return response.json();
}

// Auth Types
import type { User, LoginDto, RegisterDto, AuthResponse } from '@/types';

// Auth API Functions
export async function login(dto: LoginDto): Promise<AuthResponse> {
  const response = await fetch(`${API_BASE_URL}/auth/login`, {
    method: 'POST',
    headers: {
      'Content-Type': 'application/json',
    },
    body: JSON.stringify(dto),
  });
  
  if (!response.ok) {
    const error = await response.json();
    throw new Error(error.message || 'Login failed');
  }
  
  return response.json();
}

export async function register(dto: RegisterDto): Promise<AuthResponse> {
  const response = await fetch(`${API_BASE_URL}/auth/register`, {
    method: 'POST',
    headers: {
      'Content-Type': 'application/json',
    },
    body: JSON.stringify(dto),
  });
  
  if (!response.ok) {
    const error = await response.json();
    throw new Error(error.message || 'Registration failed');
  }
  
  return response.json();
}

export async function getProfile(): Promise<User> {
  const response = await authFetch(`${API_BASE_URL}/users/profile`, {
    method: 'GET',
  });
  
  if (!response.ok) {
    throw new Error('Failed to fetch profile');
  }
  
  return response.json();
}

export async function logout(): Promise<void> {
  localStorage.removeItem('token');
  localStorage.removeItem('user');
}

// Comment Types
export interface Comment {
  id: string;
  content: string;
  articleId: string | null;
  liveBlogId: string | null;
  parentCommentId: string | null;
  userId: string;
  isVisible: boolean;
  user?: {
    id: string;
    username: string;
    email: string;
    role: string;
  };
  reactions?: {
    likes: number;
    dislikes: number;
  };
  replies?: Comment[];
  createdAt: string;
  updatedAt: string;
}

export interface CreateCommentDto {
  content: string;
  articleId?: string;
  liveBlogId?: string;
  parentCommentId?: string;
}

export interface UpdateCommentDto {
  content?: string;
  isVisible?: boolean;
}

export interface FindCommentsParams {
  articleId?: string;
  liveBlogId?: string;
  parentCommentId?: string;
  parentId?: string;
  page?: number;
  limit?: number;
}

export interface CommentsResponse {
  data: Comment[];
  total: number;
  page?: number;
  limit?: number;
}

export interface ReactionCounts {
  likes: number;
  dislikes: number;
}

export interface CreateReactionDto {
  type: 'like' | 'dislike';
  articleId?: string;
  liveBlogId?: string;
  commentId?: string;
}

// Comment API Functions
// Interface for backend comment response
interface BackendComment {
  id: string;
  content: string;
  articleId: string | null;
  liveBlogId: string | null;
  parentId: string | null;
  userId: string;
  likeCount: number;
  dislikeCount: number;
  isVisible: boolean;
  createdAt: string;
  updatedAt: string;
  user?: {
    id: string;
    username: string;
  };
  replies?: BackendComment[];
}

// Recursive function to map comment and its replies
function mapBackendComment(comment: BackendComment): Comment {
  const mappedComment: Comment = {
    id: comment.id,
    content: comment.content,
    articleId: comment.articleId,
    liveBlogId: comment.liveBlogId,
    parentCommentId: comment.parentId,
    userId: comment.userId,
    isVisible: comment.isVisible,
    reactions: {
      likes: comment.likeCount || 0,
      dislikes: comment.dislikeCount || 0,
    },
    replies: comment.replies?.map(mapBackendComment) || [],
    createdAt: comment.createdAt,
    updatedAt: comment.updatedAt,
  };
  return mappedComment;
}

export async function fetchComments(params: FindCommentsParams = {}): Promise<CommentsResponse> {
  const searchParams = new URLSearchParams();
  
  // Map parentCommentId to parentId for backend compatibility
  const backendParams = { ...params };
  if (backendParams.parentCommentId) {
    backendParams.parentId = backendParams.parentCommentId;
    delete backendParams.parentCommentId;
  }
  
  Object.entries(backendParams).forEach(([key, value]) => {
    if (value !== undefined && value !== null) {
      if (typeof value === 'number') {
        searchParams.append(key, value.toString());
      } else {
        searchParams.append(key, String(value));
      }
    }
  });

  const response = await authFetch(`${API_BASE_URL}/comments?${searchParams}`);
  if (!response.ok) {
    throw new Error('Failed to fetch comments');
  }
  
  const data = await response.json();
  
  const mappedData = (data as BackendComment[]).map(mapBackendComment);
  
  return {
    data: mappedData,
    total: mappedData.length,
  };
}

export async function createComment(dto: CreateCommentDto): Promise<Comment> {
  // Map parentCommentId to parentId for backend compatibility
  const backendDto = {
    content: dto.content,
    articleId: dto.articleId,
    liveBlogId: dto.liveBlogId,
    parentId: dto.parentCommentId,
  };
  
  const response = await authFetch(`${API_BASE_URL}/comments`, {
    method: 'POST',
    body: JSON.stringify(backendDto),
  });
  if (!response.ok) {
    throw new Error('Failed to create comment');
  }
  
  const comment = await response.json() as BackendComment;
  
  // Map backend response to frontend interface
  return mapBackendComment(comment);
}

export async function updateComment(id: string, dto: UpdateCommentDto): Promise<Comment> {
  const response = await authFetch(`${API_BASE_URL}/comments/${id}`, {
    method: 'PUT',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to update comment');
  }
  return response.json();
}

export async function deleteComment(id: string): Promise<void> {
  const response = await authFetch(`${API_BASE_URL}/comments/${id}`, {
    method: 'DELETE',
  });
  if (!response.ok) {
    throw new Error('Failed to delete comment');
  }
}

export async function addReaction(dto: CreateReactionDto): Promise<void> {
  const response = await authFetch(`${API_BASE_URL}/comments/reactions`, {
    method: 'POST',
    body: JSON.stringify(dto),
  });
  if (!response.ok) {
    throw new Error('Failed to add reaction');
  }
}

export async function getReactionCounts(
  articleId?: string,
  liveBlogId?: string,
  commentId?: string
): Promise<ReactionCounts> {
  const searchParams = new URLSearchParams();
  
  if (articleId) searchParams.append('articleId', articleId);
  if (liveBlogId) searchParams.append('liveBlogId', liveBlogId);
  if (commentId) searchParams.append('commentId', commentId);

  const url = `${API_BASE_URL}/comments/reactions/counts${searchParams.toString() ? `?${searchParams}` : ''}`;
  const response = await authFetch(url);
  if (!response.ok) {
    throw new Error('Failed to fetch reaction counts');
  }
  return response.json();
}

export async function getUserReaction(
  articleId?: string,
  liveBlogId?: string,
  commentId?: string
): Promise<{ type: string | null }> {
  const searchParams = new URLSearchParams();
  
  if (articleId) searchParams.append('articleId', articleId);
  if (liveBlogId) searchParams.append('liveBlogId', liveBlogId);
  if (commentId) searchParams.append('commentId', commentId);

  const url = `${API_BASE_URL}/comments/reactions/user${searchParams.toString() ? `?${searchParams}` : ''}`;
  const response = await authFetch(url);
  if (!response.ok) {
    if (response.status === 401) {
      return { type: null };
    }
    throw new Error('Failed to fetch user reaction');
  }
  return response.json();
}
