diff --git a/README.md b/README.md
index 49d5b2d3..bf9f1dc7 100644
--- a/README.md
+++ b/README.md
@@ -107,6 +107,7 @@ services:
- QUEUECLEANER__STALLED_IGNORE_PRIVATE=false
- CONTENTBLOCKER__ENABLED=true
+ - CONTENTBLOCKER__IGNORE_PRIVATE=true
- CONTENTBLOCKER__BLACKLIST__ENABLED=true
- CONTENTBLOCKER__BLACKLIST__PATH=https://raw.githubusercontent.com/flmorg/cleanuperr/refs/heads/main/blacklist
# OR
@@ -166,6 +167,7 @@ services:
| QUEUECLEANER__STALLED_IGNORE_PRIVATE | No | Whether to ignore stalled downloads from private trackers | false |
|||||
| CONTENTBLOCKER__ENABLED | No | Enable or disable the content blocker | false |
+| CONTENTBLOCKER__IGNORE_PRIVATE | No | Whether to ignore downloads from private trackers | false |
| CONTENTBLOCKER__BLACKLIST__ENABLED | Yes if content blocker is enabled and whitelist is not enabled | Enable or disable the blacklist | false |
| CONTENTBLOCKER__BLACKLIST__PATH | Yes if blacklist is enabled | Path to the blacklist (local file or url)
Needs to be json compatible | empty |
| CONTENTBLOCKER__WHITELIST__ENABLED | Yes if content blocker is enabled and blacklist is not enabled | Enable or disable the whitelist | false |
diff --git a/code/Common/Configuration/ContentBlocker/ContentBlockerConfig.cs b/code/Common/Configuration/ContentBlocker/ContentBlockerConfig.cs
index 1e50a5b1..5d57f58a 100644
--- a/code/Common/Configuration/ContentBlocker/ContentBlockerConfig.cs
+++ b/code/Common/Configuration/ContentBlocker/ContentBlockerConfig.cs
@@ -1,4 +1,6 @@
-namespace Common.Configuration.ContentBlocker;
+using Microsoft.Extensions.Configuration;
+
+namespace Common.Configuration.ContentBlocker;
public sealed record ContentBlockerConfig : IJobConfig
{
@@ -6,6 +8,9 @@ public sealed record ContentBlockerConfig : IJobConfig
public required bool Enabled { get; init; }
+ [ConfigurationKeyName("IGNORE_PRIVATE")]
+ public bool IgnorePrivate { get; init; }
+
public PatternConfig? Blacklist { get; init; }
public PatternConfig? Whitelist { get; init; }
diff --git a/code/Executable/appsettings.Development.json b/code/Executable/appsettings.Development.json
index c217c5c0..ffa7f62a 100644
--- a/code/Executable/appsettings.Development.json
+++ b/code/Executable/appsettings.Development.json
@@ -13,6 +13,7 @@
},
"ContentBlocker": {
"Enabled": true,
+ "IGNORE_PRIVATE": true,
"Blacklist": {
"Enabled": false,
"Path": "https://raw.githubusercontent.com/flmorg/cleanuperr/refs/heads/main/blacklist"
diff --git a/code/Executable/appsettings.json b/code/Executable/appsettings.json
index dd9d597a..df6894ce 100644
--- a/code/Executable/appsettings.json
+++ b/code/Executable/appsettings.json
@@ -13,6 +13,7 @@
},
"ContentBlocker": {
"Enabled": false,
+ "IGNORE_PRIVATE": false,
"Blacklist": {
"Enabled": false,
"Path": ""
diff --git a/code/Infrastructure/Verticals/DownloadClient/Deluge/DelugeService.cs b/code/Infrastructure/Verticals/DownloadClient/Deluge/DelugeService.cs
index 0b32e851..62862db2 100644
--- a/code/Infrastructure/Verticals/DownloadClient/Deluge/DelugeService.cs
+++ b/code/Infrastructure/Verticals/DownloadClient/Deluge/DelugeService.cs
@@ -82,6 +82,13 @@ public sealed class DelugeService : DownloadServiceBase
return;
}
+ if (_queueCleanerConfig.StalledIgnorePrivate && status.Private)
+ {
+ // ignore private trackers
+ _logger.LogDebug("skip files check | download is private | {name}", status.Name);
+ return;
+ }
+
DelugeContents? contents = null;
try
diff --git a/code/Infrastructure/Verticals/DownloadClient/QBittorrent/QBitService.cs b/code/Infrastructure/Verticals/DownloadClient/QBittorrent/QBitService.cs
index deeb571a..d918f2dd 100644
--- a/code/Infrastructure/Verticals/DownloadClient/QBittorrent/QBitService.cs
+++ b/code/Infrastructure/Verticals/DownloadClient/QBittorrent/QBitService.cs
@@ -83,6 +83,34 @@ public sealed class QBitService : DownloadServiceBase
public override async Task BlockUnwantedFilesAsync(string hash)
{
+ TorrentInfo? torrent = (await _client.GetTorrentListAsync(new TorrentListQuery { Hashes = [hash] }))
+ .FirstOrDefault();
+
+ if (torrent is null)
+ {
+ _logger.LogDebug("failed to find torrent {hash} in the download client", hash);
+ return;
+ }
+
+ TorrentProperties? torrentProperties = await _client.GetTorrentPropertiesAsync(hash);
+
+ if (torrentProperties is null)
+ {
+ _logger.LogDebug("failed to find torrent properties {hash} in the download client", hash);
+ return;
+ }
+
+ bool isPrivate = torrentProperties.AdditionalData.TryGetValue("is_private", out var dictValue) &&
+ bool.TryParse(dictValue?.ToString(), out bool boolValue)
+ && boolValue;
+
+ if (_queueCleanerConfig.StalledIgnorePrivate && isPrivate)
+ {
+ // ignore private trackers
+ _logger.LogDebug("skip files check | download is private | {name}", torrent.Name);
+ return;
+ }
+
IReadOnlyList? files = await _client.GetTorrentContentsAsync(hash);
if (files is null)
diff --git a/code/Infrastructure/Verticals/DownloadClient/Transmission/TransmissionService.cs b/code/Infrastructure/Verticals/DownloadClient/Transmission/TransmissionService.cs
index 48821f6c..070a80d3 100644
--- a/code/Infrastructure/Verticals/DownloadClient/Transmission/TransmissionService.cs
+++ b/code/Infrastructure/Verticals/DownloadClient/Transmission/TransmissionService.cs
@@ -81,6 +81,13 @@ public sealed class TransmissionService : DownloadServiceBase
{
return;
}
+
+ if (_queueCleanerConfig.StalledIgnorePrivate && (torrent.IsPrivate ?? false))
+ {
+ // ignore private trackers
+ _logger.LogDebug("skip files check | download is private | {name}", torrent.Name);
+ return;
+ }
List unwantedFiles = [];
diff --git a/code/test/docker-compose.yml b/code/test/docker-compose.yml
index 7b3a2e6b..e6a5c508 100644
--- a/code/test/docker-compose.yml
+++ b/code/test/docker-compose.yml
@@ -188,6 +188,7 @@ services:
- QUEUECLEANER__STALLED_IGNORE_PRIVATE=true
- CONTENTBLOCKER__ENABLED=true
+ - CONTENTBLOCKER__IGNORE_PRIVATE=true
- CONTENTBLOCKER__BLACKLIST__ENABLED=true
- CONTENTBLOCKER__BLACKLIST__PATH=https://raw.githubusercontent.com/flmorg/cleanuperr/refs/heads/main/blacklist
# OR