'use client';

import { useState, useEffect, useCallback, useRef } from 'react';
import Link from 'next/link';
import { listRecipes, deleteRecipe } from '@/services/recipes';
import { NutritionWarning } from '@meshitrack/shared';
import type { z } from 'zod/v4';
import type { RecipeResponseSchema } from '@meshitrack/shared';

type Recipe = z.infer<typeof RecipeResponseSchema>;

const WARNING_LABELS: Partial<Record<string, string>> = {
  [NutritionWarning.HIGH_CALORIES]: 'High cal',
  [NutritionWarning.HIGH_SODIUM]: 'High sodium',
  [NutritionWarning.HIGH_SUGAR]: 'High sugar',
  [NutritionWarning.HIGH_SATURATED_FAT]: 'High sat fat',
  [NutritionWarning.LOW_PROTEIN]: 'Low protein',
  [NutritionWarning.LOW_FIBER]: 'Low fiber',
  [NutritionWarning.HIGH_CHOLESTEROL]: 'High chol',
};

function formatTime(minutes?: number): string {
  if (!minutes) return '';
  if (minutes < 60) return `${minutes} min`;
  const h = Math.floor(minutes / 60);
  const m = minutes % 60;
  return m > 0 ? `${h}h ${m}m` : `${h}h`;
}

function useDebounce<T>(value: T, delay: number): T {
  const [debounced, setDebounced] = useState(value);
  useEffect(() => {
    const t = setTimeout(() => setDebounced(value), delay);
    return () => clearTimeout(t);
  }, [value, delay]);
  return debounced;
}

export function RecipeList({ householdId }: { householdId: string }) {
  const [recipes, setRecipes] = useState<Recipe[]>([]);
  const [loading, setLoading] = useState(true);
  const [error, setError] = useState('');
  const [search, setSearch] = useState('');
  const [filterCuisine, setFilterCuisine] = useState('');
  const [favoritesOnly, setFavoritesOnly] = useState(false);
  const debouncedSearch = useDebounce(search, 300);
  const abortRef = useRef<AbortController | null>(null);

  const fetchRecipes = useCallback(async () => {
    if (!householdId) return;
    abortRef.current?.abort();
    abortRef.current = new AbortController();
    setLoading(true);
    setError('');
    try {
      const result = await listRecipes(householdId, {
        q: debouncedSearch || undefined,
        cuisine: filterCuisine || undefined,
        isFavorite: favoritesOnly || undefined,
        limit: 50,
      });
      setRecipes(result.data);
    } catch (err) {
      if (err instanceof Error && err.name !== 'AbortError') {
        setError(err.message);
      }
    } finally {
      setLoading(false);
    }
  }, [householdId, debouncedSearch, filterCuisine, favoritesOnly]);

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

  async function handleDelete(id: string, name: string) {
    if (!confirm(`Delete "${name}"?`)) return;
    try {
      await deleteRecipe(householdId, id);
      setRecipes((prev) => prev.filter((r) => r._id !== id));
    } catch (err) {
      setError(err instanceof Error ? err.message : 'Failed to delete recipe');
    }
  }

  return (
    <div style={{ padding: '28px 32px 56px', maxWidth: 1200 }}>
      {/* Toolbar */}
      <div
        style={{
          display: 'flex',
          gap: 12,
          marginBottom: 24,
          flexWrap: 'wrap',
          alignItems: 'center',
        }}
      >
        <input
          type="search"
          placeholder="Search recipes..."
          value={search}
          onChange={(e) => setSearch(e.target.value)}
          style={{
            flex: '1 1 240px',
            padding: '8px 12px',
            borderRadius: 'var(--r-md)',
            border: '1px solid var(--border)',
            background: 'var(--bg-elev)',
            color: 'var(--ink)',
            fontSize: 14,
          }}
        />
        <input
          type="text"
          placeholder="Cuisine..."
          value={filterCuisine}
          onChange={(e) => setFilterCuisine(e.target.value)}
          style={{
            width: 160,
            padding: '8px 12px',
            borderRadius: 'var(--r-md)',
            border: '1px solid var(--border)',
            background: 'var(--bg-elev)',
            color: 'var(--ink)',
            fontSize: 14,
          }}
        />
        <label
          style={{ display: 'flex', alignItems: 'center', gap: 6, fontSize: 14, cursor: 'pointer' }}
        >
          <input
            type="checkbox"
            checked={favoritesOnly}
            onChange={(e) => setFavoritesOnly(e.target.checked)}
          />
          Favorites
        </label>
        <Link
          href="/recipes/new"
          style={{
            padding: '8px 16px',
            background: 'var(--brand)',
            color: '#fff',
            borderRadius: 'var(--r-md)',
            fontSize: 14,
            textDecoration: 'none',
            whiteSpace: 'nowrap',
          }}
        >
          + New Recipe
        </Link>
      </div>

      {error && <p style={{ color: 'var(--danger)', marginBottom: 16, fontSize: 14 }}>{error}</p>}

      {loading ? (
        <div
          style={{
            display: 'grid',
            gridTemplateColumns: 'repeat(auto-fill, minmax(300px, 1fr))',
            gap: 16,
          }}
        >
          {[...Array(6)].map((_, i) => (
            <div
              key={i}
              style={{
                height: 160,
                background: 'var(--bg-elev)',
                borderRadius: 'var(--r-md)',
                opacity: 0.5,
              }}
            />
          ))}
        </div>
      ) : recipes.length === 0 ? (
        <div
          style={{
            textAlign: 'center',
            padding: '64px 24px',
            color: 'var(--ink-muted)',
            fontSize: 14,
          }}
        >
          {search || filterCuisine || favoritesOnly
            ? 'No recipes match your filters.'
            : 'No recipes yet. Create your first recipe.'}
        </div>
      ) : (
        <div
          style={{
            display: 'grid',
            gridTemplateColumns: 'repeat(auto-fill, minmax(300px, 1fr))',
            gap: 16,
          }}
        >
          {recipes.map((recipe) => (
            <RecipeCard key={recipe._id} recipe={recipe} onDelete={handleDelete} />
          ))}
        </div>
      )}
    </div>
  );
}

function RecipeCard({
  recipe,
  onDelete,
}: {
  recipe: Recipe;
  onDelete: (id: string, name: string) => void;
}) {
  const time = recipe.totalTime ?? (recipe.prepTime ?? 0) + (recipe.cookTime ?? 0);

  return (
    <div
      style={{
        background: 'var(--bg-elev)',
        border: '1px solid var(--border)',
        borderRadius: 'var(--r-md)',
        padding: 20,
        display: 'flex',
        flexDirection: 'column',
        gap: 10,
      }}
    >
      <div style={{ display: 'flex', justifyContent: 'space-between', alignItems: 'flex-start' }}>
        <Link
          href={`/recipes/${recipe._id}`}
          style={{
            fontSize: 16,
            fontWeight: 600,
            color: 'var(--ink)',
            textDecoration: 'none',
            lineHeight: 1.3,
          }}
        >
          {recipe.isFavorite && <span style={{ marginRight: 4 }}>&#9733;</span>}
          {recipe.name}
        </Link>
      </div>

      {recipe.cuisine && (
        <span style={{ fontSize: 12, color: 'var(--ink-muted)' }}>{recipe.cuisine}</span>
      )}

      <div
        style={{
          display: 'flex',
          gap: 16,
          fontSize: 13,
          color: 'var(--ink-muted)',
        }}
      >
        <span>
          {recipe.servings} serving{recipe.servings !== 1 ? 's' : ''}
        </span>
        {time > 0 && <span>{formatTime(time)}</span>}
        <span style={{ color: 'var(--ink)', fontWeight: 500 }}>
          {Math.round(recipe.perServingNutrition.calories)} kcal
        </span>
      </div>

      {recipe.warnings.length > 0 && (
        <div style={{ display: 'flex', gap: 4, flexWrap: 'wrap' }}>
          {recipe.warnings.slice(0, 3).map((w) => (
            <span
              key={w}
              style={{
                fontSize: 11,
                padding: '2px 6px',
                borderRadius: 4,
                background: 'var(--danger-soft, #fee)',
                color: 'var(--danger)',
              }}
            >
              {WARNING_LABELS[w] ?? w}
            </span>
          ))}
        </div>
      )}

      {recipe.tags.length > 0 && (
        <div style={{ display: 'flex', gap: 4, flexWrap: 'wrap' }}>
          {recipe.tags.slice(0, 4).map((tag) => (
            <span
              key={tag}
              style={{
                fontSize: 11,
                padding: '2px 6px',
                borderRadius: 4,
                background: 'var(--bg-subtle, var(--bg))',
                color: 'var(--ink-muted)',
                border: '1px solid var(--border)',
              }}
            >
              {tag}
            </span>
          ))}
        </div>
      )}

      <div style={{ display: 'flex', gap: 8, marginTop: 4 }}>
        <Link
          href={`/recipes/${recipe._id}/edit`}
          style={{
            fontSize: 13,
            color: 'var(--brand)',
            textDecoration: 'none',
          }}
        >
          Edit
        </Link>
        <button
          type="button"
          onClick={() => onDelete(recipe._id, recipe.name)}
          style={{
            background: 'none',
            border: 'none',
            fontSize: 13,
            color: 'var(--ink-muted)',
            cursor: 'pointer',
            padding: 0,
          }}
        >
          Delete
        </button>
      </div>
    </div>
  );
}
