import { apiRequest } from '../lib/api'
import { getActiveBusinessId } from '../lib/businessContext'
import { extractFirstImageUrl } from '../utils/htmlImages'
import type { Blog, BlogAuthor, BlogDetail, BlogPostType, BlogStatus } from '../types/blog'

export const BLOGS_PER_PAGE = 12

export interface BlogApi {
  id: string
  businessId: string
  title: string
  slug: string
  type: BlogPostType
  abstract: string
  mainTextHtml: string
  status: BlogStatus
  categoryId: string | null
  categoryName: string
  tags: string[]
  titleImageUrl: string | null
  featuredMediaId: string | null
  authorId?: string | null
  author?: BlogAuthor | null
  commentCount: number
  publishedAt: string | null
  createdAt: string
  updatedAt: string
}

export interface BlogsListResponse {
  items: BlogApi[]
  total: number
  page: number
  pageSize: number
}

export interface ListBlogsParams {
  page?: number
  pageSize?: number
  status?: BlogStatus
  type?: BlogPostType
  categoryId?: string
  title?: string
}

function businessPath(suffix = '') {
  const businessId = getActiveBusinessId()
  if (!businessId) {
    throw new Error('No active business selected. Please sign in again.')
  }
  return `/businesses/${businessId}/blogs${suffix}`
}

export interface CreateBlogPayload {
  title: string
  type: BlogPostType
  abstract?: string
  mainTextHtml?: string
  categoryId?: string
  status?: BlogStatus
  featuredMediaId?: string
  tags?: string[]
}

export interface UpdateBlogPayload {
  title?: string
  type?: BlogPostType
  abstract?: string | null
  mainTextHtml?: string | null
  categoryId?: string | null
  status?: BlogStatus
  featuredMediaId?: string | null
  tags?: string[]
}

export function resolveBlogTitleImageUrl(blog: BlogApi): string | null {
  return blog.titleImageUrl?.trim() || extractFirstImageUrl(blog.mainTextHtml) || null
}

export function mapBlogApiToUi(blog: BlogApi): Blog {
  return {
    id: blog.id,
    title: blog.title,
    slug: blog.slug,
    type: blog.type,
    abstract: blog.abstract,
    status: blog.status,
    categoryId: blog.categoryId,
    categoryName: blog.categoryName,
    tags: blog.tags,
    titleImageUrl: resolveBlogTitleImageUrl(blog),
    commentCount: blog.commentCount,
    author: blog.author ?? null,
    publishedAt: blog.publishedAt,
    createdAt: blog.createdAt,
    updatedAt: blog.updatedAt,
  }
}

export function mapBlogDetailFromApi(blog: BlogApi): BlogDetail {
  return {
    ...mapBlogApiToUi(blog),
    mainTextHtml: blog.mainTextHtml,
    author: blog.author ?? null,
  }
}

export function formatBlogAuthor(author: BlogAuthor | null): string {
  if (!author) return 'Unknown author'
  const name = [author.firstName, author.lastName].filter(Boolean).join(' ').trim()
  return name || author.email || 'Unknown author'
}

export function formatBlogDate(
  value: string | null,
  locale: 'en' | 'fa' = 'en',
): string {
  if (!value) return '—'
  const date = new Date(value)
  if (Number.isNaN(date.getTime())) return value
  return date.toLocaleDateString(locale === 'fa' ? 'fa-IR' : 'en-US', {
    year: 'numeric',
    month: 'long',
    day: 'numeric',
  })
}

export function formatBlogCardDate(
  value: string | null,
  locale: 'en' | 'fa' = 'en',
): string {
  if (!value) return locale === 'fa' ? 'منتشر نشده' : 'Not published'
  const date = new Date(value)
  if (Number.isNaN(date.getTime())) return value
  return date.toLocaleDateString(locale === 'fa' ? 'fa-IR' : 'en-US', {
    year: 'numeric',
    month: 'short',
    day: 'numeric',
  })
}

export function isBlogVerified(blog: Pick<Blog, 'status'>): boolean {
  return blog.status === 'published'
}

export async function setBlogVerified(blogId: string, verified: boolean) {
  return updateBlog(blogId, { status: verified ? 'published' : 'draft' })
}

export function mapBlogApiToFormState(blog: BlogApi) {
  return {
    title: blog.title,
    type: blog.type,
    abstract: blog.abstract,
    mainTextHtml: blog.mainTextHtml,
    categoryId: blog.categoryId ?? '',
    tags: blog.tags,
    titleImage: resolveBlogTitleImageUrl(blog),
    featuredMediaId: blog.featuredMediaId,
  }
}

export async function listBlogs(
  page = 1,
  pageSize = BLOGS_PER_PAGE,
  signal?: AbortSignal,
  filters?: Omit<ListBlogsParams, 'page' | 'pageSize'>,
) {
  const q = new URLSearchParams()
  q.set('page', String(page))
  q.set('pageSize', String(pageSize))
  if (filters?.status) q.set('status', filters.status)
  if (filters?.type) q.set('type', filters.type)
  if (filters?.categoryId) q.set('categoryId', filters.categoryId)
  if (filters?.title) q.set('title', filters.title)

  const data = await apiRequest<BlogsListResponse>(`${businessPath()}?${q.toString()}`, {
    auth: true,
    signal,
  })

  return {
    ...data,
    items: data.items.map(mapBlogApiToUi),
  }
}

export async function getBlog(blogId: string, signal?: AbortSignal) {
  const data = await apiRequest<{ blog: BlogApi }>(businessPath(`/${blogId}`), {
    auth: true,
    signal,
  })
  return data.blog
}

export async function getBlogDetail(blogId: string, signal?: AbortSignal) {
  const blog = await getBlog(blogId, signal)
  return mapBlogDetailFromApi(blog)
}

export async function createBlog(payload: CreateBlogPayload) {
  return apiRequest<{ message: string; blog: BlogApi }>(businessPath(), {
    method: 'POST',
    auth: true,
    body: payload,
  })
}

export async function updateBlog(blogId: string, payload: UpdateBlogPayload) {
  return apiRequest<{ message: string; blog: BlogApi }>(businessPath(`/${blogId}`), {
    method: 'PATCH',
    auth: true,
    body: payload,
  })
}

export async function deleteBlog(blogId: string) {
  return apiRequest<{ message: string }>(businessPath(`/${blogId}`), {
    method: 'DELETE',
    auth: true,
  })
}
