/**
 * TemplateMatchPanel — inline Script Generator panel for the case where a
 * Suggested Fix matches an existing Script Library template.
 *
 * Per FLOWPILOT-MIGRATION.md mockup 02 + Section 3.2:
 * - "Verified template" badge above the parameter form
 * - Parameters pre-filled from `fix.ai_drafted_parameters` get a cyan
 *   `from session` tag and a cyan-tinted input background
 * - Hint line per pre-filled parameter explains the source
 * - Engineer can edit any value before generating
 * - Generate posts to /scripts/generate (existing endpoint, already wired
 *   in Phase 3 to bump state_version on `ai_session_id`)
 *
 * The actual run happens outside the app — engineers copy the generated
 * script and execute it via their RMM / shell. The panel ends with a
 * Copy button + a "Mark as completed" affordance that's wired to the
 * decision endpoint (one_off, since the engineer used the existing template).
 */
import { useEffect, useState } from 'react'
import { Loader2, Copy, Check, ShieldCheck, Sparkles, X } from 'lucide-react'
import { cn } from '@/lib/utils'
import { scriptsApi } from '@/api/scripts'
import { toast } from '@/lib/toast'
import type { ScriptTemplateDetail } from '@/types'
import type { SessionSuggestedFix } from '@/api/sessionSuggestedFixes'

interface TemplateMatchPanelProps {
  fix: SessionSuggestedFix
  sessionId: string
  onClose: () => void
}

interface ParamSchemaEntry {
  key: string
  label?: string
  field_type?: string
  variable_name?: string
  required?: boolean
  options?: Array<{ label: string; value: string }>
}

export function TemplateMatchPanel({ fix, sessionId, onClose }: TemplateMatchPanelProps) {
  const [template, setTemplate] = useState<ScriptTemplateDetail | null>(null)
  const [templateLoading, setTemplateLoading] = useState(true)
  const [templateError, setTemplateError] = useState<string | null>(null)
  const [params, setParams] = useState<Record<string, string>>({})
  const [generated, setGenerated] = useState<string | null>(null)
  const [generating, setGenerating] = useState(false)
  const [copied, setCopied] = useState(false)

  const aiPrefilled: Record<string, string> = {}
  if (fix.ai_drafted_parameters) {
    for (const [k, v] of Object.entries(fix.ai_drafted_parameters)) {
      if (typeof v === 'string') aiPrefilled[k] = v
    }
  }

  useEffect(() => {
    if (!fix.script_template_id) return
    setTemplateLoading(true)
    setTemplateError(null)
    scriptsApi
      .getTemplateDetail(fix.script_template_id)
      .then((tpl) => {
        setTemplate(tpl)
        // Seed params from AI's pre-fill, then template defaults for any
        // unset keys so required fields get a starting value.
        const seeded: Record<string, string> = { ...aiPrefilled }
        const defaults = (tpl as { default_values?: Record<string, unknown> }).default_values ?? {}
        for (const [k, v] of Object.entries(defaults)) {
          if (seeded[k] === undefined && typeof v === 'string') {
            seeded[k] = v
          }
        }
        setParams(seeded)
      })
      .catch((err: unknown) => {
        const status = (err as { response?: { status?: number } })?.response?.status
        // Phase 5 edge case: template was deleted between SUGGEST_FIX emission
        // and the engineer clicking it. The doc says fall back to the
        // three-option dialog with the AI-drafted script — surface that to
        // the parent so it can swap UIs.
        if (status === 404) setTemplateError('template_deleted')
        else setTemplateError('Could not load template')
      })
      .finally(() => setTemplateLoading(false))
  }, [fix.script_template_id]) // eslint-disable-line react-hooks/exhaustive-deps

  const handleGenerate = async () => {
    if (!fix.script_template_id) return
    setGenerating(true)
    try {
      const result = await scriptsApi.generate({
        template_id: fix.script_template_id,
        parameters: params,
        ai_session_id: sessionId,
      })
      setGenerated(result.script)
    } catch {
      toast.error('Failed to generate script')
    } finally {
      setGenerating(false)
    }
  }

  const handleCopy = async () => {
    if (!generated) return
    await navigator.clipboard.writeText(generated)
    setCopied(true)
    toast.success('Script copied to clipboard')
    setTimeout(() => setCopied(false), 1500)
  }

  const paramSchema = (template?.parameters_schema?.parameters as ParamSchemaEntry[] | undefined) ?? []

  if (templateError === 'template_deleted') {
    return (
      <div className="rounded-lg border border-warning/40 bg-warning-dim/15 mx-3 mb-3 p-3">
        <div className="flex items-center justify-between mb-1">
          <span className="text-[0.75rem] font-semibold text-warning">
            Template no longer in library
          </span>
          <button onClick={onClose} className="text-muted-foreground hover:text-heading" title="Close">
            <X size={11} />
          </button>
        </div>
        <p className="text-[0.75rem] text-muted-foreground leading-relaxed">
          The template the AI suggested was deleted. Switch to the no-template
          flow to use the drafted script instead.
        </p>
      </div>
    )
  }

  return (
    <div className="rounded-lg border border-success/40 bg-bg-page mx-3 mb-3 overflow-hidden shadow-lg">
      <div className="flex items-center justify-between px-3 py-2 border-b border-default">
        <div className="flex items-center gap-2">
          <ShieldCheck size={13} className="text-success" />
          <span className="text-[0.75rem] font-semibold text-heading">Verified template</span>
          {template && (
            <span className="text-[0.6875rem] font-mono text-muted-foreground">
              {template.slug}
            </span>
          )}
        </div>
        <button
          onClick={onClose}
          disabled={generating}
          className="p-1 rounded text-muted-foreground hover:text-heading hover:bg-elevated/40 transition-colors"
          title="Close panel"
        >
          <X size={11} />
        </button>
      </div>

      <div className="p-3 space-y-3">
        {templateLoading && (
          <div className="flex items-center gap-2 text-[0.75rem] text-muted-foreground">
            <Loader2 size={12} className="animate-spin" /> Loading template...
          </div>
        )}
        {templateError && templateError !== 'template_deleted' && (
          <div className="text-[0.75rem] text-danger">{templateError}</div>
        )}

        {template && !generated && (
          <>
            <div className="text-[0.75rem] text-muted-foreground leading-relaxed">
              {template.description ?? fix.description}
            </div>

            <div className="space-y-2">
              {paramSchema.map((p) => {
                const key = p.key || p.variable_name || ''
                if (!key) return null
                const isPrefilled = aiPrefilled[key] !== undefined
                const value = params[key] ?? ''
                const isPassword = p.field_type === 'password'
                return (
                  <div key={key}>
                    <div className="flex items-center justify-between mb-1">
                      <label className="text-[0.6875rem] font-semibold text-heading">
                        {p.label || key}
                        {p.required && <span className="text-danger">*</span>}
                      </label>
                      {isPrefilled && (
                        <span className="flex items-center gap-1 text-[0.625rem] font-semibold uppercase tracking-wider text-accent">
                          <Sparkles size={9} /> from session
                        </span>
                      )}
                    </div>
                    <input
                      type={isPassword ? 'password' : 'text'}
                      value={value}
                      onChange={(e) => setParams((prev) => ({ ...prev, [key]: e.target.value }))}
                      className={cn(
                        'w-full rounded-md border px-2.5 py-1.5 text-[0.8125rem] text-heading focus:outline-none focus:ring-1',
                        isPrefilled
                          ? 'border-accent/40 bg-accent-dim/15 focus:border-accent focus:ring-accent/30'
                          : 'border-default bg-input focus:border-accent focus:ring-accent/30',
                      )}
                    />
                    {isPrefilled && (
                      <div className="mt-0.5 text-[0.625rem] text-accent-text italic">
                        Pulled from session context
                      </div>
                    )}
                  </div>
                )
              })}
            </div>

            <button
              onClick={handleGenerate}
              disabled={generating}
              className="w-full flex items-center justify-center gap-1.5 rounded-md bg-accent px-4 py-2 text-[0.8125rem] font-semibold text-white hover:bg-accent-hover transition-colors disabled:opacity-50"
            >
              {generating ? (
                <><Loader2 size={12} className="animate-spin" /> Generating...</>
              ) : (
                'Generate script'
              )}
            </button>
          </>
        )}

        {generated && (
          <>
            <pre className="text-[0.75rem] font-mono text-heading whitespace-pre-wrap overflow-x-auto rounded-lg border border-default bg-code px-3 py-2.5 max-h-[40vh] leading-relaxed">
              {generated}
            </pre>
            <div className="flex items-center gap-2">
              <button
                onClick={handleCopy}
                className="flex items-center gap-1.5 rounded-md bg-accent px-3 py-1.5 text-[0.75rem] font-semibold text-white hover:bg-accent-hover transition-colors"
              >
                {copied ? <Check size={11} /> : <Copy size={11} />} Copy
              </button>
              <button
                onClick={() => setGenerated(null)}
                className="text-[0.75rem] text-muted-foreground hover:text-heading"
              >
                Edit parameters
              </button>
            </div>
          </>
        )}
      </div>
    </div>
  )
}

export default TemplateMatchPanel
