Files
aiops/frontend/src/components/deploy/ReleaseApplyDialog.tsx
T
Logan.Li d19a03d427 refactor(frontend): services/api 迁至 src/api,http 迁至 utils/request
对齐 Vue 后台惯例:
- src/api/          域 API(原 services/api)
- src/utils/request.ts  HTTP 封装(原 services/http.ts)
- src/utils/export.ts  客户端导出工具
- src/utils/index.ts   工具统一出口

全局导入改为 @/api 与 @/utils/request,tsc + build 通过。
2026-06-26 00:09:07 +08:00

163 lines
5.1 KiB
TypeScript

// 发布管理 - 新建发布申请弹窗(自包含表单状态 + 提交逻辑) // Logan.Li
import { useState, useEffect } from 'react';
import {
Dialog,
DialogContent,
DialogDescription,
DialogFooter,
DialogHeader,
DialogTitle,
} from '@/components/ui/dialog';
import { Button } from '@/components/ui/button';
import { Input } from '@/components/ui/input';
import { Label } from '@/components/ui/label';
import { Textarea } from '@/components/ui/textarea';
import {
Select,
SelectContent,
SelectItem,
SelectTrigger,
SelectValue,
} from '@/components/ui/select';
import { Loader2 } from 'lucide-react';
import { releaseApi } from '@/api';
import { toast } from 'sonner';
interface ReleaseApplyDialogProps {
open: boolean;
onOpenChange: (open: boolean) => void;
onSuccess?: () => void;
}
export function ReleaseApplyDialog({ open, onOpenChange, onSuccess }: ReleaseApplyDialogProps) {
const [submitting, setSubmitting] = useState(false);
const [form, setForm] = useState({
appName: '',
version: '',
environment: 'dev',
commitId: '',
commitMsg: '',
description: '',
});
// 弹窗打开时重置表单 // Logan.Li
useEffect(() => {
if (open) {
setForm({ appName: '', version: '', environment: 'dev', commitId: '', commitMsg: '', description: '' });
}
}, [open]);
const handleSubmit = async () => {
if (!form.appName.trim() || !form.version.trim()) {
toast.error('请填写应用名称和版本号');
return;
}
setSubmitting(true);
try {
await releaseApi.createRelease({
app_name: form.appName.trim(),
version: form.version.trim(),
environment: form.environment,
commit_id: form.commitId.trim(),
commit_msg: form.commitMsg.trim(),
description: form.description.trim(),
});
toast.success('发布申请已提交');
onOpenChange(false);
onSuccess?.();
} catch {
toast.error('创建失败');
} finally {
setSubmitting(false);
}
};
return (
<Dialog open={open} onOpenChange={onOpenChange}>
<DialogContent className="max-w-2xl">
<DialogHeader>
<DialogTitle>新建发布</DialogTitle>
<DialogDescription>创建新的应用版本发布申请</DialogDescription>
</DialogHeader>
<div className="space-y-4 py-4">
<div>
<Label>应用名称</Label>
<Input
value={form.appName}
onChange={(e) => setForm({ ...form, appName: e.target.value })}
placeholder="如:用户中心服务"
className="mt-1"
/>
</div>
<div className="grid grid-cols-2 gap-4">
<div>
<Label>版本号</Label>
<Input
value={form.version}
onChange={(e) => setForm({ ...form, version: e.target.value })}
placeholder="v1.0.0"
className="mt-1"
/>
</div>
<div>
<Label>目标环境</Label>
<Select
value={form.environment}
onValueChange={(value) => setForm({ ...form, environment: value })}
>
<SelectTrigger className="mt-1">
<SelectValue />
</SelectTrigger>
<SelectContent>
<SelectItem value="dev">开发环境</SelectItem>
<SelectItem value="test">测试环境</SelectItem>
<SelectItem value="staging">预发环境</SelectItem>
<SelectItem value="prod">生产环境</SelectItem>
</SelectContent>
</Select>
</div>
</div>
<div className="grid grid-cols-2 gap-4">
<div>
<Label>Commit ID</Label>
<Input
value={form.commitId}
onChange={(e) => setForm({ ...form, commitId: e.target.value })}
placeholder="abc1234"
className="mt-1"
/>
</div>
<div>
<Label>提交信息</Label>
<Input
value={form.commitMsg}
onChange={(e) => setForm({ ...form, commitMsg: e.target.value })}
placeholder="feat: 新增功能"
className="mt-1"
/>
</div>
</div>
<div>
<Label>发布说明</Label>
<Textarea
value={form.description}
onChange={(e) => setForm({ ...form, description: e.target.value })}
placeholder="描述本次发布的内容..."
className="mt-1"
/>
</div>
</div>
<DialogFooter>
<Button variant="outline" onClick={() => onOpenChange(false)}>
取消
</Button>
<Button onClick={handleSubmit} disabled={submitting}>
{submitting ? <Loader2 className="h-4 w-4 mr-2 animate-spin" /> : null}
提交申请
</Button>
</DialogFooter>
</DialogContent>
</Dialog>
);
}