import { lighten } from "@material-ui/core"; import Button from "@material-ui/core/Button"; import Checkbox from "@material-ui/core/Checkbox"; import IconButton from "@material-ui/core/IconButton"; import Link from "@material-ui/core/Link"; import Paper from "@material-ui/core/Paper"; import { makeStyles } from "@material-ui/core/styles"; import Table from "@material-ui/core/Table"; import TableBody from "@material-ui/core/TableBody"; import TableCell from "@material-ui/core/TableCell"; import TableContainer from "@material-ui/core/TableContainer"; import TableHead from "@material-ui/core/TableHead"; import TablePagination from "@material-ui/core/TablePagination"; import TableRow from "@material-ui/core/TableRow"; import TableSortLabel from "@material-ui/core/TableSortLabel"; import Toolbar from "@material-ui/core/Toolbar"; import Tooltip from "@material-ui/core/Tooltip"; import Typography from "@material-ui/core/Typography"; import { Delete } from "@material-ui/icons"; import React, { useCallback, useEffect, useState } from "react"; import { useDispatch } from "react-redux"; import { toggleSnackbar } from "../../../actions"; import API from "../../../middleware/Api"; import { sizeToString } from "../../../utils"; import ShareFilter from "../Dialogs/ShareFilter"; import { formatLocalTime } from "../../../utils/datetime"; const useStyles = makeStyles((theme) => ({ root: { [theme.breakpoints.up("md")]: { marginLeft: 100, }, marginBottom: 40, }, content: { padding: theme.spacing(2), }, container: { overflowX: "auto", }, tableContainer: { marginTop: 16, }, header: { display: "flex", justifyContent: "space-between", }, headerRight: {}, highlight: theme.palette.type === "light" ? { color: theme.palette.secondary.main, backgroundColor: lighten(theme.palette.secondary.light, 0.85), } : { color: theme.palette.text.primary, backgroundColor: theme.palette.secondary.dark, }, visuallyHidden: { border: 0, clip: "rect(0 0 0 0)", height: 1, margin: -1, overflow: "hidden", padding: 0, position: "absolute", top: 20, width: 1, }, })); export default function Download() { const classes = useStyles(); const [downloads, setDownloads] = useState([]); const [page, setPage] = useState(1); const [pageSize, setPageSize] = useState(10); const [total, setTotal] = useState(0); const [filter, setFilter] = useState({}); const [users, setUsers] = useState({}); const [search, setSearch] = useState({}); const [orderBy, setOrderBy] = useState(["id", "desc"]); const [filterDialog, setFilterDialog] = useState(false); const [selected, setSelected] = useState([]); const [loading, setLoading] = useState(false); const dispatch = useDispatch(); const ToggleSnackbar = useCallback( (vertical, horizontal, msg, color) => dispatch(toggleSnackbar(vertical, horizontal, msg, color)), [dispatch] ); const loadList = () => { API.post("/admin/download/list", { page: page, page_size: pageSize, order_by: orderBy.join(" "), conditions: filter, searches: search, }) .then((response) => { setUsers(response.data.users); setDownloads(response.data.items); setTotal(response.data.total); setSelected([]); }) .catch((error) => { ToggleSnackbar("top", "right", error.message, "error"); }); }; useEffect(() => { loadList(); }, [page, pageSize, orderBy, filter, search]); const deletePolicy = (id) => { setLoading(true); API.post("/admin/download/delete", { id: [id] }) .then(() => { loadList(); ToggleSnackbar("top", "right", "任务已删除", "success"); }) .catch((error) => { ToggleSnackbar("top", "right", error.message, "error"); }) .then(() => { setLoading(false); }); }; const deleteBatch = () => { setLoading(true); API.post("/admin/download/delete", { id: selected }) .then(() => { loadList(); ToggleSnackbar("top", "right", "任务已删除", "success"); }) .catch((error) => { ToggleSnackbar("top", "right", error.message, "error"); }) .then(() => { setLoading(false); }); }; const handleSelectAllClick = (event) => { if (event.target.checked) { const newSelecteds = downloads.map((n) => n.ID); setSelected(newSelecteds); return; } setSelected([]); }; const handleClick = (event, name) => { const selectedIndex = selected.indexOf(name); let newSelected = []; if (selectedIndex === -1) { newSelected = newSelected.concat(selected, name); } else if (selectedIndex === 0) { newSelected = newSelected.concat(selected.slice(1)); } else if (selectedIndex === selected.length - 1) { newSelected = newSelected.concat(selected.slice(0, -1)); } else if (selectedIndex > 0) { newSelected = newSelected.concat( selected.slice(0, selectedIndex), selected.slice(selectedIndex + 1) ); } setSelected(newSelected); }; const isSelected = (id) => selected.indexOf(id) !== -1; return (
setFilterDialog(false)} setSearch={setSearch} setFilter={setFilter} />
{selected.length > 0 && ( 已选择 {selected.length} 个对象 )} 0 && selected.length < downloads.length } checked={ downloads.length > 0 && selected.length === downloads.length } onChange={handleSelectAllClick} inputProps={{ "aria-label": "select all desserts", }} /> setOrderBy([ "id", orderBy[1] === "asc" ? "desc" : "asc", ]) } > # {orderBy[0] === "id" ? ( {orderBy[1] === "desc" ? "sorted descending" : "sorted ascending"} ) : null} 源地址 状态 setOrderBy([ "total_size", orderBy[1] === "asc" ? "desc" : "asc", ]) } > 大小 {orderBy[0] === "total_size" ? ( {orderBy[1] === "desc" ? "sorted descending" : "sorted ascending"} ) : null} 创建者 创建于 操作 {downloads.map((row) => ( handleClick(event, row.ID) } checked={isSelected(row.ID)} /> {row.ID} {row.Source} {row.Status === 0 && "就绪"} {row.Status === 1 && "下载中"} {row.Status === 2 && "暂停中"} {row.Status === 3 && "出错"} {row.Status === 4 && "完成"} {row.Status === 5 && "取消/停止"} {row.Status === 6 && "未知"} {sizeToString(row.TotalSize)} {users[row.UserID] ? users[row.UserID].Nick : "未知"} {formatLocalTime( row.CreatedAt, "YYYY-MM-DD H:mm:ss" )} deletePolicy(row.ID) } size={"small"} > ))}
setPage(p + 1)} onChangeRowsPerPage={(e) => { setPageSize(e.target.value); setPage(1); }} />
); }