// export default PublishSeed;
import React, { useState, useRef, useEffect } from 'react';
import axios from 'axios';
import Header from '../../components/Header';
import './PublishSeed.css';
import { useUser } from '../../context/UserContext';
import { uploadFile } from '../../api/file';
import AuthButton from '../../components/AuthButton';

const PublishSeed = () => {
  const [title, setTitle] = useState('');
  const [description, setDescription] = useState('');
  const [tags, setTags] = useState([]);
  const [category, setCategory] = useState('movie');
  const [message, setMessage] = useState('');
  const [isLoading, setIsLoading] = useState(false);
  const [fileName, setFileName] = useState('');
  const [imageFile, setImageFile] = useState(null);
  const [previewUrl, setPreviewUrl] = useState('');

  const fileInputRef = useRef(null);
  const imageInputRef = useRef(null);
  const { user } = useUser();

  useEffect(() => {
    console.log('[DEBUG] 当前用户:', user);
  }, [user]);

  const handleTagsChange = (e) => {
    console.log('[DEBUG] 标签输入变化:', e.target.value);
    setTags(e.target.value.split(',').map(tag => tag.trim()).filter(Boolean));
  };

  const handleFileButtonClick = () => {
    console.log('[DEBUG] 触发文件选择按钮点击');
    fileInputRef.current?.click();
  };

  const handleImageButtonClick = () => {
    console.log('[DEBUG] 触发封面图片选择按钮点击');
    imageInputRef.current?.click();
  };

  const handleFileChange = (e) => {
    console.log('[DEBUG] 种子文件选择变化:', e.target.files);
    const selectedFile = e.target.files[0];
    if (selectedFile) {
      setFileName(selectedFile.name);
    }
  };

  const handleImageChange = (e) => {
    console.log('[DEBUG] 封面图片选择变化:', e.target.files);
    const img = e.target.files[0];
    if (!img) return;
    setImageFile(img);
    setPreviewUrl(URL.createObjectURL(img));
  };

  const handleSubmit = async (e) => {
    console.log('[DEBUG] handleSubmit 被触发', e);
    e.preventDefault();

    setIsLoading(true);
    setMessage('');

    const currentFile = fileInputRef.current?.files[0];
    console.log('[DEBUG] 当前选择文件:', currentFile);

    if (!user || !user.userId) {
      console.log('[DEBUG] 用户未登录，阻止上传');
      setMessage('请先登录');
      setIsLoading(false);
      return;
    }

    if (!currentFile || !currentFile.name.toLowerCase().endsWith('.torrent')) {
      console.log('[DEBUG] 文件校验失败');
      setMessage('请上传一个 .torrent 文件');
      setIsLoading(false);
      return;
    }

    const formData = new FormData();
    formData.append('file', currentFile);
    formData.append('title', title);
    formData.append('description', description);
    formData.append('category', category);
    formData.append('tags', tags.join(',')); // 逗号分隔字符串
    formData.append('uploader', user.userId);
    if (imageFile) {
      formData.append('coverImage', imageFile);
    }

        try {
      console.log('[DEBUG] 发送上传请求...');
      const response = await axios.post('/seeds/upload', formData);

      console.log('[DEBUG] 请求成功，响应:', response.data);

      if (response.data.code === 0) {
        setMessage('种子上传成功');
      } else if (response.data.code === 401) {
        setMessage('未登录或登录已过期，请重新登录');
      } else {
        setMessage(response.data.message || '上传失败，请稍后再试');
      }
    } catch (error) {
      console.error('[handleSubmit] 上传失败:', error);

      if (error.response?.status === 401 || error.response?.data?.code === 401) {
        setMessage('未登录或登录已过期，请重新登录');
      } else {
        setMessage(error.response?.data?.msg || '上传失败，发生了错误');
      }
    } finally {
      setIsLoading(false);
    }

  };

  return (
    <div className="ps-container">
      <Header />
      <div className="ps-card">
        {message && <div className="ps-message">{message}</div>}
        <form
          className="ps-form"
          onSubmit={(e) => {
            console.log('[DEBUG] form onSubmit 触发');
            handleSubmit(e);
          }}
          encType="multipart/form-data"
        >
          <div>
            <label className="ps-label">标题</label>
            <input
              className="ps-input-text"
              type="text"
              value={title}
              onChange={(e) => {
                console.log('[DEBUG] 标题输入变化:', e.target.value);
                setTitle(e.target.value);
              }}
              required
            />
          </div>

          <div>
            <label className="ps-label">描述</label>
            <textarea
              className="ps-textarea"
              value={description}
              onChange={(e) => {
                console.log('[DEBUG] 描述输入变化:', e.target.value);
                setDescription(e.target.value);
              }}
              required
            />
          </div>

          <div>
            <label className="ps-label">标签 (逗号分隔)</label>
            <input
              className="ps-input-text"
              type="text"
              value={tags.join(', ')}
              onChange={handleTagsChange}
              placeholder="例如：科幻, 动作"
              required
            />
          </div>

          <div>
            <label className="ps-label">分类</label>
            <select
              className="ps-select"
              value={category}
              onChange={(e) => {
                console.log('[DEBUG] 分类选择变化:', e.target.value);
                setCategory(e.target.value);
              }}
              required
            >
              <option value="movie">电影</option>
              <option value="tv">电视剧</option>
              <option value="music">音乐</option>
              <option value="anime">动漫</option>
              <option value="game">游戏</option>
              <option value="variety">综艺</option>
              <option value="software">软件</option>
              <option value="sports">体育</option>
              <option value="study">学习</option>
              <option value="documentary">纪录片</option>
              <option value="other">其他</option>
            </select>
          </div>

          <div>
            <label className="ps-label">种子文件</label>
            <div
              className="ps-seed-file-label"
              onClick={handleFileButtonClick}
              style={{ cursor: 'pointer' }}
            >
              点击选择文件
            </div>
            <input
              type="file"
              accept=".torrent"
              ref={fileInputRef}
              onChange={handleFileChange}
              className="ps-seed-file-input"
            />
            {fileName && <div style={{ marginTop: '5px', color: '#5F4437' }}>{fileName}</div>}
          </div>

          <div>
            <label className="ps-label">封面图</label>
            <div>
              <button
                type="button"
                onClick={handleImageButtonClick}
                className="ps-cover-upload-button"
              >
                上传图片
              </button>
              <input
                type="file"
                accept="image/*"
                ref={imageInputRef}
                onChange={handleImageChange}
                className="ps-cover-upload-input"
              />
            </div>
            {previewUrl && (
              <div style={{ marginTop: '10px' }}>
                <img
                  src={previewUrl}
                  alt="封面预览"
                  className="ps-img-preview"
                />
              </div>
            )}
          </div>

          <div className="ps-upload-button">
            <AuthButton
              roles={["cookie", "chocolate", "ice-cream"]}
              type="submit"
              disabled={isLoading}
              onClick={() => console.log('[DEBUG] 上传按钮 onClick 触发')}
            >
              {isLoading ? '正在上传...' : '上传种子'}
            </AuthButton>
          </div>
        </form>
      </div>
    </div>
  );
};

export default PublishSeed;
