celery 容灾升级

This commit is contained in:
2026-07-22 14:48:29 +08:00
parent 3f1c4063b0
commit 69e7dec807
67 changed files with 6161 additions and 1958 deletions
@@ -2,6 +2,7 @@ import React from 'react';
import { Empty, Spin, Tag, Typography } from 'antd';
import { PlayCircleFilled } from '@ant-design/icons';
import type { GenerationAITaskOut } from '../../types';
import { resolveGenerationUiState } from '../../utils/generationTaskStatus';
interface Props {
task: GenerationAITaskOut;
@@ -16,14 +17,6 @@ const spanByCount = (count: number, index: number): number => {
return index < 3 ? 2 : 3;
};
const LABELS: Record<string, string> = {
pending: '待处理', queued: '已入队', preparing: '准备中', generating: '生成中',
creating_provider_task: '创建任务中', waiting_remote: '等待生成', polling: '轮询中',
result_ready: '结果就绪', download_queued: '等待下载', downloading: '下载中',
retry_waiting: '等待重试', completed: '已完成', failed: '生成失败',
download_failed: '下载失败', deleted: '已删除',
};
const GenerationTaskResourceGrid: React.FC<Props> = ({ task, resolveUrl, onPreview }) => {
const count = Math.max(1, Math.min(5, Number(task.generationCount || task.childItems?.length || 1)));
const sortedChildren = [...(task.childItems || [])].sort((a, b) => Number(a.generationIndex || 0) - Number(b.generationIndex || 0));
@@ -36,14 +29,14 @@ const GenerationTaskResourceGrid: React.FC<Props> = ({ task, resolveUrl, onPrevi
return (
<div style={{ width: '100%', height: 430, display: 'grid', gridTemplateColumns: 'repeat(6, minmax(0,1fr))', gridAutoRows: 'minmax(0,1fr)', gap: items.length > 1 ? 8 : 0 }}>
{items.map((item, index) => {
const status = item.displayStatus || item.pipelineStage || item.status || 'pending';
const uiState = resolveGenerationUiState(item);
const isVideo = item.genType === 'video';
const resultUrl = resolveUrl(isVideo ? item.videoUrl : item.imageUrl);
const coverUrl = resolveUrl(item.videoCoverUrl);
const active = ['pending', 'queued', 'preparing', 'generating', 'creating_provider_task', 'waiting_remote', 'polling', 'result_ready', 'download_queued', 'downloading', 'retry_waiting'].includes(status);
const active = uiState.isActive;
return (
<div key={item.id} style={{ gridColumn: `span ${spanByCount(items.length, index)}`, minWidth: 0, minHeight: 0, border: '1px solid #edf0f5', borderRadius: 10, overflow: 'hidden', position: 'relative', background: '#f8f9fc' }}>
{resultUrl && status !== 'deleted' ? (
{resultUrl && uiState.isSuccess ? (
<button type="button" onClick={() => onPreview(resultUrl, isVideo ? 'video' : 'image', `生成结果 ${item.generationIndex || index + 1}`)} style={{ width: '100%', height: '100%', padding: 0, border: 0, background: 'transparent', cursor: 'pointer', position: 'relative' }}>
{isVideo ? (coverUrl ? <img src={coverUrl} alt="视频封面" style={{ width: '100%', height: '100%', objectFit: 'contain' }} /> : <video src={resultUrl} muted preload="metadata" style={{ width: '100%', height: '100%', objectFit: 'contain' }} />) : <img src={resultUrl} alt="生成图片" style={{ width: '100%', height: '100%', objectFit: 'contain' }} />}
{isVideo ? <PlayCircleFilled style={{ position: 'absolute', left: '50%', top: '50%', transform: 'translate(-50%,-50%)', color: '#fff', fontSize: 38, filter: 'drop-shadow(0 3px 8px rgba(0,0,0,.35))' }} /> : null}
@@ -51,7 +44,7 @@ const GenerationTaskResourceGrid: React.FC<Props> = ({ task, resolveUrl, onPrevi
) : (
<div style={{ width: '100%', height: '100%', display: 'flex', flexDirection: 'column', alignItems: 'center', justifyContent: 'center', gap: 9, padding: 12, textAlign: 'center' }}>
{active ? <Spin size="small" /> : <Empty image={Empty.PRESENTED_IMAGE_SIMPLE} description={null} />}
<Tag color={status === 'deleted' ? 'default' : (status === 'download_failed' || status === 'failed' ? 'error' : 'processing')}>{LABELS[status] || status}</Tag>
<Tag color={uiState.color}>{uiState.label}</Tag>
{item.errorMessage && !active ? <Typography.Text type="danger" style={{ fontSize: 11 }}>{item.errorMessage}</Typography.Text> : null}
</div>
)}