"use client";

import { useState, useEffect, type SyntheticEvent } from "react";
import type { ReactElement } from "react";
import type { Domain } from "@mosaic/shared";
import { DomainList } from "@/components/domains/DomainList";
import { fetchDomains, createDomain, deleteDomain } from "@/lib/api/domains";
import type { CreateDomainDto } from "@/lib/api/domains";
import { useWorkspaceId } from "@/lib/hooks";

/* ---------------------------------------------------------------------------
   Slug generation helper
   --------------------------------------------------------------------------- */

function generateSlug(name: string): string {
  return name
    .toLowerCase()
    .trim()
    .replace(/[^a-z0-9\s-]/g, "")
    .replace(/\s+/g, "-")
    .replace(/-+/g, "-")
    .slice(0, 100);
}

/* ---------------------------------------------------------------------------
   Create Domain Dialog
   --------------------------------------------------------------------------- */

interface CreateDomainDialogProps {
  open: boolean;
  onOpenChange: (open: boolean) => void;
  onSubmit: (data: CreateDomainDto) => Promise<void>;
  isSubmitting: boolean;
}

function CreateDomainDialog({
  open,
  onOpenChange,
  onSubmit,
  isSubmitting,
}: CreateDomainDialogProps): ReactElement | null {
  const [name, setName] = useState("");
  const [slug, setSlug] = useState("");
  const [slugTouched, setSlugTouched] = useState(false);
  const [description, setDescription] = useState("");
  const [formError, setFormError] = useState<string | null>(null);

  function resetForm(): void {
    setName("");
    setSlug("");
    setSlugTouched(false);
    setDescription("");
    setFormError(null);
  }

  function handleNameChange(value: string): void {
    setName(value);
    if (!slugTouched) {
      setSlug(generateSlug(value));
    }
  }

  function handleSlugChange(value: string): void {
    setSlugTouched(true);
    setSlug(value.toLowerCase().replace(/[^a-z0-9-]/g, ""));
  }

  async function handleSubmit(e: SyntheticEvent): Promise<void> {
    e.preventDefault();
    setFormError(null);

    const trimmedName = name.trim();
    if (!trimmedName) {
      setFormError("Domain name is required.");
      return;
    }

    const trimmedSlug = slug.trim();
    if (!trimmedSlug) {
      setFormError("Slug is required.");
      return;
    }

    if (!/^[a-z0-9-]+$/.test(trimmedSlug)) {
      setFormError("Slug must contain only lowercase letters, numbers, and hyphens.");
      return;
    }

    try {
      const payload: CreateDomainDto = { name: trimmedName, slug: trimmedSlug };
      const trimmedDesc = description.trim();
      if (trimmedDesc) {
        payload.description = trimmedDesc;
      }
      await onSubmit(payload);
      resetForm();
    } catch (err: unknown) {
      setFormError(err instanceof Error ? err.message : "Failed to create domain.");
    }
  }

  if (!open) return null;

  return (
    <div
      role="dialog"
      aria-modal="true"
      aria-labelledby="create-domain-title"
      style={{
        position: "fixed",
        inset: 0,
        zIndex: 50,
        display: "flex",
        alignItems: "center",
        justifyContent: "center",
      }}
    >
      {/* Backdrop */}
      <div
        style={{
          position: "fixed",
          inset: 0,
          background: "rgba(0,0,0,0.5)",
        }}
        onClick={() => {
          if (!isSubmitting) {
            resetForm();
            onOpenChange(false);
          }
        }}
      />

      {/* Dialog */}
      <div
        style={{
          position: "relative",
          background: "var(--surface, #fff)",
          borderRadius: "8px",
          border: "1px solid var(--border, #e5e7eb)",
          padding: 24,
          width: "100%",
          maxWidth: 480,
          zIndex: 1,
        }}
      >
        <h2
          id="create-domain-title"
          style={{
            fontSize: "1.125rem",
            fontWeight: 600,
            color: "var(--text, #111)",
            margin: "0 0 8px",
          }}
        >
          New Domain
        </h2>
        <p style={{ color: "var(--muted, #6b7280)", fontSize: "0.875rem", margin: "0 0 16px" }}>
          Domains help you organize tasks, projects, and events by life area.
        </p>

        <form
          onSubmit={(e) => {
            void handleSubmit(e);
          }}
        >
          {/* Name */}
          <div style={{ marginBottom: 16 }}>
            <label
              htmlFor="domain-name"
              style={{
                display: "block",
                marginBottom: 6,
                fontSize: "0.85rem",
                fontWeight: 500,
                color: "var(--text-2, #374151)",
              }}
            >
              Name <span style={{ color: "var(--danger, #ef4444)" }}>*</span>
            </label>
            <input
              id="domain-name"
              type="text"
              value={name}
              onChange={(e) => {
                handleNameChange(e.target.value);
              }}
              placeholder="e.g. Personal Finance"
              maxLength={255}
              autoFocus
              style={{
                width: "100%",
                padding: "8px 12px",
                background: "var(--bg, #f9fafb)",
                border: "1px solid var(--border, #d1d5db)",
                borderRadius: "6px",
                color: "var(--text, #111)",
                fontSize: "0.9rem",
                outline: "none",
                boxSizing: "border-box",
              }}
            />
          </div>

          {/* Slug */}
          <div style={{ marginBottom: 16 }}>
            <label
              htmlFor="domain-slug"
              style={{
                display: "block",
                marginBottom: 6,
                fontSize: "0.85rem",
                fontWeight: 500,
                color: "var(--text-2, #374151)",
              }}
            >
              Slug <span style={{ color: "var(--danger, #ef4444)" }}>*</span>
            </label>
            <input
              id="domain-slug"
              type="text"
              value={slug}
              onChange={(e) => {
                handleSlugChange(e.target.value);
              }}
              placeholder="e.g. personal-finance"
              maxLength={100}
              style={{
                width: "100%",
                padding: "8px 12px",
                background: "var(--bg, #f9fafb)",
                border: "1px solid var(--border, #d1d5db)",
                borderRadius: "6px",
                color: "var(--text, #111)",
                fontSize: "0.9rem",
                outline: "none",
                boxSizing: "border-box",
                fontFamily: "var(--mono, monospace)",
              }}
            />
            <p
              style={{
                fontSize: "0.75rem",
                color: "var(--muted, #6b7280)",
                margin: "4px 0 0",
              }}
            >
              Lowercase letters, numbers, and hyphens only.
            </p>
          </div>

          {/* Description */}
          <div style={{ marginBottom: 16 }}>
            <label
              htmlFor="domain-description"
              style={{
                display: "block",
                marginBottom: 6,
                fontSize: "0.85rem",
                fontWeight: 500,
                color: "var(--text-2, #374151)",
              }}
            >
              Description
            </label>
            <textarea
              id="domain-description"
              value={description}
              onChange={(e) => {
                setDescription(e.target.value);
              }}
              placeholder="A brief summary of this domain..."
              rows={3}
              maxLength={10000}
              style={{
                width: "100%",
                padding: "8px 12px",
                background: "var(--bg, #f9fafb)",
                border: "1px solid var(--border, #d1d5db)",
                borderRadius: "6px",
                color: "var(--text, #111)",
                fontSize: "0.9rem",
                outline: "none",
                resize: "vertical",
                fontFamily: "inherit",
                boxSizing: "border-box",
              }}
            />
          </div>

          {/* Form error */}
          {formError !== null && (
            <p
              style={{
                color: "var(--danger, #ef4444)",
                fontSize: "0.85rem",
                margin: "0 0 12px",
              }}
            >
              {formError}
            </p>
          )}

          {/* Buttons */}
          <div
            style={{
              display: "flex",
              justifyContent: "flex-end",
              gap: 8,
              marginTop: 8,
            }}
          >
            <button
              type="button"
              onClick={() => {
                resetForm();
                onOpenChange(false);
              }}
              disabled={isSubmitting}
              style={{
                padding: "8px 16px",
                background: "transparent",
                border: "1px solid var(--border, #d1d5db)",
                borderRadius: "6px",
                color: "var(--text-2, #374151)",
                fontSize: "0.85rem",
                cursor: "pointer",
              }}
            >
              Cancel
            </button>
            <button
              type="submit"
              disabled={isSubmitting || !name.trim() || !slug.trim()}
              style={{
                padding: "8px 16px",
                background: "var(--primary, #111827)",
                border: "none",
                borderRadius: "6px",
                color: "#fff",
                fontSize: "0.85rem",
                fontWeight: 500,
                cursor: isSubmitting || !name.trim() || !slug.trim() ? "not-allowed" : "pointer",
                opacity: isSubmitting || !name.trim() || !slug.trim() ? 0.6 : 1,
              }}
            >
              {isSubmitting ? "Creating..." : "Create Domain"}
            </button>
          </div>
        </form>
      </div>
    </div>
  );
}

/* ---------------------------------------------------------------------------
   Domains Page
   --------------------------------------------------------------------------- */

export default function DomainsPage(): ReactElement {
  const workspaceId = useWorkspaceId();
  const [domains, setDomains] = useState<Domain[]>([]);
  const [isLoading, setIsLoading] = useState<boolean>(true);
  const [error, setError] = useState<string | null>(null);

  // Create dialog state
  const [createOpen, setCreateOpen] = useState(false);
  const [isCreating, setIsCreating] = useState(false);

  useEffect(() => {
    if (!workspaceId) {
      setIsLoading(false);
      return;
    }
    void loadDomains();
  }, [workspaceId]);

  async function loadDomains(): Promise<void> {
    try {
      setIsLoading(true);
      const response = await fetchDomains(undefined, workspaceId ?? undefined);
      setDomains(response.data);
      setError(null);
    } catch (err) {
      setError(err instanceof Error ? err.message : "Failed to load domains");
    } finally {
      setIsLoading(false);
    }
  }

  function handleEdit(_domain: Domain): void {
    // TODO: Open edit modal/form
  }

  async function handleDelete(domain: Domain): Promise<void> {
    if (!confirm(`Are you sure you want to delete "${domain.name}"?`)) {
      return;
    }

    try {
      await deleteDomain(domain.id, workspaceId ?? undefined);
      await loadDomains();
    } catch (err) {
      setError(err instanceof Error ? err.message : "Failed to delete domain");
    }
  }

  async function handleCreate(data: CreateDomainDto): Promise<void> {
    setIsCreating(true);
    try {
      await createDomain(data, workspaceId ?? undefined);
      setCreateOpen(false);
      await loadDomains();
    } catch (err) {
      setError(err instanceof Error ? err.message : "Failed to create domain.");
    } finally {
      setIsCreating(false);
    }
  }

  return (
    <div className="max-w-6xl mx-auto p-6">
      <div className="mb-6">
        <h1 className="text-3xl font-bold mb-2">Domains</h1>
        <p className="text-gray-600">Organize your tasks and projects by life areas</p>
      </div>

      {error && (
        <div className="mb-6 p-4 bg-red-50 border border-red-200 rounded text-red-700">{error}</div>
      )}

      <div className="mb-6">
        <button
          className="px-4 py-2 bg-gray-900 text-white rounded hover:bg-gray-800"
          onClick={() => {
            setCreateOpen(true);
          }}
        >
          Create Domain
        </button>
      </div>

      <DomainList
        domains={domains}
        isLoading={isLoading}
        onEdit={handleEdit}
        onDelete={handleDelete}
      />

      <CreateDomainDialog
        open={createOpen}
        onOpenChange={setCreateOpen}
        onSubmit={handleCreate}
        isSubmitting={isCreating}
      />
    </div>
  );
}
