import React, { useState, useEffect, useCallback, useMemo } from 'react';
import { useTranslation } from 'react-i18next';
import {
  Button,
  Form,
  Typography,
  Banner,
  Tabs,
  TabPane,
  Card,
  Input,
  InputNumber,
  Switch,
  TextArea,
  Row,
  Col,
  Divider,
  Tooltip,
} from '@douyinfe/semi-ui';
import {
  IconCode,
  IconPlus,
  IconDelete,
  IconRefresh,
  IconAlertTriangle,
} from '@douyinfe/semi-icons';

const { Text } = Typography;

const JSONEditor = ({
  value = '',
  onChange,
  field,
  label,
  placeholder,
  extraText,
  extraFooter,
  showClear = true,
  template,
  templateLabel,
  editorType = 'keyValue',
  rules = [],
  formApi = null,
  ...props
}) => {
  const { t } = useTranslation();

  // 将对象转换为键值对数组（包含唯一ID）
  const objectToKeyValueArray = useCallback((obj) => {
    if (!obj || typeof obj !== 'object') return [];
    return Object.entries(obj).map(([key, value], index) => ({
      id: `${Date.now()}_${index}_${Math.random()}`, // 唯一ID
      key,
      value
    }));
  }, []);

  // 将键值对数组转换为对象（重复键时后面的会覆盖前面的）
  const keyValueArrayToObject = useCallback((arr) => {
    const result = {};
    arr.forEach(item => {
      if (item.key) {
        result[item.key] = item.value;
      }
    });
    return result;
  }, []);

  // 初始化键值对数组
  const [keyValuePairs, setKeyValuePairs] = useState(() => {
    if (typeof value === 'string' && value.trim()) {
      try {
        const parsed = JSON.parse(value);
        return objectToKeyValueArray(parsed);
      } catch (error) {
        return [];
      }
    }
    if (typeof value === 'object' && value !== null) {
      return objectToKeyValueArray(value);
    }
    return [];
  });

  // 手动模式下的本地文本缓冲
  const [manualText, setManualText] = useState(() => {
    if (typeof value === 'string') return value;
    if (value && typeof value === 'object') return JSON.stringify(value, null, 2);
    return '';
  });

  // 根据键数量决定默认编辑模式
  const [editMode, setEditMode] = useState(() => {
    if (typeof value === 'string' && value.trim()) {
      try {
        const parsed = JSON.parse(value);
        const keyCount = Object.keys(parsed).length;
        return keyCount > 10 ? 'manual' : 'visual';
      } catch (error) {
        return 'manual';
      }
    }
    return 'visual';
  });
  
  const [jsonError, setJsonError] = useState('');

  // 计算重复的键
  const duplicateKeys = useMemo(() => {
    const keyCount = {};
    const duplicates = new Set();
    
    keyValuePairs.forEach(pair => {
      if (pair.key) {
        keyCount[pair.key] = (keyCount[pair.key] || 0) + 1;
        if (keyCount[pair.key] > 1) {
          duplicates.add(pair.key);
        }
      }
    });
    
    return duplicates;
  }, [keyValuePairs]);

  // 数据同步 - 当value变化时更新键值对数组
  useEffect(() => {
    try {
      let parsed = {};
      if (typeof value === 'string' && value.trim()) {
        parsed = JSON.parse(value);
      } else if (typeof value === 'object' && value !== null) {
        parsed = value;
      }
      
      // 只在外部值真正改变时更新，避免循环更新
      const currentObj = keyValueArrayToObject(keyValuePairs);
      if (JSON.stringify(parsed) !== JSON.stringify(currentObj)) {
        setKeyValuePairs(objectToKeyValueArray(parsed));
      }
      setJsonError('');
    } catch (error) {
      console.log('JSON解析失败:', error.message);
      setJsonError(error.message);
    }
  }, [value]);

  // 外部 value 变化时，若不在手动模式，则同步手动文本
  useEffect(() => {
    if (editMode !== 'manual') {
      if (typeof value === 'string') setManualText(value);
      else if (value && typeof value === 'object') setManualText(JSON.stringify(value, null, 2));
      else setManualText('');
    }
  }, [value, editMode]);

  // 处理可视化编辑的数据变化
  const handleVisualChange = useCallback((newPairs) => {
    setKeyValuePairs(newPairs);
    const jsonObject = keyValueArrayToObject(newPairs);
    const jsonString = Object.keys(jsonObject).length === 0 ? '' : JSON.stringify(jsonObject, null, 2);
    
    setJsonError('');

    // 通过formApi设置值
    if (formApi && field) {
      formApi.setValue(field, jsonString);
    }

    onChange?.(jsonString);
  }, [onChange, formApi, field, keyValueArrayToObject]);

  // 处理手动编辑的数据变化
  const handleManualChange = useCallback((newValue) => {
    setManualText(newValue);
    if (newValue && newValue.trim()) {
      try {
        const parsed = JSON.parse(newValue);
        setKeyValuePairs(objectToKeyValueArray(parsed));
        setJsonError('');
        onChange?.(newValue);
      } catch (error) {
        setJsonError(error.message);
      }
    } else {
      setKeyValuePairs([]);
      setJsonError('');
      onChange?.('');
    }
  }, [onChange, objectToKeyValueArray]);

  // 切换编辑模式
  const toggleEditMode = useCallback(() => {
    if (editMode === 'visual') {
      const jsonObject = keyValueArrayToObject(keyValuePairs);
      setManualText(Object.keys(jsonObject).length === 0 ? '' : JSON.stringify(jsonObject, null, 2));
      setEditMode('manual');
    } else {
      try {
        let parsed = {};
        if (manualText && manualText.trim()) {
          parsed = JSON.parse(manualText);
        } else if (typeof value === 'string' && value.trim()) {
          parsed = JSON.parse(value);
        } else if (typeof value === 'object' && value !== null) {
          parsed = value;
        }
        setKeyValuePairs(objectToKeyValueArray(parsed));
        setJsonError('');
        setEditMode('visual');
      } catch (error) {
        setJsonError(error.message);
        return;
      }
    }
  }, [editMode, value, manualText, keyValuePairs, keyValueArrayToObject, objectToKeyValueArray]);

  // 添加键值对
  const addKeyValue = useCallback(() => {
    const newPairs = [...keyValuePairs];
    const existingKeys = newPairs.map(p => p.key);
    let counter = 1;
    let newKey = `field_${counter}`;
    while (existingKeys.includes(newKey)) {
      counter += 1;
      newKey = `field_${counter}`;
    }
    newPairs.push({
      id: `${Date.now()}_${Math.random()}`,
      key: newKey,
      value: ''
    });
    handleVisualChange(newPairs);
  }, [keyValuePairs, handleVisualChange]);

  // 删除键值对
  const removeKeyValue = useCallback((id) => {
    const newPairs = keyValuePairs.filter(pair => pair.id !== id);
    handleVisualChange(newPairs);
  }, [keyValuePairs, handleVisualChange]);

  // 更新键名
  const updateKey = useCallback((id, newKey) => {
    const newPairs = keyValuePairs.map(pair => 
      pair.id === id ? { ...pair, key: newKey } : pair
    );
    handleVisualChange(newPairs);
  }, [keyValuePairs, handleVisualChange]);

  // 更新值
  const updateValue = useCallback((id, newValue) => {
    const newPairs = keyValuePairs.map(pair =>
      pair.id === id ? { ...pair, value: newValue } : pair
    );
    handleVisualChange(newPairs);
  }, [keyValuePairs, handleVisualChange]);

  // 填入模板
  const fillTemplate = useCallback(() => {
    if (template) {
      const templateString = JSON.stringify(template, null, 2);

      if (formApi && field) {
        formApi.setValue(field, templateString);
      }

      setManualText(templateString);
      setKeyValuePairs(objectToKeyValueArray(template));
      onChange?.(templateString);
      setJsonError('');
    }
  }, [template, onChange, formApi, field, objectToKeyValueArray]);

  // 渲染值输入控件（支持嵌套）
  const renderValueInput = (pairId, value) => {
    const valueType = typeof value;

    if (valueType === 'boolean') {
      return (
        <div className="flex items-center">
          <Switch
            checked={value}
            onChange={(newValue) => updateValue(pairId, newValue)}
          />
          <Text type="tertiary" className="ml-2">
            {value ? t('true') : t('false')}
          </Text>
        </div>
      );
    }

    if (valueType === 'number') {
      return (
        <InputNumber
          value={value}
          onChange={(newValue) => updateValue(pairId, newValue)}
          style={{ width: '100%' }}
          placeholder={t('输入数字')}
        />
      );
    }

    if (valueType === 'object' && value !== null) {
      // 简化嵌套对象的处理，使用TextArea
      return (
        <TextArea
          rows={2}
          value={JSON.stringify(value, null, 2)}
          onChange={(txt) => {
            try {
              const obj = txt.trim() ? JSON.parse(txt) : {};
              updateValue(pairId, obj);
            } catch {
              // 忽略解析错误
            }
          }}
          placeholder={t('输入JSON对象')}
        />
      );
    }

    // 字符串或其他原始类型
    return (
      <Input
        placeholder={t('参数值')}
        value={String(value)}
        onChange={(newValue) => {
          let convertedValue = newValue;
          if (newValue === 'true') convertedValue = true;
          else if (newValue === 'false') convertedValue = false;
          else if (!isNaN(newValue) && newValue !== '' && newValue !== '0') {
            const num = Number(newValue);
            // 检查是否为整数
            if (Number.isInteger(num)) {
              convertedValue = num;
            }
          }
          updateValue(pairId, convertedValue);
        }}
      />
    );
  };

  // 渲染键值对编辑器
  const renderKeyValueEditor = () => {
    return (
      <div className="space-y-1">
        {/* 重复键警告 */}
        {duplicateKeys.size > 0 && (
          <Banner
            type="warning"
            icon={<IconAlertTriangle />}
            description={
              <div>
                <Text strong>{t('存在重复的键名：')}</Text>
                <Text>{Array.from(duplicateKeys).join(', ')}</Text>
                <br />
                <Text type="tertiary" size="small">
                  {t('注意：JSON中重复的键只会保留最后一个同名键的值')}
                </Text>
              </div>
            }
            className="mb-3"
          />
        )}

        {keyValuePairs.length === 0 && (
          <div className="text-center py-6 px-4">
            <Text type="tertiary" className="text-gray-500 text-sm">
              {t('暂无数据，点击下方按钮添加键值对')}
            </Text>
          </div>
        )}

        {keyValuePairs.map((pair, index) => {
          const isDuplicate = duplicateKeys.has(pair.key);
          const isLastDuplicate = isDuplicate && 
            keyValuePairs.slice(index + 1).every(p => p.key !== pair.key);
          
          return (
            <Row key={pair.id} gutter={8} align="middle">
              <Col span={6}>
                <div className="relative">
                  <Input
                    placeholder={t('键名')}
                    value={pair.key}
                    onChange={(newKey) => updateKey(pair.id, newKey)}
                    status={isDuplicate ? 'warning' : undefined}
                  />
                  {isDuplicate && (
                    <Tooltip
                      content={
                        isLastDuplicate 
                          ? t('这是重复键中的最后一个，其值将被使用')
                          : t('重复的键名，此值将被后面的同名键覆盖')
                      }
                    >
                      <IconAlertTriangle
                        className="absolute right-2 top-1/2 transform -translate-y-1/2"
                        style={{ 
                          color: isLastDuplicate ? '#ff7d00' : '#faad14',
                          fontSize: '14px'
                        }}
                      />
                    </Tooltip>
                  )}
                </div>
              </Col>
              <Col span={16}>
                {renderValueInput(pair.id, pair.value)}
              </Col>
              <Col span={2}>
                <Button
                  icon={<IconDelete />}
                  type="danger"
                  theme="borderless"
                  onClick={() => removeKeyValue(pair.id)}
                  style={{ width: '100%' }}
                />
              </Col>
            </Row>
          );
        })}

        <div className="mt-2 flex justify-center">
          <Button
            icon={<IconPlus />}
            type="primary"
            theme="outline"
            onClick={addKeyValue}
          >
            {t('添加键值对')}
          </Button>
        </div>
      </div>
    );
  };

  // 渲染区域编辑器（特殊格式）- 也需要改造以支持重复键
  const renderRegionEditor = () => {
    const defaultPair = keyValuePairs.find(pair => pair.key === 'default');
    const modelPairs = keyValuePairs.filter(pair => pair.key !== 'default');

    return (
      <div className="space-y-2">
        {/* 重复键警告 */}
        {duplicateKeys.size > 0 && (
          <Banner
            type="warning"
            icon={<IconAlertTriangle />}
            description={
              <div>
                <Text strong>{t('存在重复的键名：')}</Text>
                <Text>{Array.from(duplicateKeys).join(', ')}</Text>
                <br />
                <Text type="tertiary" size="small">
                  {t('注意：JSON中重复的键只会保留最后一个同名键的值')}
                </Text>
              </div>
            }
            className="mb-3"
          />
        )}

        {/* 默认区域 */}
        <Form.Slot label={t('默认区域')}>
          <Input
            placeholder={t('默认区域，如: us-central1')}
            value={defaultPair ? defaultPair.value : ''}
            onChange={(value) => {
              if (defaultPair) {
                updateValue(defaultPair.id, value);
              } else {
                const newPairs = [...keyValuePairs, {
                  id: `${Date.now()}_${Math.random()}`,
                  key: 'default',
                  value: value
                }];
                handleVisualChange(newPairs);
              }
            }}
          />
        </Form.Slot>

        {/* 模型专用区域 */}
        <Form.Slot label={t('模型专用区域')}>
          <div>
            {modelPairs.map((pair) => {
              const isDuplicate = duplicateKeys.has(pair.key);
              return (
                <Row key={pair.id} gutter={8} align="middle" className="mb-2">
                  <Col span={10}>
                    <div className="relative">
                      <Input
                        placeholder={t('模型名称')}
                        value={pair.key}
                        onChange={(newKey) => updateKey(pair.id, newKey)}
                        status={isDuplicate ? 'warning' : undefined}
                      />
                      {isDuplicate && (
                        <Tooltip content={t('重复的键名')}>
                          <IconAlertTriangle
                            className="absolute right-2 top-1/2 transform -translate-y-1/2"
                            style={{ color: '#faad14', fontSize: '14px' }}
                          />
                        </Tooltip>
                      )}
                    </div>
                  </Col>
                  <Col span={12}>
                    <Input
                      placeholder={t('区域')}
                      value={pair.value}
                      onChange={(newValue) => updateValue(pair.id, newValue)}
                    />
                  </Col>
                  <Col span={2}>
                    <Button
                      icon={<IconDelete />}
                      type="danger"
                      theme="borderless"
                      onClick={() => removeKeyValue(pair.id)}
                      style={{ width: '100%' }}
                    />
                  </Col>
                </Row>
              );
            })}

            <div className="mt-2 flex justify-center">
              <Button
                icon={<IconPlus />}
                onClick={addKeyValue}
                type="primary"
                theme="outline"
              >
                {t('添加模型区域')}
              </Button>
            </div>
          </div>
        </Form.Slot>
      </div>
    );
  };

  // 渲染可视化编辑器
  const renderVisualEditor = () => {
    switch (editorType) {
      case 'region':
        return renderRegionEditor();
      case 'object':
      case 'keyValue':
      default:
        return renderKeyValueEditor();
    }
  };

  const hasJsonError = jsonError && jsonError.trim() !== '';

  return (
    <Form.Slot label={label}>
      <Card
        header={
          <div className="flex justify-between items-center">
            <Tabs
              type="slash"
              activeKey={editMode}
              onChange={(key) => {
                if (key === 'manual' && editMode === 'visual') {
                  setEditMode('manual');
                } else if (key === 'visual' && editMode === 'manual') {
                  toggleEditMode();
                }
              }}
            >
              <TabPane tab={t('可视化')} itemKey="visual" />
              <TabPane tab={t('手动编辑')} itemKey="manual" />
            </Tabs>

            {template && templateLabel && (
              <Button
                type="tertiary"
                onClick={fillTemplate}
                size="small"
              >
                {templateLabel}
              </Button>
            )}
          </div>
        }
        headerStyle={{ padding: '12px 16px' }}
        bodyStyle={{ padding: '16px' }}
        className="!rounded-2xl"
      >
        {/* JSON错误提示 */}
        {hasJsonError && (
          <Banner
            type="danger"
            description={`JSON 格式错误: ${jsonError}`}
            className="mb-3"
          />
        )}

        {/* 编辑器内容 */}
        {editMode === 'visual' ? (
          <div>
            {renderVisualEditor()}
            {/* 隐藏的Form字段用于验证和数据绑定 */}
            <Form.Input
              field={field}
              value={value}
              rules={rules}
              style={{ display: 'none' }}
              noLabel={true}
              {...props}
            />
          </div>
        ) : (
          <div>
            <TextArea
              placeholder={placeholder}
              value={manualText}
              onChange={handleManualChange}
              showClear={showClear}
              rows={Math.max(8, manualText ? manualText.split('\n').length : 8)}
            />
            {/* 隐藏的Form字段用于验证和数据绑定 */}
            <Form.Input
              field={field}
              value={value}
              rules={rules}
              style={{ display: 'none' }}
              noLabel={true}
              {...props}
            />
          </div>
        )}

        {/* 额外文本显示在卡片底部 */}
        {extraText && (
          <Divider margin='12px' align='center'>
            <Text type="tertiary" size="small">{extraText}</Text>
          </Divider>
        )}
        {extraFooter && (
          <div className="mt-1">
            {extraFooter}
          </div>
        )}
      </Card>
    </Form.Slot>
  );
};

export default JSONEditor;