"use client"

import { useEffect, useMemo, useState } from "react"
import { Button } from "@/components/ui/button"
import { Card, CardContent, CardHeader, CardTitle } from "@/components/ui/card"
import { Progress } from "@/components/ui/progress"
import { Alert, AlertDescription } from "@/components/ui/alert"
import { Upload, File as FileIcon, Loader2, ChevronDown, ChevronUp, X } from "lucide-react"
import { getApiUrl } from "@/config/backend"

interface JobStatus {
  job_id: string
  stage: string
  status_message?: string | null
  processed_files: number
  total_files: number
  error?: string | null
}

const STAGE_COPY: Record<string, string> = {
  received: "Job received",
  saving_files: "Saving files",
  extracting: "Extracting document content",
  analyzing: "Calling Claude for causal relations",
  building_graph: "Writing to Neo4j knowledge graph",
  completed: "Completed",
  failed: "Failed",
}

interface MultiDocsUploadInlineProps {
  onJobCreated?: (jobId: string) => void
}

// Default export for easier importing
export default MultiDocsUploadInline

export function MultiDocsUploadInline({ onJobCreated }: MultiDocsUploadInlineProps) {
  const [isExpanded, setIsExpanded] = useState(false)
  const [files, setFiles] = useState<File[]>([])
  const [uploading, setUploading] = useState(false)
  const [jobId, setJobId] = useState<string | null>(null)
  const [status, setStatus] = useState<JobStatus | null>(null)
  const [error, setError] = useState<string | null>(null)

  const uploadUrl = useMemo(() => getApiUrl("/api/multi-docs/jobs"), [])

  useEffect(() => {
    if (!jobId) return

    let cancelled = false
    const interval = setInterval(async () => {
      try {
        const response = await fetch(getApiUrl(`/api/multi-docs/jobs/${jobId}`))
        if (!response.ok) {
          throw new Error(`Status request failed with ${response.status}`)
        }
        const data = (await response.json()) as JobStatus
        if (!cancelled) {
          setStatus(data)
          if (data.stage === "completed" || data.stage === "failed") {
            clearInterval(interval)
            if (data.stage === "completed" && onJobCreated) {
              onJobCreated(jobId)
            }
          }
        }
      } catch (err: any) {
        if (!cancelled) {
          console.error("Failed to poll job status:", err)
          setError(err.message ?? "Failed to fetch job status")
          clearInterval(interval)
        }
      }
    }, 4000)

    return () => {
      cancelled = true
      clearInterval(interval)
    }
  }, [jobId, onJobCreated])

  const handleFileSelect = (event: React.ChangeEvent<HTMLInputElement>) => {
    if (!event.target.files) return
    const selected = Array.from(event.target.files)
    setFiles(prev => [...prev, ...selected])
  }

  const removeFile = (fileName: string) => {
    setFiles(prev => prev.filter(file => file.name !== fileName))
  }

  const startUpload = async () => {
    setError(null)
    if (files.length === 0) {
      setError("Please select at least one file.")
      return
    }

    const formData = new FormData()
    files.forEach(file => formData.append("files", file))

    setUploading(true)
    try {
      const response = await fetch(uploadUrl, {
        method: "POST",
        body: formData,
      })

      if (!response.ok) {
        let errorMessage = `Upload failed with ${response.status}`
        try {
          const errorData = await response.json()
          errorMessage = errorData.detail || errorData.message || errorMessage
        } catch {
          const text = await response.text()
          errorMessage = text || errorMessage
        }
        throw new Error(errorMessage)
      }

      const data = await response.json()
      setJobId(data.job_id)
      setStatus({
        job_id: data.job_id,
        stage: data.stage,
        total_files: data.total_files,
        processed_files: 0,
      })
      setUploading(false)
      setIsExpanded(true) // Keep expanded when upload starts
    } catch (err: any) {
      console.error("Upload failed:", err)
      setError(err.message ?? "Upload failed. Please try again.")
      setUploading(false)
    }
  }

  // Calculate progress based on stage and file processing
  const progressPercent = status
    ? (() => {
        // File extraction progress (0-30%)
        const fileProgress = status.total_files > 0
          ? Math.round((status.processed_files / status.total_files) * 30)
          : 0
        
        // Stage-based progress
        let stageProgress = 0
        if (status.stage === "saving_files") {
          stageProgress = 5
        } else if (status.stage === "extracting") {
          stageProgress = 10 + fileProgress // 10-40%
        } else if (status.stage === "analyzing") {
          // Analyzing takes the longest, show 40-85%
          stageProgress = 40 + Math.min(fileProgress * 1.5, 45) // 40-85%
        } else if (status.stage === "building_graph") {
          stageProgress = 85 + Math.min(fileProgress * 0.5, 10) // 85-95%
        } else if (status.stage === "completed") {
          stageProgress = 100
        } else if (status.stage === "failed") {
          stageProgress = fileProgress // Show progress up to failure point
        }
        
        return Math.min(stageProgress, 100)
      })()
    : 0

  const resetUpload = () => {
    setFiles([])
    setJobId(null)
    setStatus(null)
    setError(null)
    setUploading(false)
  }

  return (
    <Card className="bg-white/5 border border-white/10 rounded-xl">
      <CardHeader 
        className="cursor-pointer hover:bg-white/5 transition-colors"
        onClick={() => setIsExpanded(!isExpanded)}
      >
        <div className="flex items-center justify-between">
          <div className="flex items-center space-x-3">
            <Upload className="h-5 w-5 text-orange-400" />
            <CardTitle className="text-lg text-white">
              Upload Documents for Knowledge Graph
            </CardTitle>
          </div>
          <div className="flex items-center space-x-2">
            {status && status.stage === "completed" && (
              <span className="text-xs text-green-400 bg-green-400/10 px-2 py-1 rounded-full">
                Completed
              </span>
            )}
            {status && status.stage === "failed" && (
              <span className="text-xs text-red-400 bg-red-400/10 px-2 py-1 rounded-full">
                Failed
              </span>
            )}
            {isExpanded ? (
              <ChevronUp className="h-5 w-5 text-white/60" />
            ) : (
              <ChevronDown className="h-5 w-5 text-white/60" />
            )}
          </div>
        </div>
        <p className="text-sm text-white/60 mt-2">
          Upload documents to extract causal relationships and build a knowledge graph in Neo4j
        </p>
      </CardHeader>
      
      {isExpanded && (
        <CardContent className="space-y-4">
          {status?.stage === "completed" ? (
            <div className="space-y-3">
              <Alert className="bg-green-500/10 border border-green-500/40 text-green-200">
                <AlertDescription>
                  ✅ Knowledge graph created successfully! {status.total_files} file(s) processed.
                </AlertDescription>
              </Alert>
              <Button
                onClick={resetUpload}
                variant="outline"
                className="w-full border-white/20 text-white hover:bg-white/10"
              >
                Upload More Documents
              </Button>
            </div>
          ) : status?.stage === "failed" ? (
            <div className="space-y-3">
              <Alert variant="destructive" className="bg-red-500/10 border border-red-500/40 text-red-200">
                <AlertDescription>
                  {error || "Upload failed. Please try again."}
                </AlertDescription>
              </Alert>
              <Button
                onClick={resetUpload}
                variant="outline"
                className="w-full border-white/20 text-white hover:bg-white/10"
              >
                Try Again
              </Button>
            </div>
          ) : (
            <>
              <div className="border border-dashed border-orange-400/40 rounded-lg p-4 text-center bg-black/40">
                <input
                  id="multi-docs-input-inline"
                  type="file"
                  multiple
                  onChange={handleFileSelect}
                  className="hidden"
                  disabled={uploading}
                />
                <label 
                  htmlFor="multi-docs-input-inline" 
                  className={`flex flex-col items-center cursor-pointer space-y-2 ${uploading ? 'opacity-50 cursor-not-allowed' : ''}`}
                >
                  <Upload className="h-8 w-8 text-orange-400" />
                  <div>
                    <p className="font-semibold text-white text-sm">Click to select files</p>
                    <p className="text-xs text-white/60">
                      PDF, DOCX, PPT, XLS, JSON, XML, Markdown, images, audio/video
                    </p>
                  </div>
                </label>
              </div>

              {files.length > 0 && (
                <div className="bg-black/40 border border-white/10 rounded-lg p-3 space-y-2">
                  <p className="text-xs font-semibold text-white/70">Selected Files ({files.length})</p>
                  <ul className="space-y-1 max-h-32 overflow-y-auto">
                    {files.map(file => (
                      <li key={file.name} className="flex items-center justify-between text-xs text-white/80 bg-white/5 rounded px-2 py-1">
                        <span className="flex items-center gap-2">
                          <FileIcon className="h-3 w-3 text-orange-400" />
                          <span className="truncate max-w-[200px]">{file.name}</span>
                        </span>
                        <button
                          type="button"
                          className="text-orange-300 hover:text-orange-200"
                          onClick={(e) => {
                            e.stopPropagation()
                            removeFile(file.name)
                          }}
                          disabled={uploading}
                        >
                          <X className="h-3 w-3" />
                        </button>
                      </li>
                    ))}
                  </ul>
                </div>
              )}

              {error && (
                <Alert variant="destructive" className="bg-red-500/10 border border-red-500/40 text-red-200">
                  <AlertDescription className="text-xs">{error}</AlertDescription>
                </Alert>
              )}

              {status && (
                <div className="space-y-2">
                  <div className="flex items-center justify-between text-xs text-white/70">
                    <span>{STAGE_COPY[status.stage] || status.stage}</span>
                    <span>{progressPercent}%</span>
                  </div>
                  <Progress value={progressPercent} className="h-1.5" />
                  {status.status_message && (
                    <p className="text-xs text-white/60">{status.status_message}</p>
                  )}
                </div>
              )}

              <Button
                onClick={(e) => {
                  e.stopPropagation()
                  startUpload()
                }}
                className="w-full bg-orange-500 hover:bg-orange-600 text-black font-semibold"
                disabled={uploading || files.length === 0}
              >
                {uploading ? (
                  <>
                    <Loader2 className="mr-2 h-4 w-4 animate-spin" /> Uploading...
                  </>
                ) : (
                  <>
                    Start Upload <Upload className="ml-2 h-4 w-4" />
                  </>
                )}
              </Button>
            </>
          )}
        </CardContent>
      )}
    </Card>
  )
}

