# 硬链接到媒体库 内置插件「硬链接到媒体库」(`hardlink`)在种子整理完成后,把正片与字幕链接到一个单独的媒体库目录。下载目录保持原样,种子继续做种;媒体服务器只扫描媒体库目录。 该插件**默认停用**。它在每个种子整理完成后运行,重命名方式为 `none` 时也会运行。 ## 启用 1. 打开 **设置 → 插件**,找到「硬链接到媒体库」,展开 **配置**。 2. 填写 **下载根目录**(`source_root`)与 **媒体库目录**(`library_root`)。两者都是 AB 看到的绝对路径,媒体库目录不能位于下载根目录内。 3. 下载器看到的路径与 AB 不同时,填写 **路径映射**(见下文)。 4. 点击 **保存配置**,再打开插件的 **启用** 开关。 插件卡片显示「运行中」后即生效。保存时 AB 校验配置:路径不是绝对路径、媒体库在下载根目录内时,保存被拒绝。 媒体库中的路径与文件在下载根目录下的相对路径相同: ``` 下载根目录 /media/downloads/Bangumi 媒体库目录 /media/library /media/downloads/Bangumi/葬送的芙莉莲 (2023)/Season 1/葬送的芙莉莲 S01E05.mkv >> /media/library/葬送的芙莉莲 (2023)/Season 1/葬送的芙莉莲 S01E05.mkv ``` ## 选项 | 选项 | WebUI 名称 | 说明 | 默认值 | | --- | --- | --- | --- | | `source_root` | 下载根目录 | AB 本地的绝对路径。媒体库保持与它相同的目录结构 | 无,必填 | | `library_root` | 媒体库目录 | AB 本地的绝对路径,不能位于 `source_root` 内 | 无,必填 | | `path_map` | 路径映射 | 下载器路径到 AB 本地路径的映射列表,见下文 | 空 | | `cross_device` | 跨文件系统时 | `copy` 复制文件,`symlink` 创建软链接,`skip` 跳过并通知 | `copy` | ## 路径映射 整理完成事件中的文件路径是**下载器看到的路径**。下载器与 AB 运行在不同容器中、挂载点不同时,用路径映射把它换成 AB 本地路径。 每行有三个字段: - **下载器**(`downloader`):下载器实例 id,默认为 `default`。每个下载器实例需要自己的映射行,见 [多下载器](./downloaders.md)。 - **下载器路径**(`from`):下载器看到的路径前缀。 - **本地路径**(`to`):同一位置在 AB 中的路径。 AB 只使用与事件中下载器 id 相同的行,并按最长前缀匹配。没有匹配的路径原样使用。 示例:qBittorrent 把磁盘挂载为 `/downloads`,AB 把同一块盘挂载为 `/media/downloads`;第二个下载器 `nas` 看到的路径是 `/volume1/downloads`: ```json "path_map": [ { "downloader": "default", "from": "/downloads", "to": "/media/downloads" }, { "downloader": "nas", "from": "/volume1/downloads", "to": "/media/nas" } ] ``` 在设置页中,点击 **添加一行** 新增映射,点击 **删除** 移除一行。 映射后的路径必须位于下载根目录下。否则该文件不处理,AB 发送「硬链接未完成」通知。 ## 跨盘与 Docker 硬链接只能在同一个文件系统内建立。下载根目录与媒体库不在同一个文件系统时,AB 按 **跨文件系统时**(`cross_device`)处理: - `copy`(默认):复制文件,保留修改时间。媒体库占用双倍磁盘空间;大文件复制需要较长时间。 - `symlink`:创建软链接。删除下载目录中的文件后,软链接失效。 - `skip`:不处理,发送「硬链接未完成」通知。 ::: tip Docker 请把下载目录与媒体库放在同一块盘上,并以**同一个挂载点**映射进 AB 容器。例如把 `/mnt/media` 整体挂载为 `/media`,下载目录与媒体库都在其下。两个分别挂载的目录即使在同一块盘上,也会被视为不同的文件系统,此时按 `cross_device` 处理。 ::: AB 先把链接或副本写到目标旁的临时文件(`.<文件名>.<随机串>.ab-hardlink`),再原子地改名为目标文件。复制中断时,媒体库中不会留下不完整的文件。 ## 媒体库中已有文件 插件记录它放进媒体库的每个文件。目标位置已有文件时: | 情况 | 结果 | | --- | --- | | 目标是源文件的硬链接、软链接或相同的副本 | 视为已完成,不做任何事 | | 目标不是本插件放置的,或放置后被换成了别的文件 | 跳过,**绝不覆盖**,发送通知 | | 目标是本插件为同一位置放置的旧文件 | 版本升级,原子替换为新文件 | **版本升级**:新版本种子(如 `v2`)替换旧种子后,整理出的文件名不变。插件把之前放置的链接替换为指向新文件的链接。 同一个种子的所有问题合并为一条「硬链接未完成」通知,列出每个文件和原因。通知只显示种子 hash,不显示种子名。 ## 链接已有文件 插件只处理启用后整理完成的种子。启用前已经下载的文件,需要手动补链: 1. 打开 **设置**,在分区列表末尾找到「硬链接补链」。插件运行时才显示该分区。 2. 点击 **链接已有文件**。 AB 遍历下载根目录下的 `.mp4`、`.mkv`、`.ass`、`.srt` 文件,并显示四项计数:已链接、已存在、冲突、失败。补链只在点击时运行,不发送通知。已链接的文件不会重复处理。补链直接读取 AB 本地的下载根目录,不使用路径映射。 也可以调用 `POST /api/v1/plugins/hardlink/backfill`,它返回同样的计数。 ## 删除种子 删除种子不会删除媒体库中的文件。使用硬链接或复制时,删除种子及其文件后,媒体库中的文件仍可播放;使用软链接时,链接失效。