Skip to content

Commit

Permalink
Add stopping download after metadata functionality
Browse files Browse the repository at this point in the history
  • Loading branch information
qstokkink committed Feb 21, 2025
1 parent d2a9871 commit 863f4ed
Show file tree
Hide file tree
Showing 10 changed files with 63 additions and 8 deletions.
13 changes: 13 additions & 0 deletions src/tribler/core/libtorrent/download_manager/download.py
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,9 @@ def __init__(self, # noqa: PLR0913
if self.download_manager.config.get("libtorrent/check_after_complete"):
self.register_task("Recheck torrent after finish", self._recheck_after_finish)

if config and config.get_stop_after_metainfo():
self.stop_after_metainfo()

alert_handlers = {"tracker_reply_alert": self.on_tracker_reply_alert,
"tracker_error_alert": self.on_tracker_error_alert,
"tracker_warning_alert": self.on_tracker_warning_alert,
Expand Down Expand Up @@ -185,6 +188,16 @@ async def _recheck_after_finish(self) -> None:
await self.future_finished
self.force_recheck()

@task
async def stop_after_metainfo(self) -> None:
"""
Wait for the metadata to be received, then stop.
"""
self.config.set_stop_after_metainfo(True) # Persist between restarts
await self.future_metainfo
await self.stop()
self.config.set_stop_after_metainfo(False) # We succeeded without shutdown: no longer persist

def add_stream(self) -> None:
"""
Initialize a stream for this download.
Expand Down
13 changes: 13 additions & 0 deletions src/tribler/core/libtorrent/download_manager/download_config.py
Original file line number Diff line number Diff line change
Expand Up @@ -78,6 +78,7 @@ def write(self) -> None: ... # noqa: D102
add_download_to_channel = boolean(default=False)
saveas = string(default=None)
completed_dir = string(default=None)
stop_after_metainfo = boolean(default=False)
[state]
metainfo = string(default='ZGU=')
Expand Down Expand Up @@ -312,3 +313,15 @@ def get_engineresumedata(self) -> dict | None:
Get the engine resume data dict for this download or None if it cannot be decoded.
"""
return _to_dict(self.config["state"]["engineresumedata"])

def set_stop_after_metainfo(self, value: bool) -> None:
"""
Set the download to stop after receiving the metainfo.
"""
self.config["download_defaults"]["stop_after_metainfo"] = value

def get_stop_after_metainfo(self) -> bool:
"""
Get whether the download should stop after receiving the metainfo.
"""
return self.config["download_defaults"].get("stop_after_metainfo", False)
25 changes: 17 additions & 8 deletions src/tribler/core/libtorrent/restapi/downloads_endpoint.py
Original file line number Diff line number Diff line change
Expand Up @@ -394,22 +394,29 @@ def _get_default_trackers(self) -> list[bytes]:
summary="Start a download from a provided URI.",
parameters=[{
"in": "query",
"name": "get_peers",
"description": "Flag indicating whether or not to include peers",
"type": "boolean",
"name": "anon_hops",
"description": "Number of hops for the anonymous download. No hops is equivalent to a plain download",
"type": "integer",
"required": False
},
{
"in": "query",
"name": "get_pieces",
"description": "Flag indicating whether or not to include pieces",
"name": "safe_seeding",
"description": "Whether the seeding of the download should be anonymous or not",
"type": "boolean",
"required": False
},
{
"in": "query",
"name": "get_files",
"description": "Flag indicating whether or not to include files",
"name": "destination",
"description": "The download destination path of the torrent",
"type": "string",
"required": False
},
{
"in": "query",
"name": "only_metadata",
"description": "Stop the download after the metadata has been received",
"type": "boolean",
"required": False
}],
Expand All @@ -423,7 +430,7 @@ def _get_default_trackers(self) -> list[bytes]:
@json_schema(schema(AddDownloadRequest={
"anon_hops": (Integer, "Number of hops for the anonymous download. No hops is equivalent to a plain download"),
"safe_seeding": (Boolean, "Whether the seeding of the download should be anonymous or not"),
"destination": (String, "the download destination path of the torrent"),
"destination": (String, "The download destination path of the torrent"),
"uri*": (String, "The URI of the torrent file that should be downloaded. This URI can either represent a file "
"location, a magnet link or a HTTP(S) url."),
}))
Expand Down Expand Up @@ -471,6 +478,8 @@ async def add_download(self, request: Request) -> RESTResponse: # noqa: C901, P
if self.download_manager.config.get("libtorrent/download_defaults/trackers_file"):
await download.get_handle() # We can only add trackers to a valid handle, wait for it.
download.add_trackers(self._get_default_trackers())
if params.get("only_metadata", "false") != "false":
download.stop_after_metainfo()
except Exception as e:
return RESTResponse({"error": {
"handled": True,
Expand Down
1 change: 1 addition & 0 deletions src/tribler/ui/public/locales/en_US.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"AlwaysAsk": "Always ask download settings",
"DownloadAnon": "Download anonymously using proxies",
"SeedAnon": "Encrypted anonymous seeding using proxies",
"StopAfterMetadata": "Stop download after metadata is received",
"TorrentWatchFolder": "Torrent watch folder",
"WatchFolder": "Watch Folder",
"EnableWatchFolder": "Enable watch folder (requires restart)",
Expand Down
1 change: 1 addition & 0 deletions src/tribler/ui/public/locales/es_ES.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"AlwaysAsk": "¿Preguntar siempre donde guardar las descargas?",
"DownloadAnon": "Descarga anónima mediante proxies",
"SeedAnon": "Siembra anónima cifrada mediante proxies",
"StopAfterMetadata": "Detener la descarga después de que se reciba los metadatos",
"TorrentWatchFolder": "Carpeta de seguimiento de torrents",
"WatchFolder": "Carpeta de seguimiento",
"EnableWatchFolder": "Habilitar carpeta de vigilancia (es necesario reiniciar)",
Expand Down
1 change: 1 addition & 0 deletions src/tribler/ui/public/locales/ko_KR.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"AlwaysAsk": "항상 내려받기 설정 확인",
"DownloadAnon": "프록시를 사용하여 익명으로 내려받기",
"SeedAnon": "프록시를 사용하여 암호화된 익명 시딩",
"StopAfterMetadata": "메타 데이터를받은 후 다운로드 중지",
"TorrentWatchFolder": "토렌트 폴더 보기",
"WatchFolder": "폴더 보기",
"EnableWatchFolder": "감시 폴더 활성화(다시 시작해야 함)",
Expand Down
1 change: 1 addition & 0 deletions src/tribler/ui/public/locales/pt_BR.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"AlwaysAsk": "Sempre peça configurações de download",
"DownloadAnon": "Baixe anonimamente usando proxies",
"SeedAnon": "Semear anonimamente usando proxies",
"StopAfterMetadata": "Parar do download após os metadados forem recebidos",
"TorrentWatchFolder": "Observar pasta torrent",
"WatchFolder": "Monitoramento de pasta",
"EnableWatchFolder": "Ativar pasta monitorada (requer reinicialização)",
Expand Down
1 change: 1 addition & 0 deletions src/tribler/ui/public/locales/ru_RU.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"AlwaysAsk": "Всегда спрашивать настройки закачки",
"DownloadAnon": "Загружать торренты анонимно (через других участников)",
"SeedAnon": "Раздавать торренты анонимно (через других участников)",
"StopAfterMetadata": "Остановите загрузку после получения метаданных",
"TorrentWatchFolder": "Папка автоскачивания:",
"WatchFolder": "Автоскачивание торрентов из папки",
"EnableWatchFolder": "Включить папку просмотра (требуется перезагрузка)",
Expand Down
1 change: 1 addition & 0 deletions src/tribler/ui/public/locales/zh_CN.json
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
"AlwaysAsk": "总是询问下载设置",
"DownloadAnon": "使用代理匿名下载",
"SeedAnon": "使用代理加密地匿名做种",
"StopAfterMetadata": "收到元数据后停止下载",
"TorrentWatchFolder": "种子监视文件夹",
"WatchFolder": "监视文件夹",
"EnableWatchFolder": "启用监视文件夹(需要重新启动)",
Expand Down
14 changes: 14 additions & 0 deletions src/tribler/ui/src/dialogs/SaveAs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -290,6 +290,20 @@ export default function SaveAs(props: SaveAsProps & JSX.IntrinsicAttributes & Di
{t('SeedAnon')}
</label>
</div>
<div className="flex items-center space-x-2">
<Checkbox
checked={params.only_metadata}
hidden={files.length !== 0}
onCheckedChange={(value) => setParams({ ...params, only_metadata: !!value })}
id="only_metadata" />
<label
htmlFor="only_metadata"
hidden={files.length !== 0}
className="text-sm font-medium leading-none peer-disabled:cursor-not-allowed peer-disabled:opacity-70"
>
{t('StopAfterMetadata')}
</label>
</div>
<DialogFooter>
{warning && (
<div className="flex flex-row text-muted-foreground space-x-2">
Expand Down

0 comments on commit 863f4ed

Please sign in to comment.