Fixed issues with retrying and cancelling torrents.

This commit is contained in:
Roger Far 2021-10-28 08:29:42 -06:00
parent 799316413a
commit 0d5d28483b
8 changed files with 111 additions and 50 deletions

View file

@ -4,6 +4,10 @@ All notable changes to this project will be documented in this file.
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
## [1.9.4] - 2021-10-28
### Changed
- Fixed issues retrying torrents after multiple failed downloads in large torrents.
## [1.9.3] - 2021-10-27
### Changed
- Fixed issue with the unpack queue.

View file

@ -55,7 +55,7 @@
<a class="navbar-item"> Profile </a>
<a class="navbar-item" (click)="logout()"> Logout </a>
<hr class="navbar-divider" />
<div class="navbar-item">Version 1.9.3</div>
<div class="navbar-item">Version 1.9.4</div>
</div>
</div>
</div>

View file

@ -1,6 +1,6 @@
{
"name": "rdt-client",
"version": "1.9.3",
"version": "1.9.4",
"description": "This is a web interface to manage your torrents on Real-Debrid.",
"main": "index.js",
"dependencies": {

View file

@ -90,6 +90,9 @@ namespace RdtClient.Service.Services
public async Task Cancel()
{
Finished = true;
Error = null;
if (Downloader == null)
{
return;

View file

@ -168,6 +168,10 @@ namespace RdtClient.Service.Services.Downloaders
if (download == null)
{
DownloadComplete?.Invoke(this, new DownloadCompleteEventArgs
{
Error = $"Download was not found in Aria2"
});
return;
}

View file

@ -4,9 +4,11 @@ using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Net.Http;
using System.Threading;
using System.Threading.Tasks;
using System.Web;
using Aria2NET;
using Microsoft.Extensions.DependencyInjection;
using Microsoft.Extensions.Logging;
using Newtonsoft.Json;
using RdtClient.Data.Enums;
@ -27,15 +29,19 @@ namespace RdtClient.Service.Services
public static readonly ConcurrentDictionary<Guid, DownloadClient> ActiveDownloadClients = new();
public static readonly ConcurrentDictionary<Guid, UnpackClient> ActiveUnpackClients = new();
public static readonly SemaphoreSlim TorrentResetLock = new(1, 1);
private readonly ILogger<TorrentRunner> _logger;
private readonly IServiceProvider _serviceProvider;
private readonly Torrents _torrents;
private readonly Downloads _downloads;
private readonly RemoteService _remoteService;
private readonly HttpClient _httpClient;
public TorrentRunner(ILogger<TorrentRunner> logger, Torrents torrents, Downloads downloads, RemoteService remoteService)
public TorrentRunner(ILogger<TorrentRunner> logger, IServiceProvider serviceProvider, Torrents torrents, Downloads downloads, RemoteService remoteService)
{
_logger = logger;
_serviceProvider = serviceProvider;
_torrents = torrents;
_downloads = downloads;
_remoteService = remoteService;
@ -185,9 +191,17 @@ namespace RdtClient.Service.Services
{
Log($"Retrying torrent", download, download.Torrent);
await _torrents.RetryTorrent(download.TorrentId, download.Torrent.RetryCount + 1);
_ = Task.Run(async () =>
{
using var blockScope = _serviceProvider.CreateScope();
var torrentsService = (Torrents) blockScope.ServiceProvider.GetService(typeof(Torrents));
await torrentsService.RetryTorrent(download.TorrentId, download.Torrent.RetryCount + 1);
});
continue;
// Force a delay and return the main loop to prevent concurrency issues.
await Task.Delay(10000);
return;
}
else
{
@ -468,8 +482,17 @@ namespace RdtClient.Service.Services
{
Log($"Retrying torrent", torrent);
await _torrents.RetryTorrent(torrent.TorrentId, torrent.RetryCount + 1);
continue;
_ = Task.Run(async () =>
{
using var blockScope = _serviceProvider.CreateScope();
var torrentsService = (Torrents) blockScope.ServiceProvider.GetService(typeof(Torrents));
await torrentsService.RetryTorrent(torrent.TorrentId, torrent.RetryCount + 1);
});
// Force a delay and return the main loop to prevent concurrency issues.
await Task.Delay(10000);
return;
}
Log($"Received RealDebrid error: {torrent.RdStatusRaw}, not processing further", torrent);

View file

@ -27,6 +27,8 @@ namespace RdtClient.Service.Services
private readonly ITorrentClient _torrentClient;
public static readonly SemaphoreSlim TorrentResetLock = new(1, 1);
public Torrents(ILogger<Torrents> logger,
TorrentData torrentData,
Downloads downloads,
@ -219,6 +221,8 @@ namespace RdtClient.Service.Services
Log($"Deleting", torrent);
await UpdateComplete(torrentId, DateTimeOffset.UtcNow);
foreach (var download in torrent.Downloads)
{
while (TorrentRunner.ActiveDownloadClients.TryGetValue(download.DownloadId, out var downloadClient))
@ -359,59 +363,82 @@ namespace RdtClient.Service.Services
public async Task RetryTorrent(Guid torrentId, Int32 retryCount)
{
var torrent = await _torrentData.GetById(torrentId);
await TorrentResetLock.WaitAsync();
if (torrent == null)
try
{
return;
}
var torrent = await _torrentData.GetById(torrentId);
Log($"Retrying Torrent", torrent);
foreach (var download in torrent.Downloads)
{
while (TorrentRunner.ActiveDownloadClients.TryGetValue(download.DownloadId, out var downloadClient))
if (torrent == null)
{
await downloadClient.Cancel();
await Task.Delay(100);
return;
}
while (TorrentRunner.ActiveUnpackClients.TryGetValue(download.DownloadId, out var unpackClient))
Log($"Retrying Torrent", torrent);
await UpdateComplete(torrent.TorrentId, DateTimeOffset.Now);
foreach (var download in torrent.Downloads)
{
unpackClient.Cancel();
await Task.Delay(100);
await _downloads.UpdateError(download.DownloadId, null);
await _downloads.UpdateCompleted(download.DownloadId, DateTimeOffset.Now);
}
foreach (var download in torrent.Downloads)
{
while (TorrentRunner.ActiveDownloadClients.TryGetValue(download.DownloadId, out var downloadClient))
{
await downloadClient.Cancel();
await Task.Delay(100);
}
while (TorrentRunner.ActiveUnpackClients.TryGetValue(download.DownloadId, out var unpackClient))
{
unpackClient.Cancel();
await Task.Delay(100);
}
}
await Delete(torrentId, true, true, true);
if (String.IsNullOrWhiteSpace(torrent.FileOrMagnet))
{
throw new Exception($"Cannot re-add this torrent, original magnet or file not found");
}
Torrent newTorrent;
if (torrent.IsFile)
{
var bytes = Convert.FromBase64String(torrent.FileOrMagnet);
newTorrent = await UploadFile(bytes,
torrent.Category,
torrent.DownloadAction,
torrent.FinishedAction,
torrent.DownloadMinSize,
torrent.DownloadManualFiles,
torrent.Priority);
}
else
{
newTorrent = await UploadMagnet(torrent.FileOrMagnet,
torrent.Category,
torrent.DownloadAction,
torrent.FinishedAction,
torrent.DownloadMinSize,
torrent.DownloadManualFiles,
torrent.Priority);
}
await _torrentData.UpdateRetryCount(newTorrent.TorrentId, retryCount);
}
await Delete(torrentId, true, true, true);
if (String.IsNullOrWhiteSpace(torrent.FileOrMagnet))
finally
{
throw new Exception($"Cannot re-add this torrent, original magnet or file not found");
TorrentResetLock.Release();
}
Torrent newTorrent;
if (torrent.IsFile)
{
var bytes = Convert.FromBase64String(torrent.FileOrMagnet);
newTorrent = await UploadFile(bytes, torrent.Category, torrent.DownloadAction, torrent.FinishedAction, torrent.DownloadMinSize, torrent.DownloadManualFiles, torrent.Priority);
}
else
{
newTorrent = await UploadMagnet(torrent.FileOrMagnet,
torrent.Category,
torrent.DownloadAction,
torrent.FinishedAction,
torrent.DownloadMinSize,
torrent.DownloadManualFiles,
torrent.Priority);
}
await _torrentData.UpdateRetryCount(newTorrent.TorrentId, retryCount);
}
public async Task RetryDownload(Guid downloadId)

View file

@ -4,7 +4,7 @@
<TargetFramework>net5.0</TargetFramework>
<OutputType>Exe</OutputType>
<UserSecretsId>94c24cba-f03f-4453-a671-3640b517c573</UserSecretsId>
<Version>1.9.3</Version>
<Version>1.9.4</Version>
</PropertyGroup>
<ItemGroup>