import { useState, useMemo, useRef } from "react"
import { useQuery, useMutation, useQueryClient } from "@tanstack/react-query"
import { api } from "../lib/api"
import { EmptyState } from "../components/EmptyState"
import { LoadingSpinner } from "../components/LoadingSpinner"
import { SuggestionInput } from "../components/SuggestionInput"
import type { TimeEntryInsert, SavedView } from "@emberclone/shared"

function renderSimpleMarkdown(text: string | null) {
  if (!text) return null
  return text
    .split('\n')
    .map((line, i) => (
      <div key={i} className="mb-1">
        {line
          .replace(/\*\*(.*?)\*\*/g, '<strong>$1</strong>')
          .replace(/\*(.*?)\*/g, '<em>$1</em>')}
      </div>
    ))
}

export default function TimeEntries() {
  const queryClient = useQueryClient()
  const fileInputRef = useRef<HTMLInputElement>(null)
  
  const [formData, setFormData] = useState({
    description: "",
    startTime: "",
    endTime: "",
    projectId: "",
    notes: ""
  })

  const [filters, setFilters] = useState({
    search: "",
    from: "",
    to: ""
  })

  const [selectedIds, setSelectedIds] = useState<string[]>([])
  const [expandedRows, setExpandedRows] = useState<Record<string, boolean>>({})

  const { data: entries, isLoading, isError } = useQuery({
    queryKey: ["time-entries", filters.from, filters.to],
    queryFn: () => api.listTimeEntries({ 
      from: filters.from || undefined, 
      to: filters.to || undefined 
    })
  })

  const { data: savedViews } = useQuery({
    queryKey: ["saved-views", "time-entries"],
    queryFn: () => api.listSavedViews({ entityType: 'time-entries' })
  })

  const descriptionSuggestions = useMemo(() => {
    if (!entries) return []
    return Array.from(new Set(entries.map(e => e.description).filter(Boolean))).slice(0, 50) as string[]
  }, [entries])

  const createMutation = useMutation({
    mutationFn: (data: Partial<TimeEntryInsert>) => api.createTimeEntry(data),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["time-entries"] })
      setFormData({ description: "", startTime: "", endTime: "", projectId: "", notes: "" })
    }
  })

  const deleteMutation = useMutation({
    mutationFn: (id: string) => api.deleteTimeEntry(id),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["time-entries"] })
    }
  })

  const bulkDeleteMutation = useMutation({
    mutationFn: (ids: string[]) => api.bulkDeleteTimeEntries(ids),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["time-entries"] })
      setSelectedIds([])
    }
  })

  const importMutation = useMutation({
    mutationFn: (file: File) => api.importTimeEntriesCsv(file),
    onSuccess: (data) => {
      alert(`Successfully imported ${data.count} entries.`)
      queryClient.invalidateQueries({ queryKey: ["time-entries"] })
    },
    onError: (error: any) => {
      alert(`Import failed: ${error.message || "Unknown error"}`)
    }
  })

  const saveViewMutation = useMutation({
    mutationFn: (view: { name: string, filters: any }) => api.createSavedView(view),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["saved-views", "time-entries"] })
    }
  })

  const deleteViewMutation = useMutation({
    mutationFn: (id: string) => api.deleteSavedView(id),
    onSuccess: () => {
      queryClient.invalidateQueries({ queryKey: ["saved-views", "time-entries"] })
    }
  })

  const filteredEntries = useMemo(() => {
    if (!entries) return []
    return entries.filter(entry => 
      entry.description?.toLowerCase().includes(filters.search.toLowerCase())
    )
  }, [entries, filters.search])

  const handleSubmit = (e: React.FormEvent) => {
    e.preventDefault()
    createMutation.mutate({
      description: formData.description,
      startTime: new Date(formData.startTime) as any,
      endTime: new Date(formData.endTime) as any,
      projectId: formData.projectId || undefined,
      notes: formData.notes || undefined
    })
  }

  const handleExport = () => {
    const params = new URLSearchParams()
    if (filters.from) params.append("from", filters.from)
    if (filters.to) params.append("to", filters.to)
    window.location.href = `/api/time-entries/export.csv?${params.toString()}`
  }

  if (isLoading) return <div className="p-8 flex justify-center"><LoadingSpinner /></div>
  if (isError) return <div className="p-8 text-red-500">Error loading time entries.</div>

  return (
    <div className="p-6 max-w-7xl mx-auto space-y-8">
      <div className="flex justify-between items-center">
        <h1 className="text-2xl font-bold">Time Entries</h1>
        <div className="flex gap-2">
          <button 
            onClick={() => fileInputRef.current?.click()}
            className="px-4 py-2 bg-gray-100 hover:bg-gray-200 rounded text-sm font-medium"
          >
            Import CSV
          </button>
          <input 
            type="file" 
            ref={fileInputRef} 
            className="hidden" 
            accept=".csv" 
            onChange={(e) => e.target.files?.[0] && importMutation.mutate(e.target.files[0])} 
          />
          <button 
            onClick={handleExport}
            className="px-4 py-2 bg-gray-100 hover:bg-gray-200 rounded text-sm font-medium"
          >
            Export CSV
          </button>
        </div>
      </div>

      <form onSubmit={handleSubmit} className="grid grid-cols-1 md:grid-cols-5 gap-4 p-4 bg-gray-50 rounded-lg border">
        <div className="md:col-span-2">
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">Description</label>
          <SuggestionInput 
            value={formData.description}
            onChange={(val) => setFormData(prev => ({ ...prev, description: val }))}
            suggestions={descriptionSuggestions}
            placeholder="What are you working on?"
          />
        </div>
        <div>
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">Start</label>
          <input 
            type="datetime-local" 
            className="w-full p-2 border rounded text-sm"
            value={formData.startTime}
            onChange={e => setFormData(prev => ({ ...prev, startTime: e.target.value }))}
            required
          />
        </div>
        <div>
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">End</label>
          <input 
            type="datetime-local" 
            className="w-full p-2 border rounded text-sm"
            value={formData.endTime}
            onChange={e => setFormData(prev => ({ ...prev, endTime: e.target.value }))}
            required
          />
        </div>
        <div className="flex items-end">
          <button 
            type="submit" 
            disabled={createMutation.isPending}
            className="w-full py-2 bg-blue-600 text-white rounded text-sm font-medium hover:bg-blue-700 disabled:opacity-50"
          >
            {createMutation.isPending ? "Saving..." : "Add Entry"}
          </button>
        </div>
        <div className="md:col-span-5">
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">Notes (Optional)</label>
          <textarea 
            className="w-full p-2 border rounded text-sm"
            rows={2}
            value={formData.notes}
            onChange={e => setFormData(prev => ({ ...prev, notes: e.target.value }))}
          />
        </div>
      </form>

      <div className="flex flex-wrap gap-4 items-end border-b pb-4">
        <div className="flex-1 min-w-[200px]">
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">Search</label>
          <input 
            type="text" 
            className="w-full p-2 border rounded text-sm"
            placeholder="Filter by description..."
            value={filters.search}
            onChange={e => setFilters(prev => ({ ...prev, search: e.target.value }))}
          />
        </div>
        <div>
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">From</label>
          <input 
            type="date" 
            className="p-2 border rounded text-sm"
            value={filters.from}
            onChange={e => setFilters(prev => ({ ...prev, from: e.target.value }))}
          />
        </div>
        <div>
          <label className="block text-xs font-semibold uppercase text-gray-500 mb-1">To</label>
          <input 
            type="date" 
            className="p-2 border rounded text-sm"
            value={filters.to}
            onChange={e => setFilters(prev => ({ ...prev, to: e.target.value }))}
          />
        </div>
      </div>

      {filteredEntries.length === 0 ? (
        <EmptyState message="No time entries found matching your filters." />
      ) : (
        <div className="overflow-x-auto">
          <table className="w-full text-left border-collapse">
            <thead>
              <tr className="border-b text-xs font-semibold uppercase text-gray-500">
                <th className="p-2 w-10">
                  <input 
                    type="checkbox" 
                    checked={selectedIds.length === filteredEntries.length}
                    onChange={e => {
                      if (e.target.checked) setSelectedIds(filteredEntries.map(en => en.id))
                      else setSelectedIds([])
                    }}
                  />
                </th>
                <th className="p-2">Description</th>
                <th className="p-2">Start</th>
                <th className="p-2">End</th>
                <th className="p-2">Duration</th>
                <th className="p-2 text-right">Actions</th>
              </tr>
            </thead>
            <tbody>
              {filteredEntries.map(entry => (
                <React.Fragment key={entry.id}>
                  <tr className="border-b hover:bg-gray-50 group">
                    <td className="p-2">
                      <input 
                        type="checkbox" 
                        checked={selectedIds.includes(entry.id)}
                        onChange={e => {
                          if (e.target.checked) setSelectedIds(prev => [...prev, entry.id])
                          else setSelectedIds(prev => prev.filter(id => id !== entry.id))
                        }}
                      />
                    </td>
                    <td className="p-2">
                      <div 
                        className="cursor-pointer font-medium" 
                        onClick={() => setExpandedRows(prev => ({ ...prev, [entry.id]: !prev[entry.id] }))}
                      >
                        {entry.description}
                      </div>
                    </td>
                    <td className="p-2 text-sm text-gray-600">{new Date(entry.startTime).toLocaleString()}</td>
                    <td className="p-2 text-sm text-gray-600">{new Date(entry.endTime).toLocaleString()}</td>
                    <td className="p-2 text-sm text-gray-600">
                      {((new Date(entry.endTime).getTime() - new Date(entry.startTime).getTime()) / (1000 * 60 * 60)).toFixed(2)}h
                    </td>
                    <td className="p-2 text-right">
                      <button 
                        onClick={() => deleteMutation.mutate(entry.id)}
                        className="text-red-500 opacity-0 group-hover:opacity-100 p-1 hover:bg-red-50 rounded"
                      >
                        Delete
                      </button>
                    </td>
                  </tr>
                  {expandedRows[entry.id] && (
                    <tr>
                      <td colSpan={6} className="p-4 bg-gray-50 border-b">
                        <div className="text-sm text-gray-700 max-w-3xl">
                          {renderSimpleMarkdown(entry.notes)}
                        </div>
                      </td>
                    </tr>
                  )}
                </React.Fragment>
              ))}
            </tbody>
          </table>
        </div>
      )}

      {selectedIds.length > 0 && (
        <div className="fixed bottom-8 left-1/2 -translate-x-1/2 bg-gray-900 text-white px-6 py-3 rounded-full shadow-xl flex items-center gap-4">
          <span className="text-sm">{selectedIds.length} entries selected</span>
          <button 
            onClick={() => {
              if (confirm(`Delete ${selectedIds.length} entries?`)) {
                bulkDeleteMutation.mutate(selectedIds)
              }
            }}
            className="text-sm bg-red-600 hover:bg-red-700 px-3 py-1 rounded font-medium"
          >
            Delete Selected
          </button>
        </div>
      )}
    </div>
  )
}