import { getArticleBySlug } from '@/lib/feature/article/article.external';
import { ArrowLeftIcon, CalendarIcon, ClockIcon } from 'lucide-react';
import Link from 'next/link';
import { notFound } from 'next/navigation';
import { Suspense } from 'react';
import ReactMarkdown from 'react-markdown';
import remarkGfm from 'remark-gfm';

type ArticlePageProps = {
    params: Promise<{ slug: string }>;
};

type ArticleContentProps = {
    params: Promise<{ slug: string }>;
};

function readingTime(text: string): number {
    const words = text.trim().split(/\s+/).length;
    return Math.max(1, Math.ceil(words / 200));
}

function formatDate(date: Date): string {
    return new Intl.DateTimeFormat('en-US', {
        year: 'numeric',
        month: 'long',
        day: 'numeric',
    }).format(date);
}

const ArticleContentSkeleton = () => (
    <article className='w-full'>
        <div className='h-64 w-full animate-pulse bg-muted md:h-96' />

        <div className='container mx-auto max-w-3xl px-4'>
            <div className='-mt-16 relative z-10'>
                <div className='mb-6 h-4 w-24 animate-pulse rounded bg-muted' />

                <header className='mb-10'>
                    <div className='mb-4 space-y-2'>
                        <div className='h-8 w-full animate-pulse rounded bg-muted' />
                        <div className='h-8 w-3/4 animate-pulse rounded bg-muted' />
                    </div>

                    <div className='mb-5 space-y-2'>
                        <div className='h-5 w-full animate-pulse rounded bg-muted' />
                        <div className='h-5 w-2/3 animate-pulse rounded bg-muted' />
                    </div>

                    <div className='flex gap-4'>
                        <div className='h-3 w-28 animate-pulse rounded bg-muted' />
                        <div className='h-3 w-16 animate-pulse rounded bg-muted' />
                    </div>
                </header>

                <hr className='mb-10 border-border' />

                <div className='space-y-3 pb-16'>
                    {[...Array(4)].map((_, i) => (
                        <div key={i} className='space-y-2'>
                            <div className='h-4 w-full animate-pulse rounded bg-muted' />
                            <div className='h-4 w-full animate-pulse rounded bg-muted' />
                            <div className='h-4 w-5/6 animate-pulse rounded bg-muted' />
                        </div>
                    ))}
                </div>
            </div>
        </div>
    </article>
);

const ArticleContent = async ({ params }: ArticleContentProps) => {
    const { slug } = await params;
    const articleResult = await getArticleBySlug(slug);
    if (!articleResult.ok) throw articleResult.error;
    const article = articleResult.value;

    if (!article) notFound();

    const minutes = readingTime(article.content);

    return (
        <article className='w-full'>
            {article.coverImageUrl && (
                <div className='relative h-64 w-full overflow-hidden md:h-96'>
                    {/* eslint-disable-next-line @next/next/no-img-element */}
                    <img
                        src={article.coverImageUrl}
                        alt={article.title}
                        className='h-full w-full object-cover'
                    />
                    <div className='absolute inset-0 bg-linear-to-t from-background via-background/40 to-transparent' />
                </div>
            )}

            <div className='container mx-auto max-w-3xl px-4'>
                <div
                    className={
                        article.coverImageUrl ? '-mt-16 relative z-10' : 'pt-12'
                    }
                >
                    <Link
                        href='/home'
                        className='mb-6 inline-flex items-center gap-1.5 text-sm text-muted-foreground transition-colors hover:text-foreground'
                    >
                        <ArrowLeftIcon className='size-3.5' />
                        All articles
                    </Link>

                    <header className='mb-10'>
                        <h1 className='mb-4 text-3xl font-bold leading-tight tracking-tight md:text-4xl'>
                            {article.title}
                        </h1>

                        <p className='mb-5 text-lg leading-relaxed text-muted-foreground'>
                            {article.description}
                        </p>

                        <div className='flex flex-wrap items-center gap-4 text-xs text-muted-foreground'>
                            <span className='flex items-center gap-1.5'>
                                <CalendarIcon className='size-3.5 shrink-0' />
                                <time
                                    dateTime={article.createdAt.toISOString()}
                                >
                                    {formatDate(article.createdAt)}
                                </time>
                            </span>
                            <span className='flex items-center gap-1.5'>
                                <ClockIcon className='size-3.5 shrink-0' />
                                {minutes} min read
                            </span>
                        </div>
                    </header>

                    <hr className='mb-10 border-border' />

                    <div className='prose prose-neutral dark:prose-invert max-w-none pb-16'>
                        <ReactMarkdown remarkPlugins={[remarkGfm]}>
                            {article.content}
                        </ReactMarkdown>
                    </div>
                </div>
            </div>
        </article>
    );
};

const ArticlePage = ({ params }: ArticlePageProps) => {
    return (
        <Suspense fallback={<ArticleContentSkeleton />}>
            <ArticleContent params={params} />
        </Suspense>
    );
};

export default ArticlePage;
