import { notFound } from 'next/navigation'
import { getPublishedNote } from '@/app/actions/notes-publishing'
import { Flag, Sparkles } from 'lucide-react'
import { format } from 'date-fns'
import { fr } from 'date-fns/locale'
import { computePublishedSourceHash } from '@/lib/publish/template-render'
import { processNoteHtmlForPublish } from '@/lib/publish/process-note-html'
import { REWRITE_SHARED_CSS, KATEX_PUBLISH_CSS } from '@/lib/publish/shared-css'
import { ReadingProgress } from '@/components/publish/reading-progress'
import { CopyLinkButton } from '@/components/publish/copy-link-button'

export async function generateMetadata({ params }: { params: Promise<{ slug: string }> }) {
  const { slug } = await params
  const note = await getPublishedNote(slug)
  if (!note) return { title: 'Note introuvable — Memento' }
  return {
    title: `${note.title || 'Note publiée'} — Memento`,
    description: note.content?.replace(/<[^>]+>/g, '').slice(0, 160),
  }
}

export const revalidate = 60

function estimateReadingTime(html: string): number {
  const words = html.replace(/<[^>]+>/g, ' ').trim().split(/\s+/).filter(Boolean).length
  return Math.max(1, Math.ceil(words / 200))
}

function formatDate(d: Date | string | null | undefined, pattern = 'd MMMM yyyy') {
  if (!d) return null
  return format(new Date(d), pattern, { locale: fr })
}

/* ─── Shared base CSS (selection, print, typography polish) ─────────────── */
const BASE_RESET = `
  *, *::before, *::after { box-sizing: border-box; margin: 0; padding: 0; }
  html { -webkit-font-smoothing: antialiased; -moz-osx-font-smoothing: grayscale; text-rendering: optimizeLegibility; }
  img { max-width: 100%; height: auto; }
  ::selection { background: color-mix(in srgb, var(--pub-accent, #A47148) 28%, transparent); }
  @media print {
    .pub-nav, .pub-progress, .pub-copy, .pub-report { display: none !important; }
    .pub-root { min-height: auto !important; }
  }
`

const ARTICLE_TYPO = `
  .pub-article img { max-width: 100%; height: auto; }
  .pub-article h2 { scroll-margin-top: 5rem; }
  .pub-article h3 { scroll-margin-top: 5rem; }
  .pub-article p + p { margin-top: 0; }
  .pub-article .pub-body-source > p:first-of-type::first-letter,
  .pub-article .pub-rewrite-body > p:first-of-type::first-letter {
    font-weight: 700;
  }
  .pub-article mark {
    background: color-mix(in srgb, var(--pub-accent, #A47148) 22%, transparent);
    padding: 0.05em 0.2em;
    border-radius: 2px;
  }
  .pub-article hr {
    border: none;
    border-top: 1px solid color-mix(in srgb, var(--pub-accent, #A47148) 25%, transparent);
    margin: 2.5em auto;
    width: 40%;
  }
  .pub-article .pub-gallery {
    display: grid;
    grid-template-columns: repeat(auto-fit, minmax(200px, 1fr));
    gap: 12px;
    margin-top: 2.5em;
  }
  .pub-article .pub-gallery-img {
    width: 100%;
    height: 200px;
    object-fit: cover;
    border-radius: 8px;
    display: block;
  }
  .pub-article .pub-figure { margin: 2.25em 0; text-align: center; }
  .pub-article .pub-figure-img {
    max-width: 100%;
    border-radius: 10px;
    box-shadow: 0 16px 48px rgba(0,0,0,0.1);
  }
  .pub-article .pub-figure-caption {
    margin-top: 0.7em;
    font-size: 0.82em;
    opacity: 0.65;
    font-style: italic;
  }
`

/* ─── MAGAZINE — editorial prestige ─────────────────────────────────────── */
function MagazinePage({ note, bodyHtml, readingTime, slug, isStale }: PageProps) {
  const dateLabel = formatDate(note.publishedAt)
  return (
    <>
      <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.css" />
      <link href="https://fonts.googleapis.com/css2?family=Fraunces:opsz,wght@9..144,500;9..144,700;9..144,900&family=Source+Serif+4:ital,opsz,wght@0,8..60,400;0,8..60,600;1,8..60,400&family=Inter:wght@400;500;600&display=swap" rel="stylesheet" />
      <ReadingProgress accent="#C9A227" />

      <div className="mag-root pub-root" data-pub-root>
        <nav className="mag-nav pub-nav">
          <span className="mag-nav-brand">Memento</span>
          <div className="mag-nav-right">
            <CopyLinkButton
              className="mag-copy pub-copy"
              label="Copier le lien"
              copiedLabel="Copié"
            />
            <span className="mag-badge"><Sparkles size={10} /> Magazine</span>
            <a href={`/p/${slug}/report`} className="mag-report pub-report"><Flag size={12} /> Signaler</a>
          </div>
        </nav>

        <header className="mag-header">
          <div className="mag-header-glow" aria-hidden />
          <div className="mag-header-inner">
            <div className="mag-kicker">
              <span>Article</span>
              {dateLabel && <><span className="mag-dot" />{dateLabel}</>}
              <span className="mag-dot" />
              <span>{readingTime} min de lecture</span>
            </div>
            <h1 className="mag-title">{note.title || 'Sans titre'}</h1>
            {note.user?.name && (
              <div className="mag-author">
                {note.user.image && <img src={note.user.image} alt="" className="mag-avatar" />}
                <div>
                  <span className="mag-author-name">{note.user.name}</span>
                  <span className="mag-author-role">Publié sur Memento</span>
                </div>
              </div>
            )}
          </div>
        </header>

        <div className="mag-content">
          <div dir="auto" className="mag-body pub-article" dangerouslySetInnerHTML={{ __html: bodyHtml }} />
        </div>

        <footer className="mag-footer">
          <div className="mag-footer-inner">
            <div className="mag-footer-brand">Memento</div>
            <p className="mag-footer-tag">Votre mémoire augmentée par l&rsquo;IA</p>
            {isStale && (
              <p className="mag-stale">Le contenu source a évolué depuis la dernière publication.</p>
            )}
          </div>
        </footer>
      </div>

      <style>{`
        ${BASE_RESET}
        ${ARTICLE_TYPO}
        .mag-root {
          --pub-accent: #C9A227;
          min-height: 100vh;
          background: #faf9f6;
          color: #141414;
          font-family: 'Inter', system-ui, sans-serif;
        }

        .mag-nav {
          position: sticky; top: 0; z-index: 30;
          background: rgba(12,12,12,0.92);
          backdrop-filter: blur(16px) saturate(1.2);
          color: #fff;
          display: flex; align-items: center; justify-content: space-between;
          padding: 0 28px; height: 54px;
          border-bottom: 1px solid rgba(255,255,255,0.06);
        }
        .mag-nav-brand {
          font-family: 'Fraunces', Georgia, serif;
          font-size: 18px; font-weight: 900; letter-spacing: 0.02em;
        }
        .mag-nav-right { display: flex; align-items: center; gap: 10px; }
        .mag-badge {
          display: none;
          align-items: center; gap: 5px;
          font-size: 10px; font-weight: 600; letter-spacing: 0.14em;
          text-transform: uppercase; color: #e8c96a;
        }
        @media (min-width: 640px) { .mag-badge { display: flex; } }
        .mag-copy {
          display: inline-flex; align-items: center; gap: 6px;
          font-size: 11px; font-weight: 500; color: rgba(255,255,255,0.65);
          background: rgba(255,255,255,0.06); border: 1px solid rgba(255,255,255,0.1);
          border-radius: 999px; padding: 5px 12px; cursor: pointer;
          font-family: inherit; transition: color .15s, background .15s;
        }
        .mag-copy:hover { color: #fff; background: rgba(255,255,255,0.12); }
        .mag-report {
          display: flex; align-items: center; gap: 5px;
          font-size: 11px; color: rgba(255,255,255,0.4); text-decoration: none;
          transition: color .15s;
        }
        .mag-report:hover { color: #fff; }

        .mag-header {
          position: relative;
          background: #0c0c0c;
          color: #fff;
          padding: 72px 28px 88px;
          text-align: center;
          overflow: hidden;
        }
        .mag-header-glow {
          position: absolute; inset: 0; pointer-events: none;
          background:
            radial-gradient(ellipse 80% 60% at 50% 0%, rgba(201,162,39,0.18), transparent 60%),
            radial-gradient(ellipse 50% 40% at 80% 100%, rgba(164,113,72,0.12), transparent 50%);
        }
        .mag-header-inner { position: relative; max-width: 820px; margin: 0 auto; }
        .mag-kicker {
          display: flex; flex-wrap: wrap; align-items: center; justify-content: center; gap: 8px;
          font-size: 11px; font-weight: 600; letter-spacing: 0.18em;
          text-transform: uppercase; color: rgba(255,255,255,0.5); margin-bottom: 28px;
        }
        .mag-kicker span:first-child { color: #e8c96a; }
        .mag-dot { width: 3px; height: 3px; border-radius: 50%; background: rgba(255,255,255,0.25); }
        .mag-title {
          font-family: 'Fraunces', Georgia, serif;
          font-size: clamp(2.1rem, 6.5vw, 4.25rem);
          font-weight: 900; line-height: 1.05; letter-spacing: -0.03em;
          margin-bottom: 36px;
          text-wrap: balance;
        }
        .mag-author {
          display: inline-flex; align-items: center; gap: 12px;
          text-align: left;
        }
        .mag-avatar {
          width: 44px; height: 44px; border-radius: 50%;
          border: 2px solid rgba(232,201,106,0.45);
          object-fit: cover;
        }
        .mag-author-name { display: block; font-size: 14px; font-weight: 600; color: #fff; }
        .mag-author-role { display: block; font-size: 12px; color: rgba(255,255,255,0.45); margin-top: 2px; }

        .mag-content {
          max-width: 720px; margin: 0 auto;
          padding: 56px 24px 96px;
        }
        @media (min-width: 900px) {
          .mag-content { padding-left: 32px; padding-right: 32px; }
        }

        .mag-body {
          font-family: 'Source Serif 4', Georgia, serif;
          font-size: 19px; line-height: 1.85; color: #1a1a1a;
          font-optical-sizing: auto;
        }
        .mag-body .pub-tpl { all: unset; display: block; }

        .mag-body .pub-magazine-dek {
          font-size: 1.28em; line-height: 1.55; color: #333;
          margin-bottom: 2.25em; padding-bottom: 1.75em;
          border-bottom: 2px solid #0c0c0c;
          font-style: italic;
          text-wrap: pretty;
        }
        .mag-body .pub-pull-quote {
          font-family: 'Fraunces', serif;
          font-size: clamp(1.45em, 3.5vw, 1.9em);
          font-style: italic; font-weight: 700;
          color: #0c0c0c; line-height: 1.3;
          margin: 2.75em 0; padding: 1.4em 0;
          border-top: 3px solid #C9A227;
          border-bottom: 3px solid #C9A227;
          text-align: center; text-wrap: balance;
        }
        .mag-body .pub-pull-quote p { margin: 0; }

        .mag-body .pub-hero {
          margin: -8px -8px 2.75rem;
          border-radius: 4px; overflow: hidden;
          max-height: 520px; aspect-ratio: 16/9; background: #1a1a1a;
          box-shadow: 0 24px 64px rgba(0,0,0,0.12);
        }
        @media (min-width: 900px) {
          .mag-body .pub-hero { margin-left: -48px; margin-right: -48px; border-radius: 6px; }
        }
        .mag-body .pub-hero-img { width: 100%; height: 100%; object-fit: cover; display: block; }

        .mag-body h2 {
          font-family: 'Fraunces', serif; font-size: 1.55em; font-weight: 700;
          margin-top: 2.6em; margin-bottom: 0.55em; letter-spacing: -0.02em; color: #0c0c0c;
        }
        .mag-body h3 { font-size: 1.18em; font-weight: 600; margin-top: 2em; margin-bottom: 0.45em; }
        .mag-body p { margin: 1.05em 0; text-wrap: pretty; }
        .mag-body .pub-body-source > p:first-of-type::first-letter {
          font-family: 'Fraunces', serif;
          float: left; font-size: 3.4em; line-height: 0.85;
          padding-right: 0.1em; padding-top: 0.08em;
          font-weight: 900; color: #0c0c0c;
        }
        .mag-body blockquote {
          border-left: 3px solid #C9A227; padding-left: 1.25em;
          margin: 1.75em 0; color: #444; font-style: italic;
        }
        .mag-body ul, .mag-body ol { padding-left: 1.4em; margin: 1.1em 0; }
        .mag-body li { margin: 0.4em 0; }
        .mag-body pre {
          background: #121212; color: #e8e3d5; padding: 22px;
          border-radius: 10px; overflow-x: auto; font-size: 13.5px; margin: 1.75em 0;
        }
        .mag-body code {
          font-family: 'SF Mono', Menlo, monospace; font-size: 0.88em;
          background: #f0ebe3; padding: 1px 6px; border-radius: 4px;
        }
        .mag-body pre code { background: none; padding: 0; color: inherit; }
        .mag-body table { border-collapse: collapse; width: 100%; margin: 1.75em 0; }
        .mag-body th {
          background: #0c0c0c; color: #fff; padding: 11px 14px;
          text-align: left; font-size: 12px; letter-spacing: 0.06em; text-transform: uppercase;
        }
        .mag-body td { border-bottom: 1px solid #e8e4dc; padding: 11px 14px; }
        .mag-body a {
          color: #9a7212; text-decoration: underline;
          text-underline-offset: 3px; text-decoration-thickness: 1px;
        }
        .mag-body a:hover { color: #6b4f0c; }
        .mag-body .pub-callout { border-radius: 8px; padding: 14px 18px; margin: 1.5em 0; }
        ${KATEX_PUBLISH_CSS}

        .mag-footer {
          background: #0c0c0c; color: rgba(255,255,255,0.4);
          padding: 48px 28px 56px; text-align: center;
        }
        .mag-footer-inner { max-width: 480px; margin: 0 auto; }
        .mag-footer-brand {
          font-family: 'Fraunces', serif; font-size: 20px; font-weight: 900;
          color: #e8c96a; margin-bottom: 8px;
        }
        .mag-footer-tag { font-size: 13px; line-height: 1.5; }
        .mag-stale { margin-top: 14px; font-size: 11px; color: rgba(255,255,255,0.28); }

        .mag-body {
          --pub-accent: #C9A227;
          --pub-summary-color: #333;
          --pub-exercise-border: #e0d4c3;
          --pub-exercise-header-bg: #faf6ee;
          --pub-solution-bg: #faf6ee;
          --pub-definition-border: #e0d4c3;
          --pub-definition-bg: #fafaf8;
          --pub-toggle-border: #e5e5e5;
          --pub-toggle-header-bg: #f7f7f5;
          --pub-highlight-bg: #faf6ee;
          --pub-checklist-bg: rgba(0,0,0,0.03);
        }
        .mag-body .pub-rewrite-body .pub-code { background: #0d0d0d; }
        .mag-body .pub-rewrite-body .pub-code code { background: #0d0d0d; color: #e8e3d5; }
        .mag-body .pub-rewrite-body .pub-definition-term { background: #e8c96a; color: #1a1a1a; }
        .mag-body .pub-rewrite-body .pub-step-num { background: #9a7212; color: #fff; }
        .mag-body .pub-rewrite-body .pub-exercise-num { color: #9a7212; }
        .mag-body .pub-rewrite-body .pub-solution > summary { color: #9a7212; }
        .mag-body .pub-rewrite-body .pub-checklist li::before { color: #9a7212; }
        ${REWRITE_SHARED_CSS}
      `}</style>
    </>
  )
}

/* ─── BRIEF — crisp knowledge card ──────────────────────────────────────── */
function BriefPage({ note, bodyHtml, readingTime, slug, isStale }: PageProps) {
  const dateLabel = formatDate(note.publishedAt, 'd MMM yyyy')
  return (
    <>
      <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.css" />
      <link href="https://fonts.googleapis.com/css2?family=DM+Sans:ital,opsz,wght@0,9..40,400;0,9..40,500;0,9..40,600;0,9..40,700;1,9..40,400&family=DM+Mono:wght@400;500&display=swap" rel="stylesheet" />
      <ReadingProgress accent="#3B82F6" />

      <div className="br-root pub-root" data-pub-root>
        <nav className="br-nav pub-nav">
          <span className="br-brand">Memento</span>
          <div className="br-nav-right">
            <CopyLinkButton className="br-copy pub-copy" label="Copier le lien" copiedLabel="Copié" />
            <span className="br-badge"><Sparkles size={9} /> Fiche expert</span>
            <a href={`/p/${slug}/report`} className="br-report pub-report" aria-label="Signaler"><Flag size={12} /></a>
          </div>
        </nav>

        <header className="br-header">
          <div className="br-header-mesh" aria-hidden />
          <div className="br-header-inner">
            <div className="br-meta">
              <span className="br-tag">Fiche expert</span>
              <span className="br-meta-item">{readingTime} min</span>
              {dateLabel && <span className="br-meta-item">{dateLabel}</span>}
            </div>
            <h1 className="br-title">{note.title || 'Sans titre'}</h1>
            {note.user?.name && (
              <div className="br-author">
                {note.user.image && <img src={note.user.image} alt="" className="br-avatar" />}
                <span>{note.user.name}</span>
              </div>
            )}
          </div>
        </header>

        <div className="br-layout">
          <div dir="auto" className="br-body pub-article" dangerouslySetInnerHTML={{ __html: bodyHtml }} />
        </div>

        <footer className="br-footer">
          <strong>Memento</strong>
          <span> — Fiche structurée pour aller à l&rsquo;essentiel</span>
          {isStale && <p className="br-stale">Le contenu source a évolué depuis la publication.</p>}
        </footer>
      </div>

      <style>{`
        ${BASE_RESET}
        ${ARTICLE_TYPO}
        .br-root {
          --pub-accent: #3B82F6;
          min-height: 100vh;
          background: linear-gradient(180deg, #eef2f8 0%, #f6f8fb 40%, #f6f8fb 100%);
          color: #0f172a;
          font-family: 'DM Sans', system-ui, sans-serif;
        }

        .br-nav {
          position: sticky; top: 0; z-index: 30;
          background: rgba(255,255,255,0.85);
          backdrop-filter: blur(16px) saturate(1.2);
          border-bottom: 1px solid rgba(15,23,42,0.06);
          display: flex; align-items: center; justify-content: space-between;
          padding: 0 24px; height: 52px;
        }
        .br-brand { font-weight: 700; font-size: 15px; letter-spacing: -0.02em; color: #0f172a; }
        .br-nav-right { display: flex; align-items: center; gap: 10px; }
        .br-badge {
          display: none; align-items: center; gap: 4px;
          font-size: 11px; font-weight: 600; color: #2563eb;
          background: #eff6ff; padding: 4px 10px; border-radius: 999px;
        }
        @media (min-width: 640px) { .br-badge { display: flex; } }
        .br-copy {
          display: inline-flex; align-items: center; gap: 6px;
          font-size: 11px; font-weight: 500; color: #475569;
          background: #f1f5f9; border: 1px solid #e2e8f0;
          border-radius: 999px; padding: 5px 12px; cursor: pointer;
          font-family: inherit; transition: background .15s;
        }
        .br-copy:hover { background: #e2e8f0; }
        .br-report { color: #94a3b8; display: flex; padding: 6px; border-radius: 8px; transition: color .15s, background .15s; }
        .br-report:hover { color: #475569; background: #f1f5f9; }

        .br-header {
          position: relative;
          background: linear-gradient(145deg, #0b1f3a 0%, #123056 45%, #1e3a5f 100%);
          color: #fff; padding: 52px 24px 64px; overflow: hidden;
        }
        .br-header-mesh {
          position: absolute; inset: 0; pointer-events: none; opacity: 0.45;
          background-image:
            radial-gradient(circle at 20% 20%, rgba(59,130,246,0.35), transparent 40%),
            radial-gradient(circle at 85% 70%, rgba(14,165,233,0.2), transparent 35%),
            linear-gradient(rgba(255,255,255,0.03) 1px, transparent 1px),
            linear-gradient(90deg, rgba(255,255,255,0.03) 1px, transparent 1px);
          background-size: auto, auto, 32px 32px, 32px 32px;
        }
        .br-header-inner { position: relative; max-width: 760px; margin: 0 auto; }
        .br-meta { display: flex; flex-wrap: wrap; align-items: center; gap: 10px; margin-bottom: 18px; }
        .br-tag {
          background: #3B82F6; color: #fff;
          font-size: 10px; font-weight: 700; letter-spacing: 0.12em;
          text-transform: uppercase; padding: 4px 10px; border-radius: 6px;
        }
        .br-meta-item {
          font-size: 12px; font-weight: 500;
          color: rgba(255,255,255,0.55); letter-spacing: 0.04em;
        }
        .br-title {
          font-size: clamp(1.6rem, 4.2vw, 2.65rem);
          font-weight: 700; line-height: 1.15; letter-spacing: -0.03em;
          margin-bottom: 22px; text-wrap: balance;
        }
        .br-author {
          display: flex; align-items: center; gap: 10px;
          font-size: 13px; color: rgba(255,255,255,0.55);
        }
        .br-avatar {
          width: 30px; height: 30px; border-radius: 50%;
          border: 2px solid rgba(255,255,255,0.2); object-fit: cover;
        }

        .br-layout {
          max-width: 760px; margin: -28px auto 0;
          padding: 0 20px 80px; position: relative; z-index: 1;
        }

        .br-body { font-size: 16.5px; line-height: 1.75; color: #1e293b; }
        .br-body .pub-tpl { all: unset; display: block; }

        .br-body .pub-brief-lead {
          background: #fff; border-radius: 16px;
          border: 1px solid rgba(15,23,42,0.06);
          border-left: 4px solid #3B82F6;
          padding: 22px 26px; margin-bottom: 1.25em;
          box-shadow: 0 12px 40px rgba(15,23,42,0.06);
        }
        .br-body .pub-brief-lead p {
          margin: 0; font-size: 1.06em; line-height: 1.7;
          color: #0f172a; font-weight: 500;
        }

        .br-body .pub-key-points {
          background: #fff; border-radius: 16px; padding: 22px 26px;
          margin-bottom: 1.25em;
          border: 1px solid rgba(15,23,42,0.06);
          box-shadow: 0 12px 40px rgba(15,23,42,0.05);
        }
        .br-body .pub-key-points-label {
          font-size: 10px; text-transform: uppercase; letter-spacing: 0.18em;
          font-weight: 700; color: #2563eb; margin-bottom: 14px; display: block;
        }
        .br-body .pub-key-points ul { list-style: none; padding: 0; margin: 0; counter-reset: kp; }
        .br-body .pub-key-points li {
          counter-increment: kp;
          padding: 12px 14px 12px 48px; border-radius: 12px;
          background: #f8fafc; margin-bottom: 8px; position: relative;
          font-size: 0.95em; font-weight: 500; border: 1px solid #eef2f7;
        }
        .br-body .pub-key-points li::before {
          content: counter(kp);
          position: absolute; left: 12px; top: 50%; transform: translateY(-50%);
          width: 26px; height: 26px; border-radius: 8px;
          background: #eff6ff; color: #2563eb;
          font-weight: 700; font-size: 12px;
          display: flex; align-items: center; justify-content: center;
        }

        .br-body .pub-body-source,
        .br-body .pub-rewrite-body {
          background: #fff; border-radius: 16px; padding: 32px 28px;
          border: 1px solid rgba(15,23,42,0.06);
          box-shadow: 0 12px 40px rgba(15,23,42,0.05);
        }
        @media (min-width: 640px) {
          .br-body .pub-body-source,
          .br-body .pub-rewrite-body { padding: 36px 40px; }
        }

        .br-body .pub-hero {
          margin: 0 0 1.25rem; border-radius: 16px; overflow: hidden;
          max-height: 380px; aspect-ratio: 16/9; background: #dbe3ef;
          box-shadow: 0 16px 48px rgba(15,23,42,0.1);
        }
        .br-body .pub-hero-img { width: 100%; height: 100%; object-fit: cover; display: block; }

        .br-body h2 {
          font-size: 1.22em; font-weight: 700; margin-top: 1.9em; margin-bottom: 0.55em;
          color: #0f172a; letter-spacing: -0.02em;
          padding-bottom: 0.4em; border-bottom: 1px solid #e2e8f0;
        }
        .br-body h3 { font-size: 1.06em; font-weight: 600; margin-top: 1.4em; margin-bottom: 0.4em; color: #1e3a5f; }
        .br-body p { margin: 0.85em 0; text-wrap: pretty; }
        .br-body blockquote {
          border-left: 3px solid #3B82F6; padding: 4px 0 4px 1em;
          margin: 1.2em 0; color: #334155; font-style: italic;
        }
        .br-body ul, .br-body ol { padding-left: 1.3em; margin: 1em 0; }
        .br-body li { margin: 0.35em 0; }
        .br-body pre {
          background: #0f172a; color: #e2e8f0; padding: 20px;
          border-radius: 12px; overflow-x: auto; font-size: 13px;
          margin: 1.4em 0; font-family: 'DM Mono', monospace;
        }
        .br-body code {
          font-family: 'DM Mono', monospace; font-size: 0.87em;
          background: #eef2f7; padding: 1px 6px; border-radius: 4px; color: #1e3a5f;
        }
        .br-body pre code { background: none; color: inherit; padding: 0; }
        .br-body table { border-collapse: collapse; width: 100%; margin: 1.4em 0; border-radius: 10px; overflow: hidden; }
        .br-body th { background: #0f172a; color: #fff; padding: 10px 14px; text-align: left; font-size: 12px; }
        .br-body td { border-bottom: 1px solid #e2e8f0; padding: 10px 14px; background: #fff; }
        .br-body a { color: #2563eb; text-decoration: underline; text-underline-offset: 3px; }
        .br-body .pub-callout { border-radius: 10px; padding: 12px 16px; margin: 1.2em 0; }
        ${KATEX_PUBLISH_CSS}

        .br-footer {
          background: #0f172a; color: rgba(255,255,255,0.4);
          padding: 36px 24px; text-align: center; font-size: 13px;
        }
        .br-footer strong { color: #fff; font-weight: 600; }
        .br-stale { font-size: 11px; color: rgba(255,255,255,0.28); margin-top: 8px; }

        .br-body {
          --pub-accent: #2563eb;
          --pub-summary-color: #334155;
          --pub-exercise-border: #bfdbfe;
          --pub-exercise-header-bg: #eff6ff;
          --pub-solution-bg: #f0f7ff;
          --pub-definition-border: #bfdbfe;
          --pub-definition-bg: #f8faff;
          --pub-toggle-border: #e2e8f0;
          --pub-toggle-header-bg: #f8fafc;
          --pub-highlight-bg: #eff6ff;
          --pub-checklist-bg: #f4f6f9;
        }
        .br-body .pub-rewrite-body .pub-code { background: #0f172a; }
        .br-body .pub-rewrite-body .pub-code code { background: #0f172a; color: #e2e8f0; }
        ${REWRITE_SHARED_CSS}
      `}</style>
    </>
  )
}

/* ─── ESSAY — literary calm ─────────────────────────────────────────────── */
function EssayPage({ note, bodyHtml, readingTime, slug, isStale }: PageProps) {
  const dateLabel = formatDate(note.publishedAt)
  return (
    <>
      <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.css" />
      <link href="https://fonts.googleapis.com/css2?family=Literata:ital,opsz,wght@0,7..72,400;0,7..72,600;0,7..72,700;1,7..72,400;1,7..72,600&family=Inter:wght@400;500;600&display=swap" rel="stylesheet" />
      <ReadingProgress accent="#7A5C2E" />

      <div className="es-root pub-root" data-pub-root>
        <nav className="es-nav pub-nav">
          <span className="es-brand">Memento</span>
          <div className="es-nav-right">
            <CopyLinkButton className="es-copy pub-copy" label="Copier le lien" copiedLabel="Copié" />
            <span className="es-badge"><Sparkles size={10} /> Essai</span>
            <a href={`/p/${slug}/report`} className="es-report pub-report" aria-label="Signaler"><Flag size={12} /></a>
          </div>
        </nav>

        <main className="es-main">
          <div className="es-ornament" aria-hidden>
            <span className="es-ornament-line" />
            <span className="es-ornament-diamond" />
            <span className="es-ornament-line" />
          </div>

          <header className="es-header">
            {dateLabel && <time className="es-date">{dateLabel}</time>}
            <h1 className="es-title">{note.title || 'Sans titre'}</h1>
            <div className="es-meta-row">
              {note.user?.name && (
                <div className="es-author">
                  {note.user.image && <img src={note.user.image} alt="" className="es-avatar" />}
                  <span className="es-author-name">{note.user.name}</span>
                </div>
              )}
              <span className="es-reading-time">{readingTime} min de lecture</span>
            </div>
          </header>

          <div dir="auto" className="es-body pub-article" dangerouslySetInnerHTML={{ __html: bodyHtml }} />

          <footer className="es-footer">
            <div className="es-ornament" aria-hidden>
              <span className="es-ornament-line" />
              <span className="es-ornament-diamond" />
              <span className="es-ornament-line" />
            </div>
            <p>Publié sur <strong>Memento</strong></p>
            {isStale && <p className="es-stale">Le contenu source a évolué depuis la publication.</p>}
          </footer>
        </main>
      </div>

      <style>{`
        ${BASE_RESET}
        ${ARTICLE_TYPO}
        .es-root {
          --pub-accent: #7A5C2E;
          min-height: 100vh;
          background:
            radial-gradient(ellipse 100% 60% at 50% 0%, #f7f1e6 0%, transparent 55%),
            #fbf8f2;
          color: #2c2416;
          font-family: 'Inter', system-ui, sans-serif;
        }

        .es-nav {
          position: sticky; top: 0; z-index: 30;
          background: rgba(251,248,242,0.88);
          backdrop-filter: blur(14px);
          border-bottom: 1px solid rgba(92,74,42,0.1);
          display: flex; align-items: center; justify-content: space-between;
          padding: 0 28px; height: 52px;
        }
        .es-brand {
          font-family: 'Literata', Georgia, serif;
          font-size: 16px; font-style: italic; color: #5c4a2a; font-weight: 600;
        }
        .es-nav-right { display: flex; align-items: center; gap: 12px; }
        .es-badge {
          display: none; align-items: center; gap: 4px;
          font-size: 11px; font-weight: 500; color: #8b6c3a;
        }
        @media (min-width: 640px) { .es-badge { display: flex; } }
        .es-copy {
          display: inline-flex; align-items: center; gap: 6px;
          font-size: 11px; font-weight: 500; color: #6b5337;
          background: transparent; border: 1px solid #d8cebc;
          border-radius: 999px; padding: 5px 12px; cursor: pointer;
          font-family: inherit; transition: background .15s;
        }
        .es-copy:hover { background: rgba(122,92,46,0.06); }
        .es-report { color: #b5a48a; display: flex; transition: color .15s; }
        .es-report:hover { color: #5c4a2a; }

        .es-main { max-width: 680px; margin: 0 auto; padding: 40px 28px 100px; }

        .es-ornament {
          display: flex; align-items: center; justify-content: center; gap: 12px;
          margin: 28px 0 8px;
        }
        .es-ornament-line {
          width: 48px; height: 1px;
          background: linear-gradient(90deg, transparent, #c8b99a, transparent);
        }
        .es-ornament-diamond {
          width: 7px; height: 7px; background: #7A5C2E;
          transform: rotate(45deg); opacity: 0.7;
        }

        .es-header { text-align: center; padding: 28px 0 8px; }
        .es-date {
          display: block; font-size: 11px; font-weight: 600;
          letter-spacing: 0.2em; text-transform: uppercase;
          color: #a08b5c; margin-bottom: 22px;
        }
        .es-title {
          font-family: 'Literata', Georgia, serif;
          font-size: clamp(1.85rem, 5.2vw, 3.1rem);
          font-weight: 600; font-style: italic; line-height: 1.18;
          letter-spacing: -0.02em; color: #1a140c;
          margin-bottom: 28px; text-wrap: balance;
        }
        .es-meta-row {
          display: flex; flex-wrap: wrap; align-items: center;
          justify-content: center; gap: 16px;
          padding-top: 22px; border-top: 1px solid #e2d9ca;
        }
        .es-author { display: flex; align-items: center; gap: 10px; }
        .es-avatar {
          width: 36px; height: 36px; border-radius: 50%;
          border: 1.5px solid #d8cebc; object-fit: cover;
        }
        .es-author-name { font-size: 13px; font-weight: 600; color: #3d2f14; }
        .es-reading-time { font-size: 12px; color: #a08b5c; }

        .es-body {
          margin-top: 48px;
          font-family: 'Literata', Georgia, serif;
          font-size: 19.5px; line-height: 1.9; color: #2c2416;
          font-optical-sizing: auto;
        }
        .es-body .pub-tpl { all: unset; display: block; }

        .es-body .pub-epigraph {
          position: relative; text-align: center;
          font-size: 1.12em; font-style: italic; color: #6b5337;
          margin: 0 0 2.75em; padding: 1.6em 1.5em 1.2em;
          border-top: 1px solid #d8cebc; border-bottom: 1px solid #d8cebc;
        }
        .es-body .pub-epigraph::before {
          content: '“';
          position: absolute; top: -0.25em; left: 50%; transform: translateX(-50%);
          font-size: 3.5em; color: #d8cebc; line-height: 1;
          font-family: 'Literata', Georgia, serif; pointer-events: none;
        }

        .es-body .pub-essay-summary {
          font-size: 1.12em; line-height: 1.75; color: #4a3726;
          margin-bottom: 2.25em; font-style: italic;
          padding-left: 1.25em; border-left: 2px solid #c8b99a;
        }

        .es-body .pub-body-source > p:first-of-type::first-letter {
          font-family: 'Literata', Georgia, serif;
          float: left; font-size: 3.6em; line-height: 0.82;
          padding-right: 0.08em; padding-top: 0.06em;
          font-weight: 700; color: #1a140c;
        }
        .es-body .pub-body-source p { text-indent: 1.5em; margin: 0 0 0.15em; }
        .es-body .pub-body-source p:first-of-type { text-indent: 0; }
        .es-body .pub-rewrite-body p { margin: 0.9em 0; }

        .es-body .pub-hero {
          margin: 0 -12px 2.75em; overflow: hidden;
          max-height: 440px; aspect-ratio: 16/9; background: #e8e0d0;
          border-radius: 2px;
        }
        @media (min-width: 720px) {
          .es-body .pub-hero { margin-left: -40px; margin-right: -40px; }
        }
        .es-body .pub-hero-img {
          width: 100%; height: 100%; object-fit: cover; display: block;
          filter: sepia(8%) contrast(1.02);
        }

        .es-body h2 {
          font-family: 'Literata', serif; font-size: 1.4em; font-style: italic;
          font-weight: 600; margin-top: 2.4em; margin-bottom: 0.65em; color: #1a140c;
        }
        .es-body h3 {
          font-family: 'Literata', serif; font-size: 1.15em;
          font-weight: 600; margin-top: 1.9em; margin-bottom: 0.45em;
        }
        .es-body p { text-wrap: pretty; }
        .es-body blockquote {
          border: none; margin: 2.25em 0; padding: 0 1.5em;
          font-size: 1.12em; color: #5c4a2a; font-style: italic;
          text-align: center;
        }
        .es-body ul, .es-body ol { padding-left: 1.35em; margin: 1em 0; }
        .es-body li { margin: 0.45em 0; }
        .es-body pre {
          background: #f2ede4; padding: 20px; border-radius: 6px;
          overflow-x: auto; font-family: 'SF Mono', Menlo, monospace;
          font-size: 13px; margin: 1.5em 0;
        }
        .es-body code {
          font-family: 'SF Mono', Menlo, monospace; font-size: 0.85em;
          background: #ede7da; padding: 1px 5px; border-radius: 3px;
        }
        .es-body pre code { background: none; padding: 0; }
        .es-body table { border-collapse: collapse; width: 100%; margin: 1.5em 0; }
        .es-body th {
          border-bottom: 2px solid #5c4a2a; padding: 8px 12px;
          text-align: left; font-size: 13px; color: #5c4a2a;
        }
        .es-body td { border-bottom: 1px solid #e8e0d0; padding: 8px 12px; }
        .es-body a {
          color: #7a5c2e; text-decoration: underline;
          text-decoration-style: dotted; text-underline-offset: 3px;
        }
        .es-body .pub-figure-img { filter: sepia(5%); border-radius: 2px; }
        .es-body .pub-callout { border-radius: 4px; padding: 12px 16px; margin: 1.5em 0; }
        ${KATEX_PUBLISH_CSS}

        .es-footer {
          text-align: center; padding: 48px 0 0;
          font-size: 13px; color: #a08b5c;
        }
        .es-footer strong { color: #5c4a2a; }
        .es-stale { font-size: 11px; color: #c4b49a; margin-top: 8px; }

        .es-body {
          --pub-accent: #7a5c2e;
          --pub-summary-color: #5c4a2a;
          --pub-exercise-border: #d8cebc;
          --pub-exercise-header-bg: #f5f0e8;
          --pub-solution-bg: rgba(122,92,46,0.05);
          --pub-definition-border: #d8cebc;
          --pub-definition-bg: #fdfbf7;
          --pub-toggle-border: #e2d9ca;
          --pub-toggle-header-bg: #f7f3ec;
          --pub-highlight-bg: #fdf6eb;
          --pub-checklist-bg: rgba(0,0,0,0.025);
        }
        .es-body .pub-rewrite-body .pub-code { background: #2c2416; }
        .es-body .pub-rewrite-body .pub-code code { background: #2c2416; color: #f0e8da; }
        ${REWRITE_SHARED_CSS}
      `}</style>
    </>
  )
}

/* ─── SIMPLE — clean Substack-grade default ─────────────────────────────── */
function SimplePage({ note, bodyHtml, readingTime, slug, isStale }: PageProps) {
  const dateLabel = formatDate(note.publishedAt, 'd MMM yyyy')
  return (
    <>
      <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/katex@0.16.9/dist/katex.min.css" />
      <link href="https://fonts.googleapis.com/css2?family=Source+Serif+4:ital,opsz,wght@0,8..60,400;0,8..60,600;0,8..60,700;1,8..60,400&family=Inter:wght@400;500;600&display=swap" rel="stylesheet" />
      <ReadingProgress accent="#A47148" />

      <div className="sp-root pub-root" data-pub-root>
        <nav className="sp-nav pub-nav">
          <span className="sp-brand">Memento</span>
          <div className="sp-nav-right">
            <CopyLinkButton className="sp-copy pub-copy" label="Copier le lien" copiedLabel="Copié" />
            <a href={`/p/${slug}/report`} className="sp-report pub-report">
              <Flag size={12} /> Signaler
            </a>
          </div>
        </nav>

        <article className="sp-article">
          <header className="sp-header">
            <div className="sp-kicker">
              {dateLabel && <span>{dateLabel}</span>}
              {dateLabel && <span className="sp-dot" />}
              <span>{readingTime} min de lecture</span>
            </div>
            <h1 className="sp-title">{note.title || 'Sans titre'}</h1>
            {note.user?.name && (
              <div className="sp-author">
                {note.user.image && <img src={note.user.image} alt="" className="sp-avatar" />}
                <span>par <strong>{note.user.name}</strong></span>
              </div>
            )}
          </header>

          <div className="sp-rule" />

          <div dir="auto" className="sp-body pub-article" dangerouslySetInnerHTML={{ __html: bodyHtml }} />
        </article>

        <footer className="sp-footer">
          <span className="sp-footer-brand">Memento</span>
          <span> — Votre mémoire augmentée par l&rsquo;IA</span>
          {isStale && (
            <p className="sp-stale">Le contenu source a évolué depuis la publication.</p>
          )}
        </footer>
      </div>

      <style>{`
        ${BASE_RESET}
        ${ARTICLE_TYPO}
        .sp-root {
          --pub-accent: #A47148;
          min-height: 100vh;
          background: #faf9f5;
          color: #1a1a1a;
          font-family: 'Inter', system-ui, sans-serif;
        }

        .sp-nav {
          position: sticky; top: 0; z-index: 30;
          background: rgba(250,249,245,0.9);
          backdrop-filter: blur(14px);
          border-bottom: 1px solid rgba(0,0,0,0.06);
          display: flex; align-items: center; justify-content: space-between;
          padding: 0 24px; height: 52px;
        }
        .sp-brand {
          font-family: 'Source Serif 4', Georgia, serif;
          font-weight: 700; font-size: 16px; color: #1a1a1a;
        }
        .sp-nav-right { display: flex; align-items: center; gap: 10px; }
        .sp-copy {
          display: inline-flex; align-items: center; gap: 6px;
          font-size: 11px; font-weight: 500; color: #555;
          background: #fff; border: 1px solid rgba(0,0,0,0.08);
          border-radius: 999px; padding: 5px 12px; cursor: pointer;
          font-family: inherit; box-shadow: 0 1px 2px rgba(0,0,0,0.04);
          transition: border-color .15s, color .15s;
        }
        .sp-copy:hover { border-color: #A47148; color: #A47148; }
        .sp-report {
          display: flex; align-items: center; gap: 5px;
          font-size: 12px; color: #888; text-decoration: none;
          padding: 5px 10px; border-radius: 8px;
          border: 1px solid rgba(0,0,0,0.08); transition: color .15s, border-color .15s;
        }
        .sp-report:hover { color: #333; border-color: rgba(0,0,0,0.15); }

        .sp-article {
          max-width: 680px; margin: 0 auto;
          padding: 48px 24px 72px;
        }
        .sp-header { margin-bottom: 8px; }
        .sp-kicker {
          display: flex; flex-wrap: wrap; align-items: center; gap: 8px;
          font-size: 12px; font-weight: 500; color: #888; margin-bottom: 16px;
          letter-spacing: 0.02em;
        }
        .sp-dot { width: 3px; height: 3px; border-radius: 50%; background: #ccc; }
        .sp-title {
          font-family: 'Source Serif 4', Georgia, serif;
          font-size: clamp(1.75rem, 4.5vw, 2.5rem);
          font-weight: 700; line-height: 1.18; letter-spacing: -0.025em;
          margin: 0 0 20px; text-wrap: balance; color: #111;
        }
        .sp-author {
          display: flex; align-items: center; gap: 10px;
          font-size: 14px; color: #666;
        }
        .sp-author strong { color: #333; font-weight: 600; }
        .sp-avatar {
          width: 32px; height: 32px; border-radius: 50%;
          object-fit: cover; border: 1px solid rgba(0,0,0,0.08);
        }
        .sp-rule {
          height: 1px; background: linear-gradient(90deg, transparent, rgba(0,0,0,0.1), transparent);
          margin: 32px 0 36px;
        }

        .sp-body {
          font-family: 'Source Serif 4', Georgia, serif;
          font-size: 18px; line-height: 1.85; color: #1f1f1f;
          font-optical-sizing: auto;
        }
        .sp-body h2 {
          font-size: 1.4em; font-weight: 700; margin-top: 2em; margin-bottom: 0.55em;
          letter-spacing: -0.02em; color: #111;
        }
        .sp-body h3 { font-size: 1.15em; font-weight: 600; margin-top: 1.7em; margin-bottom: 0.45em; }
        .sp-body p { margin: 1em 0; text-wrap: pretty; }
        .sp-body .pub-body-source > p:first-of-type::first-letter {
          font-weight: 700; color: #A47148;
        }
        .sp-body ul, .sp-body ol { padding-left: 1.4em; margin: 1em 0; }
        .sp-body li { margin: 0.4em 0; }
        .sp-body blockquote {
          border-left: 3px solid #A47148; padding: 2px 0 2px 1.1em;
          margin: 1.4em 0; color: #555; font-style: italic;
        }
        .sp-body pre {
          background: #f0ede6; padding: 18px; border-radius: 10px;
          overflow-x: auto; font-size: 13.5px; margin: 1.4em 0;
        }
        .sp-body code {
          font-family: 'SF Mono', Menlo, monospace; font-size: 0.87em;
          background: #f0ede6; padding: 1px 5px; border-radius: 4px;
        }
        .sp-body pre code { background: none; padding: 0; }
        .sp-body table { border-collapse: collapse; width: 100%; margin: 1.4em 0; }
        .sp-body th, .sp-body td { border: 1px solid #e0dcd3; padding: 9px 12px; text-align: left; }
        .sp-body th { background: #f4f1ea; font-weight: 600; font-size: 13px; }
        .sp-body a {
          color: #A47148; text-decoration: underline; text-underline-offset: 3px;
        }
        .sp-body .pub-callout { border-radius: 10px; padding: 12px 16px; margin: 1.1em 0; }
        .sp-body .pub-hero {
          margin: 0 0 2rem; border-radius: 12px; overflow: hidden;
          max-height: 420px; aspect-ratio: 16/9; background: #e8e4dc;
        }
        .sp-body .pub-hero-img { width: 100%; height: 100%; object-fit: cover; display: block; }
        ${KATEX_PUBLISH_CSS}
        ${REWRITE_SHARED_CSS}

        .sp-footer {
          border-top: 1px solid rgba(0,0,0,0.07);
          padding: 36px 24px 48px; text-align: center;
          font-size: 13px; color: #999;
        }
        .sp-footer-brand {
          font-family: 'Source Serif 4', serif;
          font-weight: 700; color: #A47148;
        }
        .sp-stale { margin-top: 10px; font-size: 11px; color: #bbb; }

        .sp-body {
          --pub-accent: #A47148;
          --pub-summary-color: #555;
          --pub-exercise-border: #e0d4c3;
          --pub-exercise-header-bg: #f6f1ea;
          --pub-solution-bg: rgba(164,113,72,0.05);
          --pub-definition-border: #e0d4c3;
          --pub-definition-bg: #faf8f4;
          --pub-toggle-border: #e8e4dc;
          --pub-toggle-header-bg: #f5f2eb;
          --pub-highlight-bg: #faf6ee;
          --pub-checklist-bg: rgba(0,0,0,0.03);
        }
      `}</style>
    </>
  )
}

/* ─── Types ─────────────────────────────────────────────────────────────── */
type NoteData = NonNullable<Awaited<ReturnType<typeof getPublishedNote>>>
interface PageProps {
  note: NoteData
  bodyHtml: string
  readingTime: number
  slug: string
  isStale: boolean
}

/* ─── Route ──────────────────────────────────────────────────────────────── */
export default async function PublishedNotePage({ params }: { params: Promise<{ slug: string }> }) {
  const { slug } = await params
  const note = await getPublishedNote(slug)
  if (!note) notFound()

  const usesAiLayout = Boolean(note.publishedContent)
  const rawHtml = usesAiLayout ? note.publishedContent! : (note.content || '')
  const bodyHtml = processNoteHtmlForPublish(rawHtml)

  const readingSource = usesAiLayout ? note.publishedContent! : (note.content || '')
  const readingTime = estimateReadingTime(readingSource)
  const isStale = Boolean(
    note.publishedSourceHash
    && computePublishedSourceHash(note.content || '') !== note.publishedSourceHash
  )

  const props: PageProps = { note, bodyHtml, readingTime, slug, isStale }

  if (!usesAiLayout) return <SimplePage {...props} />
  if (note.publishedTemplate === 'brief') return <BriefPage {...props} />
  if (note.publishedTemplate === 'essay') return <EssayPage {...props} />
  return <MagazinePage {...props} />
}
