'use client';

import { useEffect, useState } from 'react';
import { useAction, useMutation, useQuery } from 'convex/react';
import { makeFunctionReference } from 'convex/server';
import { Brain } from 'lucide-react';
import { toast } from 'sonner';

import { api } from '@spoon/backend/convex/_generated/api.js';
import {
  Button,
  Card,
  CardContent,
  CardHeader,
  CardTitle,
  Input,
  Label,
  Select,
  SelectContent,
  SelectItem,
  SelectTrigger,
  SelectValue,
} from '@spoon/ui';

type ReasoningEffort = 'none' | 'minimal' | 'low' | 'medium' | 'high' | 'xhigh';

const saveOpenAiSettingsRef = makeFunctionReference<
  'action',
  { apiKey: string; model: string; reasoningEffort: ReasoningEffort },
  { success: true }
>('aiSettingsNode:saveOpenAiSettings');

const modelOptions = [
  { value: 'gpt-5.5', label: 'GPT-5.5' },
  { value: 'gpt-5.5-pro', label: 'GPT-5.5 Pro' },
  { value: 'gpt-5.4', label: 'GPT-5.4' },
  { value: 'gpt-5.4-mini', label: 'GPT-5.4 Mini' },
];

const reasoningOptions: { value: ReasoningEffort; label: string }[] = [
  { value: 'none', label: 'None' },
  { value: 'minimal', label: 'Minimal' },
  { value: 'low', label: 'Low' },
  { value: 'medium', label: 'Medium' },
  { value: 'high', label: 'High' },
  { value: 'xhigh', label: 'Extra high' },
];

export const OpenAiStatusPanel = () => {
  const status = useQuery(api.integrations.getStatus, {});
  const settings = useQuery(api.aiSettings.getMine, {});
  const saveOpenAiSettings = useAction(saveOpenAiSettingsRef);
  const updatePreferences = useMutation(api.aiSettings.updatePreferences);
  const removeOpenAiKey = useMutation(api.aiSettings.removeOpenAiKey);
  const [apiKey, setApiKey] = useState('');
  const [model, setModel] = useState('gpt-5.5');
  const [reasoningEffort, setReasoningEffort] =
    useState<ReasoningEffort>('medium');
  const [submitting, setSubmitting] = useState(false);

  useEffect(() => {
    if (!settings) return;
    setModel(settings.model);
    setReasoningEffort(settings.reasoningEffort as ReasoningEffort);
  }, [settings]);

  const save = async (event: React.FormEvent<HTMLFormElement>) => {
    event.preventDefault();
    setSubmitting(true);
    try {
      if (apiKey.trim()) {
        await saveOpenAiSettings({
          apiKey,
          model,
          reasoningEffort,
        });
        setApiKey('');
      } else {
        await updatePreferences({
          model,
          reasoningEffort,
        });
      }
      toast.success('OpenAI settings saved.');
    } catch (error) {
      console.error(error);
      toast.error('Could not save OpenAI settings.');
    } finally {
      setSubmitting(false);
    }
  };

  const remove = async () => {
    try {
      await removeOpenAiKey({});
      toast.success('OpenAI API key removed.');
    } catch (error) {
      console.error(error);
      toast.error('Could not remove OpenAI API key.');
    }
  };

  return (
    <Card className='shadow-none'>
      <CardHeader>
        <CardTitle className='flex items-center gap-2 text-base'>
          <Brain className='size-4' />
          OpenAI reviews
        </CardTitle>
      </CardHeader>
      <CardContent className='space-y-2 text-sm'>
        <p className='text-muted-foreground'>
          Compatibility reviews use your own OpenAI API key. Spoon encrypts the
          key before storing it and only shows a short preview.
        </p>
        <div>
          <p className='text-muted-foreground'>Encryption</p>
          <p className='font-medium'>
            {status?.encryptionConfigured ? 'Configured' : 'Missing server key'}
          </p>
        </div>
        <div>
          <p className='text-muted-foreground'>OpenAI API key</p>
          <p className='font-medium'>
            {settings?.configured ? settings.apiKeyPreview : 'Not configured'}
          </p>
        </div>
        <form onSubmit={save} className='space-y-4 pt-2'>
          <div className='grid gap-2'>
            <Label htmlFor='openai-api-key'>API key</Label>
            <Input
              id='openai-api-key'
              type='password'
              value={apiKey}
              placeholder={
                settings?.configured
                  ? 'Leave blank to keep current key'
                  : 'sk-...'
              }
              onChange={(event) => setApiKey(event.target.value)}
            />
          </div>
          <div className='grid gap-2 md:grid-cols-2'>
            <div className='grid gap-2'>
              <Label>Review model</Label>
              <Select value={model} onValueChange={(value) => setModel(value)}>
                <SelectTrigger>
                  <SelectValue />
                </SelectTrigger>
                <SelectContent>
                  {modelOptions.map((option) => (
                    <SelectItem key={option.value} value={option.value}>
                      {option.label}
                    </SelectItem>
                  ))}
                </SelectContent>
              </Select>
            </div>
            <div className='grid gap-2'>
              <Label>Thinking</Label>
              <Select
                value={reasoningEffort}
                onValueChange={(value) =>
                  setReasoningEffort(value as ReasoningEffort)
                }
              >
                <SelectTrigger>
                  <SelectValue />
                </SelectTrigger>
                <SelectContent>
                  {reasoningOptions.map((option) => (
                    <SelectItem key={option.value} value={option.value}>
                      {option.label}
                    </SelectItem>
                  ))}
                </SelectContent>
              </Select>
            </div>
          </div>
          <div className='flex flex-wrap gap-2'>
            <Button type='submit' disabled={submitting}>
              {submitting ? 'Saving...' : 'Save OpenAI settings'}
            </Button>
            <Button
              type='button'
              variant='outline'
              onClick={remove}
              disabled={!settings?.configured}
            >
              Remove key
            </Button>
          </div>
        </form>
      </CardContent>
    </Card>
  );
};
