import React, { useCallback, useEffect, useMemo, useRef, useState } from 'react';
import {
  Button,
  Card,
  Empty,
  Input,
  message,
  Modal,
  Select,
  Space,
  Table,
  Tag,
  Tooltip,
  Typography,
} from 'antd';
import {
  CheckCircleOutlined,
  ClockCircleOutlined,
  CloseCircleOutlined,
  EyeOutlined,
  FileImageOutlined,
  LoadingOutlined,
  PlayCircleOutlined,
  SearchOutlined,
  VideoCameraOutlined,
} from '@ant-design/icons';
import { getAdminGenerationAiTasks } from '../api';
import type { GenerationAIMediaReference, GenerationAITaskOut } from '../types';
import { formatDate } from '../utils/formatDate';

const RAW_API_BASE = import.meta.env.VITE_API_BASE || 'http://localhost:8000';
// 资源 URL 由后端返回相对路径，例如 /generate/images/xxx.png?exp=xxx&sign=xxx。
// 如果 VITE_API_BASE 被配置成 http://host/api 或 /api，这里会去掉 /api，避免拼成 /api/generate/xxx 导致 404。
const RESOURCE_BASE = RAW_API_BASE.replace(/\/api\/?$/i, '').replace(/\/$/, '');
const PAGE_SIZE = 20;

type ResourceState = 'empty' | 'checking' | 'valid' | 'invalid';

interface PreviewResourceState {
  image: ResourceState;
  video: ResourceState;
  videoCover: ResourceState;
  references: Record<string, ResourceState>;
}

const EMPTY_RESOURCE_STATE: PreviewResourceState = {
  image: 'empty',
  video: 'empty',
  videoCover: 'empty',
  references: {},
};

const STATUS_MAP: Record<string, { color: string; text: string; icon: React.ReactNode }> = {
  pending: { color: 'default', text: '待处理', icon: <ClockCircleOutlined /> },
  generating: { color: 'warning', text: '生成中', icon: <LoadingOutlined spin /> },
  completed: { color: 'success', text: '已完成', icon: <CheckCircleOutlined /> },
  failed: { color: 'error', text: '失败', icon: <CloseCircleOutlined /> },
};

const PIPELINE_STAGE_MAP: Record<string, string> = {
    timeout: '任务超时',
    queued: '已入队',
    preparing: '准备中',
    creating_provider_task: '创建任务中',
    waiting_remote: '等待生成',
    result_ready: '结果就绪',
    downloading: '下载中',
    done: '完成',
    download_failed: '下载失败',
    polling: '轮询中',
    failed: '失败',
};

const GEN_TYPE_MAP: Record<string, { text: string; color: string; icon: React.ReactNode }> = {
  image: { text: '图片', color: 'purple', icon: <FileImageOutlined /> },
  video: { text: '视频', color: 'geekblue', icon: <VideoCameraOutlined /> },
};

const isAbsoluteLikeUrl = (url: string): boolean => (
    /^(https?:)?\/\//i.test(url) || /^(blob|data):/i.test(url)
);

const isBlobUrl = (url?: string | null): boolean => !!url && /^blob:/i.test(url.trim());

const apiUrl = (url?: string | null): string => {
  if (!url) return '';
  const value = String(url).trim();
  if (!value) return '';
  if (isAbsoluteLikeUrl(value)) return value;

  if (!RESOURCE_BASE) {
    return value.startsWith('/') ? value : `/${value}`;
  }
  return `${RESOURCE_BASE}${value.startsWith('/') ? value : `/${value}`}`;
};

const truncateId = (value?: string | null): string => {
  if (!value) return '-';
  return value.length > 12 ? `${value.slice(0, 8)}...` : value;
};

const safeDate = (value?: string | null): string => {
  if (!value) return '-';
  return formatDate(value);
};

const isEmptyValue = (value: React.ReactNode): boolean => (
    value === null || value === undefined || value === ''
);

const isUrlExpired = (url?: string | null): boolean => {
  if (!url || isBlobUrl(url)) return false;

  try {
    const parsed = new URL(apiUrl(url), window.location.origin);
    const expireValue =
        parsed.searchParams.get('exp') ||
        parsed.searchParams.get('expires') ||
        parsed.searchParams.get('expire') ||
        parsed.searchParams.get('expires_at') ||
        parsed.searchParams.get('x-expires');

    if (!expireValue) return false;

    const expireNumber = Number(expireValue);
    if (!Number.isFinite(expireNumber)) return false;

    const expireMs = expireNumber > 10_000_000_000 ? expireNumber : expireNumber * 1000;
    return Date.now() >= expireMs;
  } catch {
    return false;
  }
};

const getInitialResourceState = (url?: string | null): ResourceState => {
  if (!url) return 'empty';
  if (isBlobUrl(url)) return 'invalid';
  if (isUrlExpired(url)) return 'invalid';
  return 'checking';
};

const getReferenceUrl = (ref: GenerationAIMediaReference): string | undefined => {
  const value = ref.url || ref.mediaUrl || ref.fileUrl;
  return typeof value === 'string' && value.trim() ? value.trim() : undefined;
};

const getReferenceType = (ref: GenerationAIMediaReference): string => {
  const rawType = String(ref.type || ref.mediaType || ref.mimeType || '').toLowerCase();
  const url = getReferenceUrl(ref)?.toLowerCase() || '';

  if (rawType.includes('video') || /\.(mp4|mov|webm|m4v)(\?|$)/i.test(url)) return 'video';
  if (rawType.includes('image') || /\.(png|jpe?g|webp|gif|bmp|svg)(\?|$)/i.test(url)) return 'image';
  return rawType || 'unknown';
};

const getReferenceKey = (ref: GenerationAIMediaReference, index: number): string => {
  const refUrl = getReferenceUrl(ref) || 'empty';
  return `${index}-${refUrl}`;
};

const getMediaInvalidText = (url?: string | null, type = '资源'): string => {
  if (isBlobUrl(url)) return '本地临时素材已失效';
  if (isUrlExpired(url)) return `${type}链接已超时，请刷新列表或重新搜索后再查看`;
  return `${type}加载失败，请刷新列表或重新搜索后再查看`;
};

const MediaPlaceholder: React.FC<{
  text: string;
  minHeight?: number;
  compact?: boolean;
  action?: React.ReactNode;
}> = ({ text, minHeight = 240, compact = false, action }) => (
    <div
        style={{
          width: '100%',
          minHeight: compact ? undefined : minHeight,
          height: compact ? '100%' : undefined,
          borderRadius: compact ? 10 : 12,
          background: '#f8f9fc',
          border: '1px dashed #cbd5e1',
          color: '#64748b',
          display: 'flex',
          alignItems: 'center',
          justifyContent: 'center',
          flexDirection: 'column',
          gap: compact ? 4 : 10,
          textAlign: 'center',
          // padding: compact ? 6 : 18,
        }}
    >
      <Typography.Text style={{ color: '#64748b', fontSize: compact ? 11 : 13 }}>{text}</Typography.Text>
      {action}
    </div>
);

const InfoItem: React.FC<{ label: string; value?: React.ReactNode }> = ({ label, value }) => (
    <div style={{ flex: 1, minWidth: 120 }}>
      <Typography.Text style={{ fontSize: 11, color: '#94a3b8', display: 'block' }}>{label}</Typography.Text>
      <Typography.Text strong style={{ fontSize: 14 }}>{isEmptyValue(value) ? '-' : value}</Typography.Text>
    </div>
);

const AdminGenerationAiRecords: React.FC = () => {
  const [records, setRecords] = useState<GenerationAITaskOut[]>([]);
  const [total, setTotal] = useState(0);
  const [loading, setLoading] = useState(false);
  const [page, setPage] = useState(1);

  const [filterStatus, setFilterStatus] = useState<string>('');
  const [filterGenType, setFilterGenType] = useState<string>('');
  const [inputUserId, setInputUserId] = useState<string>('');
  const [inputUserName, setInputUserName] = useState<string>('');
  const [queryUserId, setQueryUserId] = useState<string>('');
  const [queryUserName, setQueryUserName] = useState<string>('');
  const [reloadKey, setReloadKey] = useState(0);

  const [preview, setPreview] = useState<GenerationAITaskOut | null>(null);
  const [resourceState, setResourceState] = useState<PreviewResourceState>(EMPTY_RESOURCE_STATE);
  const [videoPlaying, setVideoPlaying] = useState(false);
  const videoRef = useRef<HTMLVideoElement | null>(null);

  const load = useCallback(async () => {
    setLoading(true);
    try {
      const res = await getAdminGenerationAiTasks({
        genType: filterGenType || undefined,
        status: filterStatus || undefined,
        userId: queryUserId || undefined,
        userName: queryUserName || undefined,
        page,
        pageSize: PAGE_SIZE,
      });
      setRecords(res.items || []);
      setTotal(res.total || 0);
    } catch (e: any) {
      message.error(e?.message || '加载创作记录失败');
    } finally {
      setLoading(false);
    }
  }, [filterGenType, filterStatus, page, queryUserId, queryUserName]);

  useEffect(() => {
    load();
  }, [load, reloadKey]);

  useEffect(() => {
    if (!preview) {
      setResourceState(EMPTY_RESOURCE_STATE);
      return;
    }

    const references = preview.mediaReferences || [];
    const initialReferences = references.reduce<Record<string, ResourceState>>((acc, ref, index) => {
      const refUrl = getReferenceUrl(ref);
      acc[getReferenceKey(ref, index)] = getInitialResourceState(refUrl);
      return acc;
    }, {});

    if (videoRef.current) {
      videoRef.current.pause();
      videoRef.current.currentTime = 0;
    }

    setVideoPlaying(false);
    setResourceState({
      image: getInitialResourceState(preview.imageUrl),
      video: getInitialResourceState(preview.videoUrl),
      videoCover: getInitialResourceState(preview.videoCoverUrl),
      references: initialReferences,
    });
  }, [preview]);

  const handleSearch = () => {
    setPage(1);
    setQueryUserId(inputUserId.trim());
    setQueryUserName(inputUserName.trim());
    setReloadKey((v) => v + 1);
  };

  const handleOpenPreview = useCallback((record: GenerationAITaskOut) => {
    setPreview(record);
  }, []);

  const handleClosePreview = () => {
    if (videoRef.current) {
      videoRef.current.pause();
    }
    setVideoPlaying(false);
    setPreview(null);
  };

  const patchResourceState = (patch: Partial<PreviewResourceState>) => {
    setResourceState((prev) => ({ ...prev, ...patch }));
  };

  const patchReferenceState = (key: string, state: ResourceState) => {
    setResourceState((prev) => ({
      ...prev,
      references: {
        ...prev.references,
        [key]: state,
      },
    }));
  };

  const handlePlayVideo = () => {
    if (!preview?.videoUrl) return;

    if (isUrlExpired(preview.videoUrl)) {
      patchResourceState({ video: 'invalid' });
      message.warning('视频链接已超时，请刷新列表或重新搜索后再查看');
      return;
    }

    setVideoPlaying(true);
    window.setTimeout(() => {
      videoRef.current?.play().catch(() => {
        setVideoPlaying(false);
        patchResourceState({ video: 'invalid' });
        message.warning('视频播放失败，请确认资源链接是否仍然有效');
      });
    }, 0);
  };

  const handleOpenExternalResource = (url?: string | null, type = '素材') => {
    if (!url) {
      message.warning(`${type}链接为空，暂无法查看`);
      return;
    }

    if (isBlobUrl(url)) {
      message.warning('本地临时素材已失效，暂无法查看');
      return;
    }

    if (isUrlExpired(url)) {
      message.warning(`${type}链接已超时，请刷新列表或重新搜索后再查看`);
      return;
    }

    window.open(apiUrl(url), '_blank', 'noopener,noreferrer');
  };

  const columns = useMemo(() => [
    {
      title: '用户', key: 'user', width: 150,
      render: (_: any, r: GenerationAITaskOut) => (
          <div>
            <Typography.Text strong style={{ fontSize: 13 }}>{r.userName || '未知用户'}</Typography.Text>
            <div style={{ fontSize: 11, color: '#94a3b8' }}>{truncateId(r.userId)}</div>
          </div>
      ),
    },
    {
      title: '类型', dataIndex: 'genType', width: 90,
      render: (v: string) => {
        const cfg = GEN_TYPE_MAP[v] || { text: v || '-', color: 'default', icon: null };
        return <Tag color={cfg.color} icon={cfg.icon}>{cfg.text}</Tag>;
      },
    },
    {
      title: '提示词', key: 'prompt', ellipsis: true,
      render: (_: any, r: GenerationAITaskOut) => (
          <Tooltip title={r.originalPrompt} placement="topLeft">
            <Typography.Text style={{ fontSize: 12, color: '#475569' }} ellipsis>
              {r.originalPrompt || '-'}
            </Typography.Text>
          </Tooltip>
      ),
    },
    {
      title: '参数', key: 'params', width: 180,
      render: (_: any, r: GenerationAITaskOut) => (
          r.genType === 'video' ? (
              r.duration || r.aspectRatio || r.resolution ? (
                  <Space size={4} wrap>
                    {r.duration ? <Tag>{r.duration}s</Tag> : null}
                    {r.aspectRatio ? <Tag>{r.aspectRatio}</Tag> : null}
                    {r.resolution ? <Tag>{r.resolution}</Tag> : null}
                  </Space>
              ) : <Tag color="default">无参数</Tag>
          ) : (
              r.imageSize || r.imageProportion || r.imagePx ? (
                  <Space size={4} wrap>
                    {r.imageSize ? <Tag>{r.imageSize}</Tag> : null}
                    {r.imageProportion ? <Tag>{r.imageProportion}</Tag> : null}
                    {r.imagePx ? <Tag>{r.imagePx}</Tag> : null}
                  </Space>
              ) : <Tag color="default">无参数</Tag>
          )
      ),
    },
    {
      title: '积分', key: 'credits', width: 130,
      render: (_: any, r: GenerationAITaskOut) => (
          <div style={{ fontSize: 12 }}>
            <div style={{ color: '#6366f1' }}>总: {r.creditsCost || 0}</div>
            {r.textCreditsCost > 0 ? <div style={{ color: '#f59e0b' }}>文字: {r.textCreditsCost}</div> : null}
          </div>
      ),
    },
    {
      title: '状态', dataIndex: 'status', width: 100,
      render: (v: string) => {
        const cfg = STATUS_MAP[v] || { color: 'default', text: v || '-', icon: null };
        return <Tag color={cfg.color} icon={cfg.icon}>{cfg.text}</Tag>;
      },
    },
    {
      title: '阶段', dataIndex: 'pipelineStage', width: 120,
      render: (v: string) => <Tag color="blue">{PIPELINE_STAGE_MAP[v] || v || '-'}</Tag>,
    },
    {
      title: '时间', key: 'time', width: 170,
      render: (_: any, r: GenerationAITaskOut) => (
          <div style={{ fontSize: 12, color: '#94a3b8' }}>
            <div>{safeDate(r.createdAt)}</div>
            {r.generatedAt ? <div style={{ color: '#10b981' }}>生成: {safeDate(r.generatedAt)}</div> : null}
          </div>
      ),
    },
    {
      title: '操作', key: 'action', width: 90, fixed: 'right' as const,
      render: (_: any, r: GenerationAITaskOut) => (
          <Button size="small" icon={<EyeOutlined />} onClick={() => handleOpenPreview(r)}>
            详情
          </Button>
      ),
    },
  ], [handleOpenPreview]);

  const previewTypeConfig = preview ? (GEN_TYPE_MAP[preview.genType] || { text: preview.genType || '-', color: 'default', icon: null }) : null;
  const previewStatusConfig = preview ? (STATUS_MAP[preview.status] || { color: 'default', text: preview.status || '-', icon: null }) : null;

  const renderResultImage = () => {
    if (!preview || preview.genType !== 'image' || preview.status !== 'completed') return null;

    if (!preview.imageUrl) {
      return <MediaPlaceholder text="此图片任务暂无结果图片" minHeight={260} />;
    }

    if (resourceState.image === 'invalid') {
      return <MediaPlaceholder text={getMediaInvalidText(preview.imageUrl, '图片')} minHeight={260} />;
    }

    const src = apiUrl(preview.imageUrl);

    return (
        <div
            style={{
              position: 'relative',
              width: '100%',
              minHeight: 260,
              borderRadius: 12,
              background: '#f8f9fc',
              border: '1px solid #e2e8f0',
              overflow: 'hidden',
              display: 'flex',
              alignItems: 'center',
              justifyContent: 'center',
            }}
        >
          <img
              key={`${preview.id}-${src}`}
              src={src}
              alt="生成图片"
              onLoad={() => patchResourceState({ image: 'valid' })}
              onError={() => patchResourceState({ image: 'invalid' })}
              style={{
                display: resourceState.image === 'valid' ? 'block' : 'none',
                width: '100%',
                maxHeight: 560,
                objectFit: 'contain',
                background: '#fff',
              }}
          />
          {resourceState.image === 'checking' ? (
              <MediaPlaceholder text="图片加载检测中..." minHeight={260} />
          ) : null}
        </div>
    );
  };

  const renderVideoMask = () => {
    if (!preview || videoPlaying || resourceState.video === 'invalid') return null;

    const canPlay = !!preview.videoUrl;
    const playButton = canPlay ? (
        <Button
            type="primary"
            shape="circle"
            size="large"
            icon={<PlayCircleOutlined />}
            onClick={handlePlayVideo}
            style={{ boxShadow: '0 8px 20px rgba(15,23,42,0.25)' }}
        />
    ) : null;

    if (!preview.videoCoverUrl) {
      return (
          <div
              style={{
                  position: 'absolute',
                  inset: 0,
                  borderRadius: 12,
                  overflow: 'hidden',
                  background: '#f8f9fc',
                  display: 'flex',
                  alignItems: 'center',
                  justifyContent: 'center',
              }}
          >
              <MediaPlaceholder text="此视频无封面" minHeight={340} action={playButton} />
          </div>
      );
    }

    if (resourceState.videoCover === 'invalid') {
      return <MediaPlaceholder text={getMediaInvalidText(preview.videoCoverUrl, '视频封面')} minHeight={340} action={playButton} />;
    }

    const coverSrc = apiUrl(preview.videoCoverUrl);

    return (
        <div
            style={{
              position: 'absolute',
              inset: 0,
              borderRadius: 12,
              overflow: 'hidden',
              background: '#f8f9fc',
              border: '1px solid #e2e8f0',
              display: 'flex',
              alignItems: 'center',
              justifyContent: 'center',
            }}
        >
          <img
              key={`${preview.id}-cover-${coverSrc}`}
              src={coverSrc}
              alt="视频封面"
              onLoad={() => patchResourceState({ videoCover: 'valid' })}
              onError={() => patchResourceState({ videoCover: 'invalid' })}
              style={{
                display: resourceState.videoCover === 'valid' ? 'block' : 'none',
                width: '100%',
                height: '100%',
                objectFit: 'contain',
                background: '#000',
              }}
          />

          {resourceState.videoCover === 'checking' ? (
              <MediaPlaceholder text="视频封面加载检测中..." minHeight={340} action={playButton} />
          ) : null}

          {resourceState.videoCover === 'valid' ? (
              <div
                  style={{
                    position: 'absolute',
                    inset: 0,
                    display: 'flex',
                    alignItems: 'center',
                    justifyContent: 'center',
                    background: 'rgba(15,23,42,0.18)',
                  }}
              >
                {playButton}
              </div>
          ) : null}
        </div>
    );
  };

  const renderResultVideo = () => {
    if (!preview || preview.genType !== 'video' || preview.status !== 'completed') return null;

    if (!preview.videoUrl) {
      return <MediaPlaceholder text="此视频任务暂无结果视频" minHeight={340} />;
    }

    if (resourceState.video === 'invalid') {
      return <MediaPlaceholder text={getMediaInvalidText(preview.videoUrl, '视频')} minHeight={340} />;
    }

    const videoSrc = apiUrl(preview.videoUrl);

    return (
        <div
            style={{
              position: 'relative',
              width: '100%',
              height: 340,
              borderRadius: 12,
              background: '#000',
              overflow: 'hidden',
              border: '1px solid #e2e8f0',
            }}
        >
          <video
              key={`${preview.id}-${videoSrc}`}
              ref={videoRef}
              src={videoSrc}
              preload="metadata"
              controls={videoPlaying}
              onLoadedMetadata={() => patchResourceState({ video: 'valid' })}
              onCanPlay={() => patchResourceState({ video: 'valid' })}
              onPlaying={() => {
                setVideoPlaying(true);
                patchResourceState({ video: 'valid' });
              }}
              onPause={() => setVideoPlaying(false)}
              onEnded={() => setVideoPlaying(false)}
              onError={() => {
                setVideoPlaying(false);
                patchResourceState({ video: 'invalid' });
              }}
              style={{
                width: '100%',
                height: '100%',
                objectFit: 'contain',
                background: '#000',
                opacity: videoPlaying ? 1 : 0,
                pointerEvents: videoPlaying ? 'auto' : 'none',
              }}
          />
          {renderVideoMask()}
        </div>
    );
  };

  const renderReferenceTile = (ref: GenerationAIMediaReference, index: number) => {
    const refUrl = getReferenceUrl(ref);
    const refType = getReferenceType(ref);
    const refKey = getReferenceKey(ref, index);
    const state = resourceState.references[refKey] || getInitialResourceState(refUrl);
    const isImage = refType === 'image';
    const isVideo = refType === 'video';
    const title = typeof ref.name === 'string' && ref.name ? ref.name : `参考素材 ${index + 1}`;

    if (!refUrl) {
      return (
          <div key={refKey} style={{ width: 94 }}>
            <div style={{ width: 94, height: 94 }}>
              <MediaPlaceholder text="无链接" compact />
            </div>
            <Typography.Text ellipsis style={{ display: 'block', marginTop: 4, fontSize: 11, color: '#94a3b8' }}>{title}</Typography.Text>
          </div>
      );
    }

    if (state === 'invalid') {
      return (
          <div key={refKey} style={{ width: 94 }}>
            <div style={{ width: 94, height: 94 }}>
              <MediaPlaceholder text={isBlobUrl(refUrl) ? '本地临时素材已失效' : '素材不可访问'} compact />
            </div>
            <Tooltip title={title}>
              <Typography.Text ellipsis style={{ display: 'block', marginTop: 4, fontSize: 11, color: '#94a3b8' }}>{title}</Typography.Text>
            </Tooltip>
          </div>
      );
    }

    const src = apiUrl(refUrl);

    return (
        <div key={refKey} style={{ width: 94 }}>
          <div
              role="button"
              tabIndex={0}
              title="点击新页面查看素材"
              onClick={() => handleOpenExternalResource(refUrl, isVideo ? '视频素材' : isImage ? '图片素材' : '素材')}
              onKeyDown={(e) => {
                if (e.key === 'Enter') handleOpenExternalResource(refUrl, isVideo ? '视频素材' : isImage ? '图片素材' : '素材');
              }}
              style={{
                width: 94,
                height: 94,
                borderRadius: 10,
                overflow: 'hidden',
                border: '1px solid #e2e8f0',
                background: '#f8f9fc',
                position: 'relative',
                display: 'flex',
                alignItems: 'center',
                justifyContent: 'center',
                cursor: 'pointer',
              }}
          >
            {isImage ? (
                <img
                    src={src}
                    alt={title}
                    onLoad={() => patchReferenceState(refKey, 'valid')}
                    onError={() => patchReferenceState(refKey, 'invalid')}
                    style={{
                      display: state === 'valid' ? 'block' : 'none',
                      width: '100%',
                      height: '100%',
                      objectFit: 'cover',
                    }}
                />
            ) : null}

            {isVideo ? (
                <>
                  <video
                      src={src}
                      preload="metadata"
                      onLoadedMetadata={() => patchReferenceState(refKey, 'valid')}
                      onError={() => patchReferenceState(refKey, 'invalid')}
                      style={{ display: 'none' }}
                  />
                  <div style={{ color: '#64748b', fontSize: 12, textAlign: 'center' }}>
                    <PlayCircleOutlined style={{ fontSize: 18 }} />
                    <div>视频素材</div>
                    <div style={{ fontSize: 10, color: '#94a3b8', marginTop: 2 }}>点击查看</div>
                  </div>
                </>
            ) : null}

            {!isImage && !isVideo ? (
                <div style={{ color: '#64748b', fontSize: 12, textAlign: 'center' }}>
                  文件素材
                  <div style={{ fontSize: 10, color: '#94a3b8', marginTop: 2 }}>点击查看</div>
                </div>
            ) : null}

            {state === 'checking' && isImage ? (
                <div
                    style={{
                      position: 'absolute',
                      inset: 0,
                      display: 'flex',
                      alignItems: 'center',
                      justifyContent: 'center',
                      background: '#f8f9fc',
                    }}
                >
                  <LoadingOutlined style={{ color: '#6366f1' }} />
                </div>
            ) : null}
          </div>
          <Tooltip title={title}>
            <Typography.Text ellipsis style={{ display: 'block', marginTop: 4, fontSize: 11, color: '#94a3b8' }}>{title}</Typography.Text>
          </Tooltip>
        </div>
    );
  };

  const renderReferences = () => {
    if (!preview?.mediaReferences || preview.mediaReferences.length === 0) return null;

    return (
        <div>
          <Typography.Text style={{ fontSize: 12, color: '#94a3b8', display: 'block', marginBottom: 6 }}>参考内容</Typography.Text>
          <div style={{ display: 'flex', gap: 10, flexWrap: 'wrap' }}>
            {preview.mediaReferences.map((ref, index) => renderReferenceTile(ref, index))}
          </div>
        </div>
    );
  };

  return (
      <div>
        <Card variant="outlined" style={{ borderRadius: 12, border: '1px solid #f0f0f5' }}>
          <div style={{ display: 'flex', justifyContent: 'space-between', marginBottom: 16, flexWrap: 'wrap', gap: 12 }}>
            <Space>
              <PlayCircleOutlined style={{ fontSize: 18, color: '#6366f1' }} />
              <Typography.Text strong style={{ fontSize: 16 }}>创作记录管理</Typography.Text>
              <Tag color="purple">{total} 条记录</Tag>
            </Space>
            <Space>
              <Select
                allowClear
                placeholder="状态筛选"
                value={filterStatus || undefined}
                style={{ width: 140 }}
                onChange={(v) => { setFilterStatus(v || ''); setPage(1); }}
                options={[
                  { value: 'generating', label: '生成中' },
                  { value: 'completed', label: '已完成' },
                  { value: 'failed', label: '失败' },
                ]}
              />
              <Select
                allowClear
                placeholder="类型筛选"
                value={filterGenType || undefined}
                style={{ width: 120 }}
                onChange={(v) => { setFilterGenType(v || ''); setPage(1); }}
                options={[
                  { value: 'image', label: '图片' },
                  { value: 'video', label: '视频' },
                ]}
              />
              <Input
                placeholder="用户ID搜索"
                prefix={<SearchOutlined style={{ color: '#94a3b8' }} />}
                style={{ width: 180 }}
                value={inputUserId}
                onChange={(e) => setInputUserId(e.target.value)}
                onPressEnter={handleSearch}
                allowClear
              />
              <Input
                placeholder="用户名搜索"
                prefix={<SearchOutlined style={{ color: '#94a3b8' }} />}
                style={{ width: 160 }}
                value={inputUserName}
                onChange={(e) => setInputUserName(e.target.value)}
                onPressEnter={handleSearch}
                allowClear
              />
              <Button type="primary" onClick={handleSearch} style={{ borderRadius: 8 }}>
                搜索
              </Button>
            </Space>
          </div>

          <Table
            rowKey="id"
            loading={loading}
            columns={columns as any}
            dataSource={records}
            scroll={{ x: 1180 }}
            pagination={{
              current: page,
              pageSize: PAGE_SIZE,
              total,
              showSizeChanger: false,
              showTotal: (t) => `共 ${t} 条`,
              onChange: (p) => setPage(p),
            }}
          />
        </Card>

        <Modal
            title={(
                <Space>
                  {preview?.genType === 'video' ? <VideoCameraOutlined /> : <FileImageOutlined />}
                  <span>创作记录详情</span>
                </Space>
            )}
            open={!!preview}
            onCancel={handleClosePreview}
            footer={null}
            width={900}
            destroyOnClose
        >
          {preview ? (
              <div style={{ display: 'flex', flexDirection: 'column', gap: 16, marginTop: 12 }}>
                <div style={{ display: 'flex', gap: 12, flexWrap: 'wrap' }}>
                  {previewTypeConfig ? <Tag color={previewTypeConfig.color} icon={previewTypeConfig.icon}>{previewTypeConfig.text}</Tag> : null}
                  {previewStatusConfig ? <Tag color={previewStatusConfig.color} icon={previewStatusConfig.icon}>{previewStatusConfig.text}</Tag> : null}
                  {preview.pipelineStage ? <Tag color="blue">{PIPELINE_STAGE_MAP[preview.pipelineStage] || preview.pipelineStage}</Tag> : null}
                  {/*{preview.generationMode ? <Tag>{preview.generationMode}</Tag> : null}*/}
                </div>

                <div style={{ display: 'flex', gap: 16, padding: 12, borderRadius: 10, background: '#f8f9fc', flexWrap: 'wrap' }}>
                  <InfoItem label="用户名称" value={preview.userName || '未知用户'} />
                  <InfoItem label="用户ID" value={preview.userId || '-'} />
                  <InfoItem label="任务ID" value={preview.id} />
                </div>

                <div>
                  <Typography.Text style={{ fontSize: 12, color: '#94a3b8', display: 'block', marginBottom: 6 }}>原始提示词</Typography.Text>
                  <div style={{ padding: 12, borderRadius: 10, background: '#f8f9fc', lineHeight: 1.6 }}>
                    {preview.originalPrompt || '-'}
                  </div>
                </div>

                {preview.genType === 'video' ? (
                    <div style={{ display: 'flex', gap: 16, padding: 12, borderRadius: 10, background: '#f8f9fc', flexWrap: 'wrap' }}>
                      <InfoItem label="时长" value={preview.duration ? `${preview.duration}秒` : '-'} />
                      <InfoItem label="画面比例" value={preview.aspectRatio || '-'} />
                      <InfoItem label="分辨率" value={preview.resolution || '-'} />
                    </div>
                ) : (
                    <div style={{ display: 'flex', gap: 16, padding: 12, borderRadius: 10, background: '#f8f9fc', flexWrap: 'wrap' }}>
                      <InfoItem label="图片档位" value={preview.imageSize || '-'} />
                      <InfoItem label="图片比例" value={preview.imageProportion || '-'} />
                      <InfoItem label="像素尺寸" value={preview.imagePx || '-'} />
                    </div>
                )}

                {preview.engineSnapshot ? (
                    <div style={{ padding: 12, borderRadius: 10, background: '#f8f9fc' }}>
                      <Typography.Text style={{ fontSize: 12, color: '#94a3b8', display: 'block', marginBottom: 8 }}>引擎快照</Typography.Text>
                      <div style={{ display: 'flex', gap: 16, flexWrap: 'wrap' }}>
                        <InfoItem label="引擎名称" value={preview.engineSnapshot.name || '-'} />
                        <InfoItem label="服务商" value={preview.engineSnapshot.provider || '-'} />
                        <InfoItem label="模型" value={preview.engineSnapshot.modelName || '-'} />
                        <InfoItem label="引擎ID" value={preview.engineSnapshot.id || preview.engineId || '-'} />
                      </div>
                    </div>
                ) : null}

                <div style={{ display: 'flex', gap: 16, padding: 12, borderRadius: 10, background: '#f8f9fc', flexWrap: 'wrap' }}>
                  <InfoItem label="总积分" value={<Typography.Text strong style={{ color: '#6366f1' }}>{preview.creditsCost || 0}</Typography.Text>} />
                  <InfoItem label="文字积分" value={`${preview.textCreditsCost || 0} (${preview.textTokensUsed || 0} tokens)`} />
                  <InfoItem label="图片 tokens" value={preview.imageTokensUsed ?? 0} />
                  <InfoItem label="视频 tokens" value={preview.videoTokensUsed ?? 0} />
                </div>

                <div style={{ display: 'flex', gap: 16, padding: 12, borderRadius: 10, background: '#f8f9fc', flexWrap: 'wrap' }}>
                  <InfoItem label="第三方任务ID" value={preview.providerTaskId || preview.seedanceTaskId || '-'} />
                  <InfoItem label="轮询次数" value={preview.pollCount ?? 0} />
                  <InfoItem label="重试次数" value={preview.retryCount ?? 0} />
                </div>

                {renderReferences()}

                {preview.status === 'completed' ? (
                    <div>
                      <Typography.Text style={{ fontSize: 12, color: '#94a3b8', display: 'block', marginBottom: 6 }}>
                        {preview.genType === 'video' ? '生成视频' : '生成图片'}
                      </Typography.Text>
                      {preview.genType === 'video' ? renderResultVideo() : renderResultImage()}
                    </div>
                ) : null}

                {preview.status === 'failed' && preview.errorMessage ? (
                    <div style={{ padding: 12, borderRadius: 10, background: 'rgba(239,68,68,0.04)', border: '1px solid rgba(239,68,68,0.15)' }}>
                      <Typography.Text style={{ fontSize: 12, color: '#ef4444' }}>错误信息: {preview.errorMessage}</Typography.Text>
                    </div>
                ) : null}

                <div style={{ display: 'flex', gap: 16, fontSize: 12, color: '#94a3b8', flexWrap: 'wrap' }}>
                  <span>创建: {safeDate(preview.createdAt)}</span>
                  <span>生成: {safeDate(preview.generatedAt)}</span>
                </div>
              </div>
          ) : (
              <Empty description="暂无详情" />
          )}
        </Modal>
      </div>
  );
};

export default AdminGenerationAiRecords;
