重构前端逻辑
This commit is contained in:
parent
c285d224e4
commit
d9f084908a
@ -3,8 +3,9 @@ import type {RoleResponse, RoleRequest, RoleQuery, RoleTagResponse, RoleTagReque
|
|||||||
import {Page} from "@/types/base.ts";
|
import {Page} from "@/types/base.ts";
|
||||||
|
|
||||||
const BASE_URL = '/api/v1/role';
|
const BASE_URL = '/api/v1/role';
|
||||||
|
const ROLE_TAG_BASE_URL = '/api/v1/role-tag';
|
||||||
const ROLE_TAG_BASE_URL = '/api/v1/role-tag'
|
const PERMISSION_BASE_URL = '/api/v1/permission';
|
||||||
|
const MENU_BASE_URL = '/api/v1/menu';
|
||||||
|
|
||||||
// 获取角色列表(分页)
|
// 获取角色列表(分页)
|
||||||
export const getRoleList = (params?: RoleQuery) => request.get<Page<RoleResponse>>(`${BASE_URL}/page`, {params});
|
export const getRoleList = (params?: RoleQuery) => request.get<Page<RoleResponse>>(`${BASE_URL}/page`, {params});
|
||||||
@ -37,7 +38,7 @@ export const getRolePermissions = (roleId: number) => request.get<string[]>(`${B
|
|||||||
export const assignPermissions = (roleId: number, permissionIds: Number[]) => request.post(`${BASE_URL}/${roleId}/permissions`, permissionIds);
|
export const assignPermissions = (roleId: number, permissionIds: Number[]) => request.post(`${BASE_URL}/${roleId}/permissions`, permissionIds);
|
||||||
|
|
||||||
// 获取所有权限列表
|
// 获取所有权限列表
|
||||||
export const getAllPermissions = () => request.get<Permission[]>('/api/v1/permission/list');
|
export const getAllPermissions = () => request.get<Permission[]>(`${PERMISSION_BASE_URL}/list`);
|
||||||
|
|
||||||
// 获取权限树
|
// 获取权限树
|
||||||
export const getPermissionTree = () => request.get('/api/v1/role/permission-tree');
|
export const getPermissionTree = () => request.get(`${MENU_BASE_URL}/permission-tree`);
|
||||||
@ -27,7 +27,7 @@ export const resetPassword = (id: number, password: string) =>
|
|||||||
|
|
||||||
// 分配角色
|
// 分配角色
|
||||||
export const assignRoles = (userId: number, roleIds: number[]) =>
|
export const assignRoles = (userId: number, roleIds: number[]) =>
|
||||||
request.post(`${ROLE_BASE_URL}/${userId}/assignRoles`, roleIds);
|
request.post(`${BASE_URL}/${userId}/roles`, roleIds);
|
||||||
|
|
||||||
// 获取所有角色列表(不分页)
|
// 获取所有角色列表(不分页)
|
||||||
export const getAllRoles = () =>
|
export const getAllRoles = () =>
|
||||||
|
|||||||
@ -1,10 +1,9 @@
|
|||||||
import React from 'react';
|
import React from 'react';
|
||||||
import { Dialog, DialogPortal, DialogOverlay, DialogHeader, DialogTitle } from '@/components/ui/dialog';
|
import { Dialog, DialogContent, DialogHeader, DialogTitle } from '@/components/ui/dialog';
|
||||||
import { Tabs, TabsContent, TabsList, TabsTrigger } from '@/components/ui/tabs';
|
import { Tabs, TabsContent, TabsList, TabsTrigger } from '@/components/ui/tabs';
|
||||||
import { Badge } from '@/components/ui/badge';
|
import { Badge } from '@/components/ui/badge';
|
||||||
import * as DialogPrimitive from "@radix-ui/react-dialog";
|
import { Activity, Clock, FileText } from 'lucide-react';
|
||||||
import { X } from "lucide-react";
|
import { cn } from '@/lib/utils';
|
||||||
import { cn } from "@/lib/utils";
|
|
||||||
import { WorkflowHistoricalInstance } from '../types';
|
import { WorkflowHistoricalInstance } from '../types';
|
||||||
import { NodeType } from '../../../Design/nodes/types';
|
import { NodeType } from '../../../Design/nodes/types';
|
||||||
import FlowGraphTab from './tabs/FlowGraphTab';
|
import FlowGraphTab from './tabs/FlowGraphTab';
|
||||||
@ -81,52 +80,37 @@ const DetailModal: React.FC<DetailModalProps> = ({ visible, onCancel, instanceDa
|
|||||||
|
|
||||||
return (
|
return (
|
||||||
<Dialog open={visible} onOpenChange={(open) => !open && onCancel()}>
|
<Dialog open={visible} onOpenChange={(open) => !open && onCancel()}>
|
||||||
<DialogPortal>
|
<DialogContent className="!max-w-7xl w-[90vw] h-[85vh] flex flex-col p-0 overflow-hidden">
|
||||||
<DialogOverlay className="z-[60] backdrop-blur-sm" />
|
<DialogHeader className="px-6 pt-6 pb-4 border-b flex-shrink-0">
|
||||||
<DialogPrimitive.Content
|
<DialogTitle className="flex items-center justify-between">
|
||||||
className={cn(
|
<div className="flex items-center gap-3">
|
||||||
"fixed left-[50%] top-[50%] z-[60] grid w-full max-w-[90vw]",
|
<span className="text-lg font-semibold">流程执行详情</span>
|
||||||
"translate-x-[-50%] translate-y-[-50%]",
|
{getStatusBadge(instanceData.status)}
|
||||||
"gap-4 border-2 bg-background p-6 shadow-2xl",
|
</div>
|
||||||
"duration-300",
|
<div className="text-sm text-muted-foreground font-normal">
|
||||||
"data-[state=open]:animate-in data-[state=closed]:animate-out",
|
实例ID: <span className="font-mono">{instanceData.processInstanceId}</span>
|
||||||
"data-[state=closed]:fade-out-0 data-[state=open]:fade-in-0",
|
</div>
|
||||||
"data-[state=closed]:zoom-out-95 data-[state=open]:zoom-in-95",
|
|
||||||
"data-[state=closed]:slide-out-to-left-1/2 data-[state=closed]:slide-out-to-top-[48%]",
|
|
||||||
"data-[state=open]:slide-in-from-left-1/2 data-[state=open]:slide-in-from-top-[48%]",
|
|
||||||
"sm:rounded-xl",
|
|
||||||
"max-h-[90vh] overflow-y-auto"
|
|
||||||
)}
|
|
||||||
>
|
|
||||||
<DialogPrimitive.Close
|
|
||||||
className="absolute right-6 top-6 rounded-md opacity-70 ring-offset-background transition-all hover:opacity-100 hover:bg-accent hover:scale-110 focus:outline-none focus:ring-2 focus:ring-ring focus:ring-offset-2 disabled:pointer-events-none data-[state=open]:bg-accent data-[state=open]:text-muted-foreground p-1.5"
|
|
||||||
onClick={onCancel}
|
|
||||||
>
|
|
||||||
<X className="h-5 w-5" />
|
|
||||||
<span className="sr-only">Close</span>
|
|
||||||
</DialogPrimitive.Close>
|
|
||||||
|
|
||||||
<DialogHeader>
|
|
||||||
<DialogTitle className="text-2xl font-bold bg-gradient-to-r from-primary to-primary/60 bg-clip-text text-transparent">
|
|
||||||
流程执行详情
|
|
||||||
</DialogTitle>
|
</DialogTitle>
|
||||||
</DialogHeader>
|
</DialogHeader>
|
||||||
|
|
||||||
<Tabs defaultValue="graph" className="w-full">
|
<div className="flex-1 overflow-hidden flex flex-col">
|
||||||
<TabsList className="grid w-full grid-cols-3 h-12">
|
<Tabs defaultValue="graph" className="flex-1 flex flex-col overflow-hidden">
|
||||||
<TabsTrigger value="graph" className="text-base font-medium">
|
<TabsList className="grid w-full grid-cols-3 h-12 mx-6 mt-4 rounded-none">
|
||||||
📊 流程图
|
<TabsTrigger value="graph" className="data-[state=active]:bg-background">
|
||||||
|
<Activity className="h-4 w-4 mr-2" />
|
||||||
|
流程图
|
||||||
</TabsTrigger>
|
</TabsTrigger>
|
||||||
<TabsTrigger value="timeline" className="text-base font-medium">
|
<TabsTrigger value="timeline" className="data-[state=active]:bg-background">
|
||||||
⏱️ 执行时间线
|
<Clock className="h-4 w-4 mr-2" />
|
||||||
|
执行时间线
|
||||||
</TabsTrigger>
|
</TabsTrigger>
|
||||||
<TabsTrigger value="info" className="text-base font-medium">
|
<TabsTrigger value="info" className="data-[state=active]:bg-background">
|
||||||
📋 详细信息
|
<FileText className="h-4 w-4 mr-2" />
|
||||||
|
详细信息
|
||||||
</TabsTrigger>
|
</TabsTrigger>
|
||||||
</TabsList>
|
</TabsList>
|
||||||
|
|
||||||
{/* 流程图标签页 */}
|
<TabsContent value="graph" className="flex-1 mt-4 mx-6 overflow-auto focus-visible:outline-none focus-visible:ring-0 focus-visible:ring-offset-0">
|
||||||
<TabsContent value="graph" className="mt-6">
|
|
||||||
<FlowGraphTab
|
<FlowGraphTab
|
||||||
instanceData={instanceData}
|
instanceData={instanceData}
|
||||||
getStatusBadge={getStatusBadge}
|
getStatusBadge={getStatusBadge}
|
||||||
@ -134,8 +118,7 @@ const DetailModal: React.FC<DetailModalProps> = ({ visible, onCancel, instanceDa
|
|||||||
/>
|
/>
|
||||||
</TabsContent>
|
</TabsContent>
|
||||||
|
|
||||||
{/* 执行时间线标签页 */}
|
<TabsContent value="timeline" className="flex-1 mt-4 mx-6 overflow-auto focus-visible:outline-none focus-visible:ring-0 focus-visible:ring-offset-0">
|
||||||
<TabsContent value="timeline" className="mt-6">
|
|
||||||
<TimelineTab
|
<TimelineTab
|
||||||
instanceData={instanceData}
|
instanceData={instanceData}
|
||||||
getStatusBadge={getStatusBadge}
|
getStatusBadge={getStatusBadge}
|
||||||
@ -143,16 +126,15 @@ const DetailModal: React.FC<DetailModalProps> = ({ visible, onCancel, instanceDa
|
|||||||
/>
|
/>
|
||||||
</TabsContent>
|
</TabsContent>
|
||||||
|
|
||||||
{/* 详细信息标签页 */}
|
<TabsContent value="info" className="flex-1 mt-4 mx-6 overflow-auto focus-visible:outline-none focus-visible:ring-0 focus-visible:ring-offset-0">
|
||||||
<TabsContent value="info" className="mt-6">
|
|
||||||
<DetailInfoTab
|
<DetailInfoTab
|
||||||
instanceData={instanceData}
|
instanceData={instanceData}
|
||||||
getStatusBadge={getStatusBadge}
|
getStatusBadge={getStatusBadge}
|
||||||
/>
|
/>
|
||||||
</TabsContent>
|
</TabsContent>
|
||||||
</Tabs>
|
</Tabs>
|
||||||
</DialogPrimitive.Content>
|
</div>
|
||||||
</DialogPortal>
|
</DialogContent>
|
||||||
</Dialog>
|
</Dialog>
|
||||||
);
|
);
|
||||||
};
|
};
|
||||||
|
|||||||
@ -1,9 +1,10 @@
|
|||||||
import React, { useState, useEffect } from 'react';
|
import React, { useState, useEffect } from 'react';
|
||||||
import { Dialog, DialogContent, DialogHeader, DialogBody, DialogTitle } from '@/components/ui/dialog';
|
import { Dialog, DialogContent, DialogHeader, DialogTitle } from '@/components/ui/dialog';
|
||||||
import { Table, TableHeader, TableBody, TableHead, TableRow, TableCell } from '@/components/ui/table';
|
import { Table, TableHeader, TableBody, TableHead, TableRow, TableCell } from '@/components/ui/table';
|
||||||
import { Badge } from '@/components/ui/badge';
|
import { Badge } from '@/components/ui/badge';
|
||||||
import { Button } from '@/components/ui/button';
|
import { Button } from '@/components/ui/button';
|
||||||
import { DataTablePagination } from '@/components/ui/pagination';
|
import { DataTablePagination } from '@/components/ui/pagination';
|
||||||
|
import { Loader2, History } from 'lucide-react';
|
||||||
import { WorkflowHistoricalInstance } from '../types';
|
import { WorkflowHistoricalInstance } from '../types';
|
||||||
import { getHistoricalInstances } from '../service';
|
import { getHistoricalInstances } from '../service';
|
||||||
import DetailModal from './DetailModal';
|
import DetailModal from './DetailModal';
|
||||||
@ -73,19 +74,27 @@ const HistoryModal: React.FC<HistoryModalProps> = ({ visible, onCancel, workflow
|
|||||||
return (
|
return (
|
||||||
<>
|
<>
|
||||||
<Dialog open={visible} onOpenChange={(open) => !open && onCancel()}>
|
<Dialog open={visible} onOpenChange={(open) => !open && onCancel()}>
|
||||||
<DialogContent className="max-w-6xl">
|
<DialogContent className="max-w-6xl h-[80vh] flex flex-col p-0 overflow-hidden">
|
||||||
<DialogHeader>
|
<DialogHeader className="px-6 pt-6 pb-4 border-b flex-shrink-0">
|
||||||
<DialogTitle>历史执行记录</DialogTitle>
|
<DialogTitle className="flex items-center justify-between">
|
||||||
|
<div className="flex items-center gap-3">
|
||||||
|
<History className="h-5 w-5" />
|
||||||
|
<span className="text-lg font-semibold">历史执行记录</span>
|
||||||
|
</div>
|
||||||
|
<div className="text-sm text-muted-foreground font-normal">
|
||||||
|
共 {total} 条记录
|
||||||
|
</div>
|
||||||
|
</DialogTitle>
|
||||||
</DialogHeader>
|
</DialogHeader>
|
||||||
|
|
||||||
<DialogBody>
|
<div className="flex-1 overflow-auto px-6 py-4">
|
||||||
<div>
|
|
||||||
{loading ? (
|
{loading ? (
|
||||||
<div className="flex justify-center items-center py-8">
|
<div className="flex flex-col items-center justify-center h-full">
|
||||||
<div className="text-muted-foreground">加载中...</div>
|
<Loader2 className="h-8 w-8 animate-spin text-primary mb-2" />
|
||||||
|
<div className="text-sm text-muted-foreground">加载中...</div>
|
||||||
</div>
|
</div>
|
||||||
) : data.length === 0 ? (
|
) : data.length === 0 ? (
|
||||||
<div className="flex justify-center items-center py-8">
|
<div className="flex flex-col items-center justify-center h-full">
|
||||||
<div className="text-muted-foreground">暂无数据</div>
|
<div className="text-muted-foreground">暂无数据</div>
|
||||||
</div>
|
</div>
|
||||||
) : (
|
) : (
|
||||||
@ -125,6 +134,7 @@ const HistoryModal: React.FC<HistoryModalProps> = ({ visible, onCancel, workflow
|
|||||||
|
|
||||||
{/* 分页器 */}
|
{/* 分页器 */}
|
||||||
{pageCount > 1 && (
|
{pageCount > 1 && (
|
||||||
|
<div className="mt-4">
|
||||||
<DataTablePagination
|
<DataTablePagination
|
||||||
pageIndex={query.pageNum + 1}
|
pageIndex={query.pageNum + 1}
|
||||||
pageSize={query.pageSize}
|
pageSize={query.pageSize}
|
||||||
@ -134,11 +144,11 @@ const HistoryModal: React.FC<HistoryModalProps> = ({ visible, onCancel, workflow
|
|||||||
pageNum: page - 1
|
pageNum: page - 1
|
||||||
}))}
|
}))}
|
||||||
/>
|
/>
|
||||||
|
</div>
|
||||||
)}
|
)}
|
||||||
</>
|
</>
|
||||||
)}
|
)}
|
||||||
</div>
|
</div>
|
||||||
</DialogBody>
|
|
||||||
</DialogContent>
|
</DialogContent>
|
||||||
</Dialog>
|
</Dialog>
|
||||||
|
|
||||||
|
|||||||
Loading…
Reference in New Issue
Block a user