//! Unified PostViewer Page Component

use leptos::prelude::*;
use rustelo_core_lib::i18n::content_helper::create_content_provider_reactive;

#[component]
pub fn PostViewerPage(
    _language: String,
    #[prop(optional)] slug: Option<String>,
    #[prop(default = "content".to_string())] content_type: String,
) -> impl IntoView {
    #[cfg(not(target_arch = "wasm32"))]
    {
        view! { <crate::post_viewer::ssr::PostViewerPageSSR _language=_language.clone() slug=slug.unwrap_or_default() content_type=content_type /> }
    }
    #[cfg(target_arch = "wasm32")]
    {
        view! { <crate::post_viewer::client::PostViewerPageClient _language=_language.clone() slug=slug.unwrap_or_default() content_type=content_type /> }
    }
}

#[component]
pub fn UnifiedPostViewerPage(
    #[allow(unused_variables)]
    #[prop(default = rustelo_core_lib::config::get_default_language().to_string())]
    _language: String,
    #[prop(optional)] lang_content: Option<std::collections::HashMap<String, String>>,
    #[allow(unused_variables)]
    #[prop(default = "content".to_string())]
    content_type: String,
    #[allow(unused_variables)]
    #[prop(default = "".to_string())]
    slug: String,
    #[prop(default = true)] show_author: bool,
    #[prop(default = true)] show_date: bool,
    #[prop(default = true)] show_tags: bool,
    /// Accepted for API compatibility — no related-posts system is implemented.
    #[allow(unused_variables)]
    #[prop(default = false)]
    show_related_posts: bool,
    /// Accepted for API compatibility — no comments system is implemented.
    #[allow(unused_variables)]
    #[prop(default = false)]
    enable_comments: bool,
    /// Accepted for API compatibility — no social-sharing system is
    /// implemented.
    #[allow(unused_variables)]
    #[prop(default = false)]
    enable_social_sharing: bool,
) -> impl IntoView {
    let content = create_content_provider_reactive(lang_content.clone());

    let post_title = content.t_quiet("post-title");
    let post_subtitle = content.t_quiet("post-subtitle");
    let post_content = content.t_quiet("post-content");
    let post_author = content.t_quiet("post-author");
    let post_date = content.t_quiet("post-date");
    let post_tags_raw = content.t_quiet("post-tags");

    let has_content = !post_title.is_empty() || !post_content.is_empty();
    let has_author = show_author && !post_author.is_empty();
    let has_date = show_date && !post_date.is_empty();
    let has_tags = show_tags && !post_tags_raw.is_empty();
    let tags: Vec<String> = if has_tags {
        post_tags_raw.split(", ").map(str::to_string).collect()
    } else {
        vec![]
    };

    view! {
      <div class="ds-bg-page">
        <section
          class="relative py-ds-4 ds-container ds-rounded-lg ds-shadow-lg"
          class:hidden={!has_content}
          id="title-section"
        >
          <div class="mx-auto max-w-4xl text-center">
            <h1 class="text-balance text-4xl font-bold tracking-tight ds-text sm:text-6xl mb-ds-4">
              {post_title}
            </h1>
            <div class="mt-ds-6 ds-body ds-text-secondary max-w-2xl mx-auto">
              {post_subtitle}
            </div>

            // ── Byline: author + date ─────────────────────────────────────────
            // Always render the container so SSR and WASM produce identical DOM
            // structure. CSS `hidden` controls visibility instead of Option<View>
            // (.then(|| view!{...})), which emits `<!>` when None and causes a
            // hydration panic when WASM starts with empty lang_content.
            <div
              class="mt-ds-4 flex items-center justify-center gap-4 text-sm ds-text-secondary"
              class:hidden=(!has_author && !has_date)
            >
              <span class="flex items-center gap-1" class:hidden=(!has_author)>
                <span class="font-medium">{post_author.clone()}</span>
              </span>
              <span class:hidden=(!has_author || !has_date)>"·"</span>
              <time datetime=post_date.clone() class:hidden=(!has_date)>{post_date.clone()}</time>
            </div>

            // ── Tags ─────────────────────────────────────────────────────────
            // inner_html avoids the Vec count mismatch: SSR emits N <span>
            // children, WASM initial renders 0. Both now emit a single <div>
            // element whose inner content is opaque to the hydration cursor.
            <div
              class="mt-ds-3 flex flex-wrap justify-center gap-2"
              class:hidden=(!has_tags)
              inner_html={
                tags.iter()
                  .map(|tag| format!(
                    "<span class=\"badge badge-outline ds-text text-xs\">{}</span>",
                    tag.replace('&', "&amp;").replace('<', "&lt;").replace('>', "&gt;")
                  ))
                  .collect::<String>()
              }
            ></div>
          </div>
        </section>

        <section
          class="py-ds-6 px-ds-4 ds-bg ds-rounded-lg"
          class:hidden={!has_content}
        >
          <div class="ds-container-lg ds-container">
            <div class="max-w-4xl mx-auto">
              <div class="ds-text-secondary space-y-4">
                <div class="post-content-body" inner_html={post_content}></div>
              </div>
            </div>
          </div>
        </section>

        <div
          class="py-ds-8"
          class:hidden={has_content}
        >
          <div class="ds-container max-w-4xl mx-auto text-center">
            <div class="ds-text-secondary">
              "Loading..."
            </div>
          </div>
        </div>
      </div>
    }
}
