import { useEffect, useState, useCallback, useRef, memo } from "react";
import { motion, AnimatePresence } from "framer-motion";
import { Plus, ChevronRight, Loader2 } from "lucide-react";
import { useNavigate } from "react-router-dom";
import { useQueryClient } from "@tanstack/react-query";
import { supabase, createRealtimeChannel } from "@/integrations/supabase/client";
import { useAuth } from "@/hooks/useAuth";
import { useLike } from "@/hooks/useLike";
import AppLayout from "@/components/AppLayout";
import BrandLogo from "@/components/BrandLogo";
import PostCard from "@/components/PostCard";
import { PostSkeleton } from "@/components/Skeleton";
import StoryCard from "@/components/StoryCard";
import { AdInFeed } from "@/components/AdPost";
import { useNotifications } from "@/hooks/useNotifications";
import { preloadPage } from "@/lib/preload";

export const FEED_QUERY_KEY = ["feed-posts"];

const CHUNK_SIZE = 8;
const MemoPostCard = memo(PostCard);

interface Story {
  id: string;
  user_id: string;
  image_url: string;
  is_sponsored?: boolean;
  profiles?: any;
}

interface Post {
  id: string;
  user_id: string;
  image_url: string;
  image_urls?: string[] | null;
  caption: string | null;
  likes_count: number;
  comments_count: number;
  created_at: string;
  profiles?: any;
  liked_by_me?: boolean;
  media_type?: "image" | "video" | "audio";
  video_url?: string | null;
  thumbnail_url?: string | null;
  audio_url?: string | null;
  scale_type?: "original" | "square" | "wide" | "tall";
  music_metadata?: any;
  is_sponsored?: boolean;
  sponsor_name?: string;
  sponsor_url?: string;
}

export default function Feed() {
  const navigate = useNavigate();
  const { user } = useAuth();
  const { toggleLike } = useLike();
  const queryClient = useQueryClient();
  const { unreadCount } = useNotifications();
  const [stories, setStories] = useState<Story[]>([]);
  const [posts, setPosts] = useState<Post[]>([]);
  const [loading, setLoading] = useState(true);
  const [loadingMore, setLoadingMore] = useState(false);
  const [displayCount, setDisplayCount] = useState(CHUNK_SIZE);
  const [newPostsCount, setNewPostsCount] = useState(0);

  useEffect(() => {
    preloadPage("/messages");
    preloadPage("/notifications");
    preloadPage("/profile");
  }, []);

  const storyScrollRef = useRef<HTMLDivElement>(null);
  const lastFeedTimestampRef = useRef<string | null>(null);
  const sentinelRef = useRef<HTMLDivElement>(null);

  const load = useCallback(async () => {
    const cached = queryClient.getQueryData<Post[]>(FEED_QUERY_KEY);
    if (cached && cached.length > 0) {
      setPosts(cached);
      setLoading(false);
    } else {
      setLoading(true);
    }

    try {
      const [storiesRes, postsRes, likesRes] = await Promise.all([
        supabase.from("stories")
          .select("id,user_id,image_url,is_sponsored,profiles!stories_user_id_fkey(display_name,photo_url,username,is_verified,profile_theme)")
          .gt("expires_at", new Date().toISOString())
          .order("created_at", { ascending: false })
          .limit(30),
        supabase.from("posts")
          .select("*, profiles!posts_user_id_fkey(display_name,photo_url,username,is_verified,profile_theme)")
          .order("created_at", { ascending: false })
          .limit(30),
        user
          ? supabase.from("post_likes").select("post_id").eq("user_id", user.id)
          : Promise.resolve({ data: [] }),
      ]);

      if (storiesRes.data) setStories(storiesRes.data as any);
      
      if (postsRes.data) {
        const likedSet = new Set(((likesRes as any)?.data || []).map((l: any) => l.post_id));
        const enriched = (postsRes.data as any[]).map((x) => ({
          ...x,
          liked_by_me: likedSet.has(x.id),
        }));
        setPosts(enriched);
        queryClient.setQueryData(FEED_QUERY_KEY, enriched);
        if (enriched.length > 0) {
          lastFeedTimestampRef.current = enriched[0].created_at;
        }
      }
    } catch (err) {
      console.error("[Feed] Load error:", err);
    } finally {
      setDisplayCount(CHUNK_SIZE);
      setNewPostsCount(0);
      setLoading(false);
    }
  }, [user, queryClient]);

  useEffect(() => {
    load();
  }, [load]);

  useEffect(() => {
    const channel = createRealtimeChannel(`feed-posts-${user?.id || 'anon'}`);
    channel
      .on('postgres_changes',
        { event: 'INSERT', schema: 'public', table: 'posts' },
        () => {
          if (lastFeedTimestampRef.current) {
            setNewPostsCount(prev => prev + 1);
          }
        }
      )
      .on('postgres_changes',
        { event: 'UPDATE', schema: 'public', table: 'posts' },
        (payload) => {
          const { new: newRecord } = payload;
          setPosts((prev) => prev.map((p) =>
            p.id === newRecord.id && newRecord.likes_count !== undefined
              ? { ...p, likes_count: newRecord.likes_count }
              : p
          ));
        }
      )
      .subscribe();
    return () => { supabase.removeChannel(channel); };
  }, [user?.id]);

  const loadNewPosts = useCallback(async () => {
    if (!lastFeedTimestampRef.current) return;
    const { data: newPosts } = await supabase
      .from("posts")
      .select("*, profiles!posts_user_id_fkey(display_name,photo_url,username,is_verified,profile_theme)")
      .gt("created_at", lastFeedTimestampRef.current)
      .order("created_at", { ascending: false });
    if (!newPosts?.length) return;
    if (user) {
      const { data: likes } = await supabase.from("post_likes").select("post_id").eq("user_id", user.id);
      const likedSet = new Set((likes || []).map((l) => l.post_id));
      const enriched = (newPosts as any[]).map(x => ({ ...x, liked_by_me: likedSet.has(x.id) }));
      setPosts(prev => [...enriched, ...prev]);
    } else {
      setPosts(prev => [...(newPosts as any[]), ...prev]);
    }
    setDisplayCount(CHUNK_SIZE);
    setNewPostsCount(0);
    if (newPosts.length > 0) {
      lastFeedTimestampRef.current = newPosts[0].created_at;
    }
  }, [user]);
  
  const loadMore = useCallback(() => {
    if (loadingMore || displayCount >= posts.length) return;
    setLoadingMore(true);
    setTimeout(() => {
      setDisplayCount(prev => Math.min(prev + CHUNK_SIZE, posts.length));
      setLoadingMore(false);
    }, 150);
  }, [loadingMore, displayCount, posts.length]);

  useEffect(() => {
    if (!sentinelRef.current || loading) return;
    const observer = new IntersectionObserver(
      (entries) => {
        if (entries[0].isIntersecting) loadMore();
      },
      { rootMargin: "200px" }
    );
    observer.observe(sentinelRef.current);
    return () => observer.disconnect();
  }, [loading, loadMore]);

  const handleToggleLike = useCallback((post: Post) => {
    if (!user) return;
    const wasLiked = !!post.liked_by_me;
    setPosts((prev) => prev.map((x) =>
      x.id === post.id
        ? { ...x, liked_by_me: !wasLiked, likes_count: wasLiked ? Math.max(0, (x.likes_count || 0) - 1) : (x.likes_count || 0) + 1 }
        : x
    ));
    toggleLike(post.id, wasLiked);
  }, [user, toggleLike]);

  const storyGroups = Array.from(
    stories.reduce((map, s) => { if (!map.has(s.user_id)) map.set(s.user_id, s); return map; }, new Map<string, Story>()).values()
  );

  return (
    <AppLayout>
      <div className="mb-6 sm:mb-8">
        <div className="flex items-center justify-between mb-3">
          <h2 className="text-xs font-bold text-slate-400 tracking-wider uppercase flex items-center gap-2">
            <span className="w-1.5 h-4 rounded-full bg-sky-400" />
            Stories
          </h2>
          <button 
            onClick={() => navigate("/create-story")} 
            className="text-xs font-bold text-sky-400 hover:text-sky-300 transition-colors flex items-center gap-1"
          >
            Criar <ChevronRight className="w-3.5 h-3.5" />
          </button>
        </div>
        <div ref={storyScrollRef} className="flex gap-3 overflow-x-auto pb-2 -mx-4 px-4 sm:-mx-6 sm:px-6 scrollbar-hide">
          <motion.button
            whileTap={{ scale: 0.95 }}
            onClick={() => navigate("/create-story")}
            className="flex flex-col items-center gap-1.5 shrink-0"
          >
            <div className="w-16 h-16 rounded-full bg-gradient-to-tr from-sky-500 to-blue-600 p-0.5 shadow-sm">
              <div className="w-full h-full rounded-full bg-slate-900 flex items-center justify-center">
                <Plus className="w-6 h-6 text-sky-400" />
              </div>
            </div>
            <span className="text-[11px] text-slate-400 font-semibold">Seu story</span>
          </motion.button>
          {storyGroups.map((s) => (
            <StoryCard key={s.user_id} user_id={s.user_id} profiles={s.profiles} is_sponsored={s.is_sponsored} />
          ))}
        </div>
      </div>

      <div>
        {loading ? (
          <div className="flex flex-col items-center py-6 gap-5">
            {[1, 2, 3].map((i) => (
              <PostSkeleton key={i} />
            ))}
          </div>
        ) : posts.length === 0 ? (
          <motion.div initial={{ opacity: 0, y: 20 }} animate={{ opacity: 1, y: 0 }} className="py-20 space-y-6 text-center">
            <div className="relative mx-auto w-32 h-32 flex items-center justify-center">
              <div className="absolute inset-0 bg-blue-500/10 blur-[40px] rounded-full" />
              <BrandLogo size={100} />
            </div>
            <div>
              <p className="text-xl font-bold text-white tracking-tight">Nenhuma publicação ainda</p>
              <p className="text-sm text-slate-400 mt-1 max-w-[240px] mx-auto">Seja o primeiro a compartilhar algo com a comunidade!</p>
            </div>
            <button 
              onClick={() => navigate("/create-post")}
              className="btn-friendly text-sm font-bold px-8 py-3 rounded-full"
            >
              <Plus className="w-5 h-5" /> Criar primeira publicação
            </button>
          </motion.div>
        ) : (
          <div className="space-y-6">
            {newPostsCount > 0 && (
              <motion.button
                initial={{ opacity: 0, y: -10 }}
                animate={{ opacity: 1, y: 0 }}
                onClick={() => { loadNewPosts(); window.scrollTo({ top: 0, behavior: 'smooth' }); }}
                className="w-full py-3 rounded-2xl bg-sky-500/10 border border-sky-500/20 text-sky-400 text-xs font-bold hover:bg-sky-500/20 transition-all shadow-sm"
              >
                {newPostsCount} nova{newPostsCount > 1 ? 's' : ''} publicação{newPostsCount > 1 ? 'ões' : ''} disponível{newPostsCount > 1 ? 'is' : ''} — Toque para ver
              </motion.button>
            )}
            <AnimatePresence mode="popLayout">
              {(() => {
                const visiblePosts = posts.slice(0, displayCount);
                const items: JSX.Element[] = [];
                const adPositions = posts.length >= 10 ? [3, 7] : posts.length >= 5 ? [Math.floor(posts.length / 2)] : [];
                
                visiblePosts.forEach((post, i) => {
                  items.push(
                    <motion.div
                      key={post.id}
                      initial={{ opacity: 0, y: 16 }}
                      animate={{ opacity: 1, y: 0 }}
                      transition={{ delay: i * 0.03, type: "spring", stiffness: 300, damping: 25 }}
                      layout
                    >
                      <MemoPostCard
                        {...post}
                        onToggleLike={handleToggleLike}
                        index={i}
                      />
                    </motion.div>
                  );
                  
                  if (adPositions.includes(i)) {
                    items.push(
                      <motion.div
                        key={`ad-${i}`}
                        initial={{ opacity: 0, y: 16 }}
                        animate={{ opacity: 1, y: 0 }}
                        transition={{ delay: (i + 0.5) * 0.03, type: "spring", stiffness: 300, damping: 25 }}
                      >
                        <AdInFeed />
                      </motion.div>
                    );
                  }
                });
                
                return items;
              })()}
            </AnimatePresence>

            <div ref={sentinelRef} className="flex items-center justify-center py-6">
              {loadingMore ? (
                <Loader2 className="w-6 h-6 text-sky-400 animate-spin" />
              ) : displayCount < posts.length ? (
                <button
                  onClick={loadMore}
                  className="px-6 py-2.5 rounded-2xl bg-white/[0.04] border border-white/[0.08] text-xs font-bold text-slate-400 hover:text-white hover:bg-white/[0.08] transition-all"
                >
                  Carregar mais publicações
                </button>
              ) : null}
            </div>
          </div>
        )}
      </div>
    </AppLayout>
  );
}