import { useState, useEffect } from 'react'
import type { Question } from '@/types/questions'
import { questionToJson, questionFromJson } from '@/types/questions'
import { Label } from '@/components/ui/label'
import { Textarea } from '@/components/ui/textarea'
import { Button } from '@/components/ui/button'
import { Alert, AlertDescription } from '@/components/ui/alert'
import { AlertCircle } from 'lucide-react'

interface JSONQuestionEditorProps {
  question: Partial<Question> | null
  onChange: (question: Partial<Question> | null, isValid: boolean) => void
}

export function JSONQuestionEditor({
  question,
  onChange,
}: JSONQuestionEditorProps) {
  const [jsonText, setJsonText] = useState('')
  const [error, setError] = useState<string | null>(null)
  const [isValid, setIsValid] = useState(false)

  // Инициализация JSON из вопроса
  useEffect(() => {
    if (question) {
      try {
        const json = questionToJson(question as Question)
        setJsonText(JSON.stringify(json, null, 2))
        setError(null)
        setIsValid(true)
      } catch (e) {
        setError(`Failed to serialize question: ${e}`)
        setIsValid(false)
      }
    } else {
      setJsonText('')
      setError(null)
      setIsValid(false)
    }
  }, [question])

  // Валидация и парсинг JSON
  const handleJsonChange = (value: string) => {
    setJsonText(value)

    if (!value.trim()) {
      setError(null)
      setIsValid(false)
      onChange(null, false)
      return
    }

    try {
      const parsed: unknown = JSON.parse(value)
      if (!parsed || typeof parsed !== 'object') {
        throw new Error('JSON must be an object')
      }
      const obj = parsed as Record<string, unknown>

      // Базовая валидация структуры
      if (typeof obj.questionType !== 'string') {
        throw new Error('Missing required field: questionType')
      }
      const isMatrix = obj.questionType === 'matrix'

      if (!isMatrix && !obj.word) {
        throw new Error('Missing required field: word')
      }
      if (!isMatrix && !obj.answer) {
        throw new Error('Missing required field: answer')
      }
      if (!isMatrix && (!obj.buttons || !Array.isArray(obj.buttons))) {
        throw new Error('Missing or invalid field: buttons (must be an array)')
      }
      if (isMatrix && obj.matrixSize == null) {
        throw new Error('Missing required field for matrix: matrixSize')
      }

      // Проверка что answer существует в buttons
      if (!isMatrix) {
        const buttons = Array.isArray(obj.buttons) ? obj.buttons : []
        const buttonIds = buttons
          .map((b) => {
            const bObj: Record<string, unknown> =
              b && typeof b === 'object' ? (b as Record<string, unknown>) : {}
            return typeof bObj.id === 'string' ? bObj.id : undefined
          })
          .filter((id): id is string => typeof id === 'string')

        if (typeof obj.answer === 'string' && !buttonIds.includes(obj.answer)) {
          throw new Error(
            `Answer "${obj.answer}" not found in buttons. Available IDs: ${buttonIds.join(', ')}`,
          )
        }
      }

      // Проверка для input_buttons
      if (obj.questionType === 'input_buttons' && !obj.template) {
        throw new Error('Missing required field for input_buttons: template')
      }

      // Парсинг в Question объект
      const questionObj = questionFromJson(obj)
      setError(null)
      setIsValid(true)
      onChange(questionObj, true)
    } catch (e) {
      const errorMessage = e instanceof Error ? e.message : 'Invalid JSON'
      setError(errorMessage)
      setIsValid(false)
      onChange(null, false)
    }
  }

  // Форматирование JSON
  const formatJson = () => {
    try {
      const parsed = JSON.parse(jsonText)
      setJsonText(JSON.stringify(parsed, null, 2))
      handleJsonChange(JSON.stringify(parsed, null, 2))
    } catch {
      // Если невалидный JSON, просто показываем ошибку
    }
  }

  return (
    <div className="space-y-4">
      <div className="flex items-center justify-between">
        <Label>JSON Editor</Label>
        <Button type="button" variant="outline" size="sm" onClick={formatJson}>
          Format JSON
        </Button>
      </div>

      <Textarea
        value={jsonText}
        onChange={(e) => handleJsonChange(e.target.value)}
        placeholder='{"questionType": "simple", "word": "...", "answer": "...", "buttons": [...]}'
        rows={20}
        className="font-mono text-sm"
      />

      {error && (
        <Alert variant="destructive">
          <AlertCircle className="h-4 w-4" />
          <AlertDescription>{error}</AlertDescription>
        </Alert>
      )}

      {isValid && !error && (
        <Alert>
          <AlertCircle className="h-4 w-4" />
          <AlertDescription>JSON is valid</AlertDescription>
        </Alert>
      )}

      <div className="text-xs text-muted-foreground">
        <p className="font-semibold mb-1">Required fields:</p>
        <ul className="list-disc list-inside space-y-1">
          <li>
            <code>questionType</code>: "simple" or "input_buttons"
          </li>
          <li>
            <code>questionType</code>: "matrix" (requires <code>matrixSize</code>)
          </li>
          <li>
            <code>word</code>: Word or phrase to learn
          </li>
          <li>
            <code>answer</code>: ID of the correct button
          </li>
          <li>
            <code>buttons</code>: Array of button objects with id, text/image
          </li>
          <li>
            <code>template</code>: Required for input_buttons type
          </li>
        </ul>
      </div>
    </div>
  )
}
