/**
 * `TemplatesPanel` — feature component for agent template management (L7).
 *
 * Pure presentation: all behaviour comes from {@link useTemplates}. Styled
 * with `@/shared` design system tokens; no inline styles.
 *
 * Provides:
 * - Template list (name + version)
 * - "New template" button that opens {@link TemplateEditor} in create-mode
 * - Per-template "Edit" button that opens {@link TemplateEditor} in edit-mode
 * - Delete
 * - "Create agent from template" action per template
 *
 * The `template name` and `template content` aria-labels are preserved inside
 * `TemplateEditor`; `create template` aria-label is on the submit button.
 */

import { useState } from "react";

import type { Template } from "@/domain";
import { Button, Panel, Spinner } from "@/shared";
import { useGateways } from "@/app/di";
import { TemplateEditor } from "./TemplateEditor";
import { useTemplates } from "./useTemplates";

export interface TemplatesPanelProps {
  /** The project into which agents can be created from templates. */
  projectId: string;
}

/** Editor open-state: "create" or edit-mode for a specific template. */
type EditorState =
  | { mode: "create" }
  | { mode: "edit"; template: Template };

export function TemplatesPanel({ projectId }: TemplatesPanelProps) {
  const vm = useTemplates();
  const { profile } = useGateways();

  // Profiles list for the editor's default-profile selector
  const [profiles, setProfiles] = useState<import("@/domain").AgentProfile[]>([]);
  const [profilesLoaded, setProfilesLoaded] = useState(false);

  const [editorState, setEditorState] = useState<EditorState | null>(null);
  const [editorBusy, setEditorBusy] = useState(false);

  /** Lazily load profiles when the editor is first opened. */
  async function openEditor(state: EditorState) {
    if (!profilesLoaded) {
      try {
        const list = await profile.listProfiles();
        setProfiles(list);
      } catch {
        // Profiles are optional — continue without them.
      }
      setProfilesLoaded(true);
    }
    setEditorState(state);
  }

  async function handleSave(
    name: string,
    content: string,
    defaultProfileId: string,
  ) {
    if (!editorState) return;
    setEditorBusy(true);
    try {
      if (editorState.mode === "create") {
        await vm.createTemplate({ name, content, defaultProfileId });
      } else {
        // Update name isn't supported by the port (only content); if name
        // changed we skip it gracefully — the current port only updates content.
        await vm.updateTemplate(editorState.template.id, content);
      }
      setEditorState(null);
    } finally {
      setEditorBusy(false);
    }
  }

  return (
    <>
      {/* ── Fullscreen template editor overlay ── */}
      {editorState !== null && (
        <TemplateEditor
          template={editorState.mode === "edit" ? editorState.template : null}
          profiles={profiles}
          onSave={handleSave}
          onClose={() => setEditorState(null)}
          busy={editorBusy}
        />
      )}

      <Panel title="Templates" className="flex flex-col gap-0">
        {vm.error && (
          <p
            role="alert"
            className="mx-4 mt-3 rounded-md border border-danger/40 bg-danger/10 px-3 py-2 text-sm text-danger"
          >
            {vm.error}
          </p>
        )}

        {/* ── Create button ── */}
        <div className="flex items-center justify-between border-b border-border px-4 py-3">
          <h4 className="text-xs font-semibold uppercase tracking-wide text-faint">
            Templates
          </h4>
          <div className="flex items-center gap-2">
            {vm.busy && <Spinner size={14} />}
            <Button
              type="button"
              variant="primary"
              aria-label="create template"
              disabled={vm.busy}
              onClick={() => void openEditor({ mode: "create" })}
            >
              New template
            </Button>
          </div>
        </div>

        {/* ── Template list ── */}
        <div className="p-4">
          {vm.templates.length === 0 ? (
            <p className="text-sm text-muted">No templates yet.</p>
          ) : (
            <ul className="flex flex-col divide-y divide-border">
              {vm.templates.map((t) => (
                <li key={t.id} className="flex flex-col gap-2 py-3 first:pt-0 last:pb-0">
                  <div className="flex items-center justify-between gap-3">
                    <div className="flex min-w-0 flex-col gap-0.5">
                      <span className="font-medium text-content">{t.name}</span>
                      <span className="text-xs text-muted">v{t.version}</span>
                    </div>

                    <div className="flex items-center gap-1.5 shrink-0">
                      <Button
                        size="sm"
                        variant="ghost"
                        aria-label={`edit ${t.name}`}
                        disabled={vm.busy}
                        onClick={() => void openEditor({ mode: "edit", template: t })}
                      >
                        Edit
                      </Button>
                      <Button
                        size="sm"
                        variant="primary"
                        aria-label={`create agent from ${t.name}`}
                        disabled={vm.busy}
                        onClick={() =>
                          void vm.createAgentFromTemplate(projectId, t.id)
                        }
                      >
                        Create agent
                      </Button>
                      <Button
                        size="sm"
                        variant="ghost"
                        aria-label={`delete template ${t.name}`}
                        disabled={vm.busy}
                        onClick={() => void vm.deleteTemplate(t.id)}
                        className="text-danger hover:text-danger"
                      >
                        Delete
                      </Button>
                    </div>
                  </div>
                </li>
              ))}
            </ul>
          )}
        </div>
      </Panel>
    </>
  );
}
