mirror of
https://github.com/jxxghp/MoviePilot.git
synced 2026-09-05 23:47:41 +08:00
fix #2913
This commit is contained in:
@@ -69,8 +69,8 @@ jobs:
|
|||||||
- name: Generate Release
|
- name: Generate Release
|
||||||
uses: softprops/action-gh-release@v2
|
uses: softprops/action-gh-release@v2
|
||||||
with:
|
with:
|
||||||
tag_name: ${{ env.app_version }}
|
tag_name: v${{ env.app_version }}
|
||||||
name: ${{ env.app_version }}
|
name: v${{ env.app_version }}
|
||||||
draft: false
|
draft: false
|
||||||
prerelease: false
|
prerelease: false
|
||||||
make_latest: false
|
make_latest: false
|
||||||
|
|||||||
@@ -382,7 +382,7 @@ class ChainBase(metaclass=ABCMeta):
|
|||||||
return self.run_module("list_torrents", status=status, hashs=hashs, downloader=downloader)
|
return self.run_module("list_torrents", status=status, hashs=hashs, downloader=downloader)
|
||||||
|
|
||||||
def transfer(self, fileitem: FileItem, meta: MetaBase, mediainfo: MediaInfo,
|
def transfer(self, fileitem: FileItem, meta: MetaBase, mediainfo: MediaInfo,
|
||||||
transfer_type: str, target_storage: str = None, target_path: Path = None,
|
transfer_type: str = None, target_storage: str = None, target_path: Path = None,
|
||||||
episodes_info: List[TmdbEpisode] = None,
|
episodes_info: List[TmdbEpisode] = None,
|
||||||
scrape: bool = None) -> Optional[TransferInfo]:
|
scrape: bool = None) -> Optional[TransferInfo]:
|
||||||
"""
|
"""
|
||||||
@@ -401,17 +401,13 @@ class ChainBase(metaclass=ABCMeta):
|
|||||||
transfer_type=transfer_type, target_storage=target_storage,
|
transfer_type=transfer_type, target_storage=target_storage,
|
||||||
target_path=target_path, episodes_info=episodes_info, scrape=scrape)
|
target_path=target_path, episodes_info=episodes_info, scrape=scrape)
|
||||||
|
|
||||||
def transfer_completed(self, hashs: str, path: Path = None,
|
def transfer_completed(self, hashs: str, downloader: str = None) -> None:
|
||||||
downloader: str = None, transfer_type: str = None) -> None:
|
|
||||||
"""
|
"""
|
||||||
转移完成后的处理
|
下载器转移完成后的处理
|
||||||
:param hashs: 种子Hash
|
:param hashs: 种子Hash
|
||||||
:param path: 源目录
|
|
||||||
:param downloader: 下载器
|
:param downloader: 下载器
|
||||||
:param transfer_type: 整理方式
|
|
||||||
"""
|
"""
|
||||||
return self.run_module("transfer_completed", hashs=hashs, path=path,
|
return self.run_module("transfer_completed", hashs=hashs, downloader=downloader)
|
||||||
downloader=downloader, transfer_type=transfer_type)
|
|
||||||
|
|
||||||
def remove_torrents(self, hashs: Union[str, list], delete_file: bool = True,
|
def remove_torrents(self, hashs: Union[str, list], delete_file: bool = True,
|
||||||
downloader: str = None) -> bool:
|
downloader: str = None) -> bool:
|
||||||
|
|||||||
+29
-38
@@ -92,16 +92,16 @@ class TransferChain(ChainBase):
|
|||||||
logger.warn(f"文件不存在:{file_path}")
|
logger.warn(f"文件不存在:{file_path}")
|
||||||
continue
|
continue
|
||||||
# 检查是否为下载器监控目录中的文件
|
# 检查是否为下载器监控目录中的文件
|
||||||
transfer_dirinfo = None
|
is_downloader_monitor = False
|
||||||
for dir_info in download_dirs:
|
for dir_info in download_dirs:
|
||||||
if dir_info.monitor_type != "downloader":
|
if dir_info.monitor_type != "downloader":
|
||||||
continue
|
continue
|
||||||
if not dir_info.download_path:
|
if not dir_info.download_path:
|
||||||
continue
|
continue
|
||||||
if file_path.is_relative_to(Path(dir_info.download_path)):
|
if file_path.is_relative_to(Path(dir_info.download_path)):
|
||||||
transfer_dirinfo = dir_info
|
is_downloader_monitor = True
|
||||||
break
|
break
|
||||||
if not transfer_dirinfo:
|
if not is_downloader_monitor:
|
||||||
logger.debug(f"文件 {file_path} 不在下载器监控目录中,不通过下载器进行整理")
|
logger.debug(f"文件 {file_path} 不在下载器监控目录中,不通过下载器进行整理")
|
||||||
continue
|
continue
|
||||||
# 查询下载记录识别情况
|
# 查询下载记录识别情况
|
||||||
@@ -127,7 +127,7 @@ class TransferChain(ChainBase):
|
|||||||
mediainfo = None
|
mediainfo = None
|
||||||
|
|
||||||
# 执行整理
|
# 执行整理
|
||||||
self.__do_transfer(
|
state, errmsg = self.__do_transfer(
|
||||||
fileitem=FileItem(
|
fileitem=FileItem(
|
||||||
storage="local",
|
storage="local",
|
||||||
path=str(file_path),
|
path=str(file_path),
|
||||||
@@ -136,15 +136,14 @@ class TransferChain(ChainBase):
|
|||||||
size=file_path.stat().st_size,
|
size=file_path.stat().st_size,
|
||||||
extension=file_path.suffix.lstrip('.'),
|
extension=file_path.suffix.lstrip('.'),
|
||||||
),
|
),
|
||||||
target_storage=transfer_dirinfo.library_storage,
|
|
||||||
mediainfo=mediainfo,
|
mediainfo=mediainfo,
|
||||||
download_hash=torrent.hash,
|
download_hash=torrent.hash
|
||||||
notify=transfer_dirinfo.notify
|
|
||||||
)
|
)
|
||||||
|
|
||||||
# 设置下载任务状态
|
# 设置下载任务状态
|
||||||
self.transfer_completed(hashs=torrent.hash, path=torrent.path,
|
if state:
|
||||||
transfer_type=transfer_dirinfo.transfer_type)
|
self.transfer_completed(hashs=torrent.hash)
|
||||||
|
|
||||||
# 结束
|
# 结束
|
||||||
logger.info("所有下载器中下载完成的文件已整理完成")
|
logger.info("所有下载器中下载完成的文件已整理完成")
|
||||||
return True
|
return True
|
||||||
@@ -155,7 +154,7 @@ class TransferChain(ChainBase):
|
|||||||
target_path: Path = None, transfer_type: str = None,
|
target_path: Path = None, transfer_type: str = None,
|
||||||
season: int = None, epformat: EpisodeFormat = None,
|
season: int = None, epformat: EpisodeFormat = None,
|
||||||
min_filesize: int = 0, scrape: bool = None,
|
min_filesize: int = 0, scrape: bool = None,
|
||||||
force: bool = False, notify: bool = True) -> Tuple[bool, str]:
|
force: bool = False) -> Tuple[bool, str]:
|
||||||
"""
|
"""
|
||||||
执行一个复杂目录的整理操作
|
执行一个复杂目录的整理操作
|
||||||
:param fileitem: 文件项
|
:param fileitem: 文件项
|
||||||
@@ -193,6 +192,8 @@ class TransferChain(ChainBase):
|
|||||||
fail_num = 0
|
fail_num = 0
|
||||||
# 跳过数量
|
# 跳过数量
|
||||||
skip_num = 0
|
skip_num = 0
|
||||||
|
# 本次整理方式
|
||||||
|
current_transfer_type = transfer_type
|
||||||
|
|
||||||
# 获取待整理路径清单
|
# 获取待整理路径清单
|
||||||
trans_items = self.__get_trans_fileitems(fileitem)
|
trans_items = self.__get_trans_fileitems(fileitem)
|
||||||
@@ -412,6 +413,7 @@ class TransferChain(ChainBase):
|
|||||||
continue
|
continue
|
||||||
|
|
||||||
# 汇总信息
|
# 汇总信息
|
||||||
|
current_transfer_type = transferinfo.transfer_type
|
||||||
mkey = (file_mediainfo.tmdb_id, file_meta.begin_season)
|
mkey = (file_mediainfo.tmdb_id, file_meta.begin_season)
|
||||||
if mkey not in medias:
|
if mkey not in medias:
|
||||||
# 新增信息
|
# 新增信息
|
||||||
@@ -454,7 +456,7 @@ class TransferChain(ChainBase):
|
|||||||
transfer_meta = metas[mkey]
|
transfer_meta = metas[mkey]
|
||||||
transfer_info = transfers[mkey]
|
transfer_info = transfers[mkey]
|
||||||
# 发送通知
|
# 发送通知
|
||||||
if notify:
|
if transfer_info.need_notify:
|
||||||
se_str = None
|
se_str = None
|
||||||
if media.type == MediaType.TV:
|
if media.type == MediaType.TV:
|
||||||
se_str = f"{transfer_meta.season} {StringUtils.format_ep(season_episodes[mkey])}"
|
se_str = f"{transfer_meta.season} {StringUtils.format_ep(season_episodes[mkey])}"
|
||||||
@@ -473,9 +475,21 @@ class TransferChain(ChainBase):
|
|||||||
self.eventmanager.send_event(EventType.TransferComplete, {
|
self.eventmanager.send_event(EventType.TransferComplete, {
|
||||||
'meta': transfer_meta,
|
'meta': transfer_meta,
|
||||||
'mediainfo': media,
|
'mediainfo': media,
|
||||||
'transferinfo': transfer_info
|
'transferinfo': transfer_info,
|
||||||
|
'download_hash': download_hash,
|
||||||
})
|
})
|
||||||
|
|
||||||
|
# 移动模式处理
|
||||||
|
if current_transfer_type in ["move"]:
|
||||||
|
# 下载器hash
|
||||||
|
if download_hash:
|
||||||
|
if self.remove_torrents(download_hash):
|
||||||
|
logger.info(f"移动模式删除种子成功:{download_hash} ")
|
||||||
|
# 删除残留文件
|
||||||
|
if fileitem:
|
||||||
|
logger.warn(f"删除残留文件夹:【{fileitem.storage}】{fileitem.path}")
|
||||||
|
self.storagechain.delete_file(fileitem)
|
||||||
|
|
||||||
# 结束进度
|
# 结束进度
|
||||||
logger.info(f"{fileitem.path} 整理完成,共 {total_num} 个文件,"
|
logger.info(f"{fileitem.path} 整理完成,共 {total_num} 个文件,"
|
||||||
f"失败 {fail_num} 个,跳过 {skip_num} 个")
|
f"失败 {fail_num} 个,跳过 {skip_num} 个")
|
||||||
@@ -617,21 +631,10 @@ class TransferChain(ChainBase):
|
|||||||
|
|
||||||
# 强制整理
|
# 强制整理
|
||||||
if history.src_fileitem:
|
if history.src_fileitem:
|
||||||
# 解析源文件对象
|
state, errmsg = self.__do_transfer(fileitem=FileItem(**history.src_fileitem),
|
||||||
fileitem = FileItem(**history.src_fileitem)
|
|
||||||
# 检查目录是否发送通知
|
|
||||||
transfer_dirinfo = None
|
|
||||||
for dir_info in self.directoryhelper.get_download_dirs():
|
|
||||||
if not dir_info.download_path:
|
|
||||||
continue
|
|
||||||
if fileitem.path.is_relative_to(Path(dir_info.download_path)):
|
|
||||||
transfer_dirinfo = dir_info
|
|
||||||
break
|
|
||||||
state, errmsg = self.__do_transfer(fileitem=fileitem,
|
|
||||||
mediainfo=mediainfo,
|
mediainfo=mediainfo,
|
||||||
download_hash=history.download_hash,
|
download_hash=history.download_hash,
|
||||||
force=True,
|
force=True)
|
||||||
notify=transfer_dirinfo.notify if transfer_dirinfo else False)
|
|
||||||
if not state:
|
if not state:
|
||||||
return False, errmsg
|
return False, errmsg
|
||||||
|
|
||||||
@@ -666,16 +669,6 @@ class TransferChain(ChainBase):
|
|||||||
:param force: 是否强制整理
|
:param force: 是否强制整理
|
||||||
"""
|
"""
|
||||||
logger.info(f"手动整理:{fileitem.path} ...")
|
logger.info(f"手动整理:{fileitem.path} ...")
|
||||||
|
|
||||||
# 检查目录是否发送通知
|
|
||||||
transfer_dirinfo = None
|
|
||||||
for dir_info in self.directoryhelper.get_download_dirs():
|
|
||||||
if not dir_info.download_path:
|
|
||||||
continue
|
|
||||||
if fileitem.path.is_relative_to(Path(dir_info.download_path)):
|
|
||||||
transfer_dirinfo = dir_info
|
|
||||||
break
|
|
||||||
|
|
||||||
if tmdbid or doubanid:
|
if tmdbid or doubanid:
|
||||||
# 有输入TMDBID时单个识别
|
# 有输入TMDBID时单个识别
|
||||||
# 识别媒体信息
|
# 识别媒体信息
|
||||||
@@ -702,7 +695,6 @@ class TransferChain(ChainBase):
|
|||||||
min_filesize=min_filesize,
|
min_filesize=min_filesize,
|
||||||
scrape=scrape,
|
scrape=scrape,
|
||||||
force=force,
|
force=force,
|
||||||
notify=transfer_dirinfo.notify if transfer_dirinfo else False
|
|
||||||
)
|
)
|
||||||
if not state:
|
if not state:
|
||||||
return False, errmsg
|
return False, errmsg
|
||||||
@@ -720,8 +712,7 @@ class TransferChain(ChainBase):
|
|||||||
epformat=epformat,
|
epformat=epformat,
|
||||||
min_filesize=min_filesize,
|
min_filesize=min_filesize,
|
||||||
scrape=scrape,
|
scrape=scrape,
|
||||||
force=force,
|
force=force)
|
||||||
notify=transfer_dirinfo.notify if transfer_dirinfo else False)
|
|
||||||
return state, errmsg
|
return state, errmsg
|
||||||
|
|
||||||
def send_transfer_message(self, meta: MetaBase, mediainfo: MediaInfo,
|
def send_transfer_message(self, meta: MetaBase, mediainfo: MediaInfo,
|
||||||
|
|||||||
@@ -281,7 +281,7 @@ class FileManagerModule(_ModuleBase):
|
|||||||
return storage_oper.usage()
|
return storage_oper.usage()
|
||||||
|
|
||||||
def transfer(self, fileitem: FileItem, meta: MetaBase, mediainfo: MediaInfo,
|
def transfer(self, fileitem: FileItem, meta: MetaBase, mediainfo: MediaInfo,
|
||||||
transfer_type: str, target_storage: str = None, target_path: Path = None,
|
transfer_type: str = None, target_storage: str = None, target_path: Path = None,
|
||||||
episodes_info: List[TmdbEpisode] = None,
|
episodes_info: List[TmdbEpisode] = None,
|
||||||
scrape: bool = None) -> TransferInfo:
|
scrape: bool = None) -> TransferInfo:
|
||||||
"""
|
"""
|
||||||
@@ -329,12 +329,15 @@ class FileManagerModule(_ModuleBase):
|
|||||||
need_rename = dir_info.renaming
|
need_rename = dir_info.renaming
|
||||||
# 覆盖模式
|
# 覆盖模式
|
||||||
overwrite_mode = dir_info.overwrite_mode
|
overwrite_mode = dir_info.overwrite_mode
|
||||||
|
# 是否需要通知
|
||||||
|
need_notify = dir_info.notify
|
||||||
# 拼装媒体库一、二级子目录
|
# 拼装媒体库一、二级子目录
|
||||||
target_path = self.__get_dest_dir(mediainfo=mediainfo, target_dir=dir_info)
|
target_path = self.__get_dest_dir(mediainfo=mediainfo, target_dir=dir_info)
|
||||||
elif target_path:
|
elif target_path:
|
||||||
# 自定义目标路径
|
# 自定义目标路径,仅适用于手动整理的场景
|
||||||
need_scrape = scrape or False
|
need_scrape = scrape or False
|
||||||
need_rename = True
|
need_rename = True
|
||||||
|
need_notify = False
|
||||||
overwrite_mode = "never"
|
overwrite_mode = "never"
|
||||||
else:
|
else:
|
||||||
# 未找到有效的媒体库目录
|
# 未找到有效的媒体库目录
|
||||||
@@ -355,7 +358,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
target_path=target_path,
|
target_path=target_path,
|
||||||
episodes_info=episodes_info,
|
episodes_info=episodes_info,
|
||||||
need_scrape=need_scrape,
|
need_scrape=need_scrape,
|
||||||
need_rename=need_rename)
|
need_rename=need_rename,
|
||||||
|
need_notify=need_notify)
|
||||||
|
|
||||||
def __get_storage_oper(self, _storage: str, _func: str = None) -> Optional[StorageBase]:
|
def __get_storage_oper(self, _storage: str, _func: str = None) -> Optional[StorageBase]:
|
||||||
"""
|
"""
|
||||||
@@ -811,7 +815,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
target_path: Path,
|
target_path: Path,
|
||||||
episodes_info: List[TmdbEpisode] = None,
|
episodes_info: List[TmdbEpisode] = None,
|
||||||
need_scrape: bool = False,
|
need_scrape: bool = False,
|
||||||
need_rename: bool = True
|
need_rename: bool = True,
|
||||||
|
need_notify: bool = True,
|
||||||
) -> TransferInfo:
|
) -> TransferInfo:
|
||||||
"""
|
"""
|
||||||
识别并整理一个文件或者一个目录下的所有文件
|
识别并整理一个文件或者一个目录下的所有文件
|
||||||
@@ -825,6 +830,7 @@ class FileManagerModule(_ModuleBase):
|
|||||||
:param episodes_info: 当前季的全部集信息
|
:param episodes_info: 当前季的全部集信息
|
||||||
:param need_scrape: 是否需要刮削
|
:param need_scrape: 是否需要刮削
|
||||||
:param need_rename: 是否需要重命名
|
:param need_rename: 是否需要重命名
|
||||||
|
:param need_notify: 是否需要通知
|
||||||
:return: TransferInfo、错误信息
|
:return: TransferInfo、错误信息
|
||||||
"""
|
"""
|
||||||
|
|
||||||
@@ -854,7 +860,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
return TransferInfo(success=False,
|
return TransferInfo(success=False,
|
||||||
message=errmsg,
|
message=errmsg,
|
||||||
fileitem=fileitem,
|
fileitem=fileitem,
|
||||||
transfer_type=transfer_type)
|
transfer_type=transfer_type,
|
||||||
|
need_notify=need_notify)
|
||||||
|
|
||||||
logger.info(f"文件夹 {fileitem.path} 整理成功")
|
logger.info(f"文件夹 {fileitem.path} 整理成功")
|
||||||
# 返回整理后的路径
|
# 返回整理后的路径
|
||||||
@@ -875,7 +882,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
message=f"未识别到文件集数",
|
message=f"未识别到文件集数",
|
||||||
fileitem=fileitem,
|
fileitem=fileitem,
|
||||||
fail_list=[fileitem.path],
|
fail_list=[fileitem.path],
|
||||||
transfer_type=transfer_type)
|
transfer_type=transfer_type,
|
||||||
|
need_notify=need_notify)
|
||||||
|
|
||||||
# 文件结束季为空
|
# 文件结束季为空
|
||||||
in_meta.end_season = None
|
in_meta.end_season = None
|
||||||
@@ -938,7 +946,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
target_item=target_item,
|
target_item=target_item,
|
||||||
target_diritem=target_diritem,
|
target_diritem=target_diritem,
|
||||||
fail_list=[fileitem.path],
|
fail_list=[fileitem.path],
|
||||||
transfer_type=transfer_type)
|
transfer_type=transfer_type,
|
||||||
|
need_notify=need_notify)
|
||||||
case 'never':
|
case 'never':
|
||||||
# 存在不覆盖
|
# 存在不覆盖
|
||||||
return TransferInfo(success=False,
|
return TransferInfo(success=False,
|
||||||
@@ -947,7 +956,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
target_item=target_item,
|
target_item=target_item,
|
||||||
target_diritem=target_diritem,
|
target_diritem=target_diritem,
|
||||||
fail_list=[fileitem.path],
|
fail_list=[fileitem.path],
|
||||||
transfer_type=transfer_type)
|
transfer_type=transfer_type,
|
||||||
|
need_notify=need_notify)
|
||||||
case 'latest':
|
case 'latest':
|
||||||
# 仅保留最新版本
|
# 仅保留最新版本
|
||||||
logger.info(f"当前整理覆盖模式设置为仅保留最新版本,将覆盖:{new_file}")
|
logger.info(f"当前整理覆盖模式设置为仅保留最新版本,将覆盖:{new_file}")
|
||||||
@@ -969,7 +979,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
message=err_msg,
|
message=err_msg,
|
||||||
fileitem=fileitem,
|
fileitem=fileitem,
|
||||||
fail_list=[fileitem.path],
|
fail_list=[fileitem.path],
|
||||||
transfer_type=transfer_type)
|
transfer_type=transfer_type,
|
||||||
|
need_notify=need_notify)
|
||||||
|
|
||||||
logger.info(f"文件 {fileitem.path} 整理成功")
|
logger.info(f"文件 {fileitem.path} 整理成功")
|
||||||
return TransferInfo(success=True,
|
return TransferInfo(success=True,
|
||||||
@@ -981,7 +992,8 @@ class FileManagerModule(_ModuleBase):
|
|||||||
file_list=[fileitem.path],
|
file_list=[fileitem.path],
|
||||||
file_list_new=[new_item.path],
|
file_list_new=[new_item.path],
|
||||||
need_scrape=need_scrape,
|
need_scrape=need_scrape,
|
||||||
transfer_type=transfer_type)
|
transfer_type=transfer_type,
|
||||||
|
need_notify=need_notify)
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def __get_naming_dict(meta: MetaBase, mediainfo: MediaInfo, file_ext: str = None,
|
def __get_naming_dict(meta: MetaBase, mediainfo: MediaInfo, file_ext: str = None,
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
import shutil
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Set, Tuple, Optional, Union, List
|
from typing import Set, Tuple, Optional, Union, List
|
||||||
|
|
||||||
@@ -14,7 +13,6 @@ from app.modules.qbittorrent.qbittorrent import Qbittorrent
|
|||||||
from app.schemas import TransferTorrent, DownloadingTorrent
|
from app.schemas import TransferTorrent, DownloadingTorrent
|
||||||
from app.schemas.types import TorrentStatus, ModuleType
|
from app.schemas.types import TorrentStatus, ModuleType
|
||||||
from app.utils.string import StringUtils
|
from app.utils.string import StringUtils
|
||||||
from app.utils.system import SystemUtils
|
|
||||||
|
|
||||||
|
|
||||||
class QbittorrentModule(_ModuleBase, _DownloaderBase[Qbittorrent]):
|
class QbittorrentModule(_ModuleBase, _DownloaderBase[Qbittorrent]):
|
||||||
@@ -269,29 +267,16 @@ class QbittorrentModule(_ModuleBase, _DownloaderBase[Qbittorrent]):
|
|||||||
return None
|
return None
|
||||||
return ret_torrents
|
return ret_torrents
|
||||||
|
|
||||||
def transfer_completed(self, hashs: str, path: Path = None,
|
def transfer_completed(self, hashs: str, downloader: str = None) -> None:
|
||||||
downloader: str = None, transfer_type: str = None) -> None:
|
|
||||||
"""
|
"""
|
||||||
转移完成后的处理
|
转移完成后的处理
|
||||||
:param hashs: 种子Hash
|
:param hashs: 种子Hash
|
||||||
:param path: 源目录
|
|
||||||
:param downloader: 下载器
|
:param downloader: 下载器
|
||||||
:param transfer_type: 整理方式
|
|
||||||
"""
|
"""
|
||||||
server: Qbittorrent = self.get_instance(downloader)
|
server: Qbittorrent = self.get_instance(downloader)
|
||||||
if not server:
|
if not server:
|
||||||
return None
|
return None
|
||||||
server.set_torrents_tag(ids=hashs, tags=['已整理'])
|
server.set_torrents_tag(ids=hashs, tags=['已整理'])
|
||||||
# 移动模式删除种子
|
|
||||||
if transfer_type and transfer_type in ["move"]:
|
|
||||||
if self.remove_torrents(hashs):
|
|
||||||
logger.info(f"移动模式删除种子成功:{hashs} ")
|
|
||||||
# 删除本地残留文件
|
|
||||||
if path and path.exists():
|
|
||||||
files = SystemUtils.list_files(path, settings.RMT_MEDIAEXT)
|
|
||||||
if not files:
|
|
||||||
logger.warn(f"删除残留文件夹:{path}")
|
|
||||||
shutil.rmtree(path, ignore_errors=True)
|
|
||||||
|
|
||||||
def remove_torrents(self, hashs: Union[str, list], delete_file: bool = True,
|
def remove_torrents(self, hashs: Union[str, list], delete_file: bool = True,
|
||||||
downloader: str = None) -> Optional[bool]:
|
downloader: str = None) -> Optional[bool]:
|
||||||
|
|||||||
@@ -1,4 +1,3 @@
|
|||||||
import shutil
|
|
||||||
from pathlib import Path
|
from pathlib import Path
|
||||||
from typing import Set, Tuple, Optional, Union, List
|
from typing import Set, Tuple, Optional, Union, List
|
||||||
|
|
||||||
@@ -14,7 +13,6 @@ from app.modules.transmission.transmission import Transmission
|
|||||||
from app.schemas import TransferTorrent, DownloadingTorrent
|
from app.schemas import TransferTorrent, DownloadingTorrent
|
||||||
from app.schemas.types import TorrentStatus, ModuleType
|
from app.schemas.types import TorrentStatus, ModuleType
|
||||||
from app.utils.string import StringUtils
|
from app.utils.string import StringUtils
|
||||||
from app.utils.system import SystemUtils
|
|
||||||
|
|
||||||
|
|
||||||
class TransmissionModule(_ModuleBase, _DownloaderBase[Transmission]):
|
class TransmissionModule(_ModuleBase, _DownloaderBase[Transmission]):
|
||||||
@@ -256,14 +254,11 @@ class TransmissionModule(_ModuleBase, _DownloaderBase[Transmission]):
|
|||||||
return None
|
return None
|
||||||
return ret_torrents
|
return ret_torrents
|
||||||
|
|
||||||
def transfer_completed(self, hashs: str, path: Path = None,
|
def transfer_completed(self, hashs: str, downloader: str = None) -> None:
|
||||||
downloader: str = None, transfer_type: str = None) -> None:
|
|
||||||
"""
|
"""
|
||||||
转移完成后的处理
|
转移完成后的处理
|
||||||
:param hashs: 种子Hash
|
:param hashs: 种子Hash
|
||||||
:param path: 源目录
|
|
||||||
:param downloader: 下载器
|
:param downloader: 下载器
|
||||||
:param transfer_type: 整理方式
|
|
||||||
"""
|
"""
|
||||||
# 获取下载器
|
# 获取下载器
|
||||||
server: Transmission = self.get_instance(downloader)
|
server: Transmission = self.get_instance(downloader)
|
||||||
@@ -277,16 +272,6 @@ class TransmissionModule(_ModuleBase, _DownloaderBase[Transmission]):
|
|||||||
else:
|
else:
|
||||||
tags = ['已整理']
|
tags = ['已整理']
|
||||||
server.set_torrent_tag(ids=hashs, tags=tags)
|
server.set_torrent_tag(ids=hashs, tags=tags)
|
||||||
# 移动模式删除种子
|
|
||||||
if transfer_type and transfer_type in ["move"]:
|
|
||||||
if self.remove_torrents(hashs):
|
|
||||||
logger.info(f"移动模式删除种子成功:{hashs} ")
|
|
||||||
# 删除本地残留文件
|
|
||||||
if path and path.exists():
|
|
||||||
files = SystemUtils.list_files(path, settings.RMT_MEDIAEXT)
|
|
||||||
if not files:
|
|
||||||
logger.warn(f"删除残留文件夹:{path}")
|
|
||||||
shutil.rmtree(path, ignore_errors=True)
|
|
||||||
|
|
||||||
def remove_torrents(self, hashs: Union[str, list], delete_file: bool = True,
|
def remove_torrents(self, hashs: Union[str, list], delete_file: bool = True,
|
||||||
downloader: str = None) -> Optional[bool]:
|
downloader: str = None) -> Optional[bool]:
|
||||||
|
|||||||
+8
-13
@@ -383,8 +383,7 @@ class Monitor(metaclass=Singleton):
|
|||||||
return
|
return
|
||||||
|
|
||||||
# 查询转移目的目录
|
# 查询转移目的目录
|
||||||
dir_info = self.directoryhelper.get_dir(mediainfo, src_path=Path(mon_path))
|
if not self.directoryhelper.get_dir(mediainfo, src_path=Path(mon_path)):
|
||||||
if not dir_info:
|
|
||||||
logger.warn(f"{event_path.name} 未找到对应的目标目录")
|
logger.warn(f"{event_path.name} 未找到对应的目标目录")
|
||||||
return
|
return
|
||||||
|
|
||||||
@@ -416,11 +415,7 @@ class Monitor(metaclass=Singleton):
|
|||||||
transferinfo: TransferInfo = self.chain.transfer(fileitem=file_item,
|
transferinfo: TransferInfo = self.chain.transfer(fileitem=file_item,
|
||||||
meta=file_meta,
|
meta=file_meta,
|
||||||
mediainfo=mediainfo,
|
mediainfo=mediainfo,
|
||||||
transfer_type=dir_info.transfer_type,
|
episodes_info=episodes_info)
|
||||||
target_storage=dir_info.library_storage,
|
|
||||||
target_path=Path(dir_info.library_path),
|
|
||||||
episodes_info=episodes_info,
|
|
||||||
scrape=dir_info.scraping)
|
|
||||||
|
|
||||||
if not transferinfo:
|
if not transferinfo:
|
||||||
logger.error("文件转移模块运行失败")
|
logger.error("文件转移模块运行失败")
|
||||||
@@ -432,7 +427,7 @@ class Monitor(metaclass=Singleton):
|
|||||||
# 新增转移失败历史记录
|
# 新增转移失败历史记录
|
||||||
self.transferhis.add_fail(
|
self.transferhis.add_fail(
|
||||||
fileitem=file_item,
|
fileitem=file_item,
|
||||||
mode=dir_info.transfer_type,
|
mode=transferinfo.transfer_type if transferinfo else '',
|
||||||
download_hash=download_hash,
|
download_hash=download_hash,
|
||||||
meta=file_meta,
|
meta=file_meta,
|
||||||
mediainfo=mediainfo,
|
mediainfo=mediainfo,
|
||||||
@@ -453,15 +448,15 @@ class Monitor(metaclass=Singleton):
|
|||||||
# 新增转移成功历史记录
|
# 新增转移成功历史记录
|
||||||
self.transferhis.add_success(
|
self.transferhis.add_success(
|
||||||
fileitem=file_item,
|
fileitem=file_item,
|
||||||
mode=dir_info.transfer_type,
|
mode=transferinfo.transfer_type if transferinfo else '',
|
||||||
download_hash=download_hash,
|
download_hash=download_hash,
|
||||||
meta=file_meta,
|
meta=file_meta,
|
||||||
mediainfo=mediainfo,
|
mediainfo=mediainfo,
|
||||||
transferinfo=transferinfo
|
transferinfo=transferinfo
|
||||||
)
|
)
|
||||||
|
|
||||||
# TODO 汇总刮削
|
# 汇总刮削
|
||||||
if dir_info.scraping:
|
if transferinfo.need_scrape:
|
||||||
self.mediaChain.scrape_metadata(fileitem=transferinfo.target_diritem,
|
self.mediaChain.scrape_metadata(fileitem=transferinfo.target_diritem,
|
||||||
meta=file_meta,
|
meta=file_meta,
|
||||||
mediainfo=mediainfo)
|
mediainfo=mediainfo)
|
||||||
@@ -475,11 +470,11 @@ class Monitor(metaclass=Singleton):
|
|||||||
})
|
})
|
||||||
|
|
||||||
# 发送消息汇总
|
# 发送消息汇总
|
||||||
if dir_info.notify:
|
if transferinfo.need_notify:
|
||||||
self.__collect_msg_medias(mediainfo=mediainfo, file_meta=file_meta, transferinfo=transferinfo)
|
self.__collect_msg_medias(mediainfo=mediainfo, file_meta=file_meta, transferinfo=transferinfo)
|
||||||
|
|
||||||
# 移动模式删除空目录
|
# 移动模式删除空目录
|
||||||
if dir_info.transfer_type in ["move"]:
|
if transferinfo.transfer_type in ["move"]:
|
||||||
logger.info(f"正在删除: {file_item.storage} {file_item.path}")
|
logger.info(f"正在删除: {file_item.storage} {file_item.path}")
|
||||||
self.storagechain.delete_file(file_item)
|
self.storagechain.delete_file(file_item)
|
||||||
|
|
||||||
|
|||||||
@@ -127,9 +127,9 @@ class TransferDirectoryConf(BaseModel):
|
|||||||
renaming: Optional[bool] = False
|
renaming: Optional[bool] = False
|
||||||
# 刮削
|
# 刮削
|
||||||
scraping: Optional[bool] = False
|
scraping: Optional[bool] = False
|
||||||
|
# 是否发送通知
|
||||||
|
notify: Optional[bool] = True
|
||||||
# 媒体库类型子目录
|
# 媒体库类型子目录
|
||||||
library_type_folder: Optional[bool] = False
|
library_type_folder: Optional[bool] = False
|
||||||
# 媒体库类别子目录
|
# 媒体库类别子目录
|
||||||
library_category_folder: Optional[bool] = False
|
library_category_folder: Optional[bool] = False
|
||||||
# 是否发送通知
|
|
||||||
notify: Optional[bool] = True
|
|
||||||
|
|||||||
@@ -66,6 +66,8 @@ class TransferInfo(BaseModel):
|
|||||||
message: Optional[str] = None
|
message: Optional[str] = None
|
||||||
# 是否需要刮削
|
# 是否需要刮削
|
||||||
need_scrape: Optional[bool] = False
|
need_scrape: Optional[bool] = False
|
||||||
|
# 是否需要通知
|
||||||
|
need_notify: Optional[bool] = False
|
||||||
|
|
||||||
def to_dict(self):
|
def to_dict(self):
|
||||||
"""
|
"""
|
||||||
|
|||||||
Reference in New Issue
Block a user