feat(web): regroup console nav into 7 groups, split downloads/plans/tasks, add legacy redirects
- Sidebar: 概览/资源/订阅/下载/整理/Agent/系统, 18 items (+ 定时任务); single active item via findNavItem; 待处理 badge; collapsed rail groups; mobile drawer shares NAV_GROUPS. - New pages: /downloads (queue + cache watermark header), /downloads/plans, /downloads/:id, /tasks (business tasks only) + /tasks/:id detail, /rules. - Legacy links: ?tab= on tasks/subscriptions/sources redirect via clientLoader; /tasks/:downloadId falls back to /downloads/:id. - List filters in URL query; settingsPath() helper for settings deep links. - Copy per glossary (待处理, 收录策略, 引擎面板, 文件管理, 版本目标). Co-Authored-By: Claude Opus 5.5 <[email protected]>
This commit is contained in:
1 parent
5843527317
commit
909cd2ad49
31 files changed
+1247
-609
No files matched your search
@@ -9,9 +9,9 @@ import {
|
||||
type SubscriptionProgress,
|
||||
type SubscriptionStatus,
|
||||
} from "@umt/contracts";
|
||||
import { CalendarClock, Check, FilePlus2, Pause, Play, Plus, Search, XCircle } from "lucide-react";
|
||||
import { CalendarClock, Check, ListChecks, Pause, Play, Plus, Search, XCircle } from "lucide-react";
|
||||
import { useEffect, useId, useMemo, useState } from "react";
|
||||
import { Link, useSearchParams } from "react-router";
|
||||
import { Link } from "react-router";
|
||||
import { toast } from "sonner";
|
||||
import { useEntitySearch } from "~/api/library.ts";
|
||||
import {
|
||||
@@ -42,7 +42,6 @@ import {
|
||||
SUB_STATUS,
|
||||
} from "~/components/library/labels.ts";
|
||||
import { Chip, relTime, Tone } from "~/components/library/parts.tsx";
|
||||
import { PolicyWorkspace } from "~/components/library/subscriptions-policy.tsx";
|
||||
import { SlotsPanel } from "~/components/library/subscriptions-slots.tsx";
|
||||
import { Button, buttonVariants } from "~/components/ui/button.tsx";
|
||||
import {
|
||||
@@ -55,62 +54,42 @@ import {
|
||||
} from "~/components/ui/dialog.tsx";
|
||||
import { Input } from "~/components/ui/input.tsx";
|
||||
import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue } from "~/components/ui/select.tsx";
|
||||
import { Tabs, TabsContent, TabsList, TabsTrigger } from "~/components/ui/tabs.tsx";
|
||||
import { errorMessage } from "~/lib/api.ts";
|
||||
import { cn, formatDateTime } from "~/lib/utils.ts";
|
||||
import { legacyRedirectLoader } from "./redirects.ts";
|
||||
|
||||
// 订阅与收录规则:订阅(单次/持续、仅本季/接续)+ 各作品的收录目标 Slot + 收录策略版本(REQ §6.1、§6.4、§6.5)
|
||||
// 订阅:单次/持续、仅本季/接续 + 各作品的版本目标(REQ §6.1、§6.4)。收录策略在 /console/rules。
|
||||
|
||||
export const meta = () => [{ title: "订阅 · UHD 媒体自动化控制台" }];
|
||||
|
||||
// 旧的 ?tab=policies 跳到收录策略
|
||||
export const clientLoader = legacyRedirectLoader;
|
||||
|
||||
const SUB_KIND_LABEL: Record<SubscriptionMediaKind, string> = { movie: "电影", series: "剧集", variety: "综艺" };
|
||||
|
||||
export default function SubscriptionsPage() {
|
||||
const [params, setParams] = useSearchParams();
|
||||
const tab = params.get("tab") === "policies" ? "policies" : "subscriptions";
|
||||
const [creatingSub, setCreatingSub] = useState(false);
|
||||
const [creatingPolicy, setCreatingPolicy] = useState(false);
|
||||
|
||||
return (
|
||||
<>
|
||||
<PageHeader
|
||||
title="订阅与收录规则"
|
||||
title="订阅"
|
||||
actions={
|
||||
tab === "subscriptions" ? (
|
||||
<>
|
||||
<Button asChild variant="ghost" size="sm">
|
||||
<Link to={consolePath("rules")}>
|
||||
<ListChecks />
|
||||
收录策略
|
||||
</Link>
|
||||
</Button>
|
||||
<Button onClick={() => setCreatingSub(true)}>
|
||||
<Plus />
|
||||
新建订阅
|
||||
</Button>
|
||||
) : (
|
||||
<Button onClick={() => setCreatingPolicy(true)}>
|
||||
<FilePlus2 />
|
||||
新建策略草案
|
||||
</Button>
|
||||
)
|
||||
</>
|
||||
}
|
||||
/>
|
||||
<Tabs
|
||||
value={tab}
|
||||
onValueChange={(v) =>
|
||||
setParams(
|
||||
(p) => {
|
||||
if (v === "policies") p.set("tab", "policies");
|
||||
else p.delete("tab");
|
||||
return p;
|
||||
},
|
||||
{ replace: true },
|
||||
)
|
||||
}
|
||||
>
|
||||
<TabsList aria-label="订阅与收录规则">
|
||||
<TabsTrigger value="subscriptions">订阅</TabsTrigger>
|
||||
<TabsTrigger value="policies">收录策略</TabsTrigger>
|
||||
</TabsList>
|
||||
<TabsContent value="subscriptions">
|
||||
<SubscriptionsTab />
|
||||
</TabsContent>
|
||||
<TabsContent value="policies">
|
||||
<PolicyWorkspace creating={creatingPolicy} onCreatingChange={setCreatingPolicy} />
|
||||
</TabsContent>
|
||||
</Tabs>
|
||||
<SubscriptionsTab />
|
||||
{creatingSub ? <CreateSubscriptionDialog onClose={() => setCreatingSub(false)} /> : null}
|
||||
</>
|
||||
);
|
||||
|
||||
Reference in new issue
Block a user