Add ability to control Deluge's upload and download speeds based on Jellyfin streams.
This commit is contained in:
147
controllers/deluge.php
Normal file
147
controllers/deluge.php
Normal file
@@ -0,0 +1,147 @@
|
||||
<?php
|
||||
/**
|
||||
* Copyright 2026, Dreytac <dreytac@hobbyhome.net>
|
||||
*
|
||||
* This file is part of Kirby Deluge.
|
||||
*
|
||||
* Kirby Deluge is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License version 3 as published by the Free Software Foundation.
|
||||
*
|
||||
* Kirby Deluge is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License along with Kirby Deluge. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
return function ($page) {
|
||||
$currentStreams = $page->currentStreams()->toInt();
|
||||
$lastSeen = $page->lastSeen()->toInt();
|
||||
|
||||
$curl = curl_init($page->delugeUrl());
|
||||
$curlOptions = [
|
||||
CURLOPT_RETURNTRANSFER => true,
|
||||
CURLOPT_HEADER => true,
|
||||
CURLOPT_HTTPHEADER => ["Accept: application/json", "Content-Type: application/json"],
|
||||
CURLOPT_ENCODING => "",
|
||||
CURLOPT_COOKIEJAR => "",
|
||||
CURLOPT_CONNECTTIMEOUT => 10,
|
||||
CURLOPT_TIMEOUT => 10,
|
||||
CURLOPT_SSL_VERIFYPEER => true,
|
||||
CURLINFO_HEADER_OUT => true,
|
||||
];
|
||||
curl_setopt_array($curl, $curlOptions);
|
||||
|
||||
$reqId = 0;
|
||||
$response = site()->makeRequest($curl, $reqId, "auth.login", [$page->delugePassword()->toString()]);
|
||||
$reqId++;
|
||||
|
||||
if (get("s") == "inc") {
|
||||
// Increment number of streams and ensure speeds are set to minimums.
|
||||
$currentStreams++;
|
||||
$lastSeen = time();
|
||||
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_download_speed" => $page->minDownSpeed()->toInt()]]);
|
||||
$reqId++;
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_upload_speed" => $page->minUpSpeed()->toInt()]]);
|
||||
} elseif (get("s") == "dec") {
|
||||
// Decrement number of streams and, if 0 active streams, ensure speeds are set to maximum.
|
||||
$currentStreams--;
|
||||
|
||||
if ($lastSeen > 0) {
|
||||
if ($lastSeen < time() - ($page->maxTimeAtMin()->toInt() * 60)) {
|
||||
// Assume the sessions have finished and clear them.
|
||||
$currentStreams = 0;
|
||||
$lastSeen = 0;
|
||||
}
|
||||
}
|
||||
|
||||
if ($currentStreams <= 0) {
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_download_speed" => $page->maxDownSpeed()->toInt()]]);
|
||||
$reqId++;
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_upload_speed" => $page->maxUpSpeed()->toInt()]]);
|
||||
}
|
||||
} elseif (get("s") == "reset") {
|
||||
// Reset streams and speeds back to 0 and maximum respectively.
|
||||
$currentStreams = 0;
|
||||
$lastSeen = 0;
|
||||
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_download_speed" => $page->maxDownSpeed()->toInt()]]);
|
||||
$reqId++;
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_upload_speed" => $page->maxUpSpeed()->toInt()]]);
|
||||
} elseif (get("s") == "update") {
|
||||
// Forceably get a list of active sessions from Jellyfin and update Deluge accordingly.
|
||||
$jfCurl = curl_init($page->jellyfinUrl()->toString() . "/Sessions");
|
||||
$jfCurlOptions = [
|
||||
CURLOPT_RETURNTRANSFER => true,
|
||||
// CURLOPT_HEADER => true,
|
||||
CURLOPT_HTTPHEADER => ["Accept: application/json", "Content-Type: application/json", "Authorization: MediaBrowser Token=\"{$page->jellyfinApiKey()->toString()}\""],
|
||||
CURLOPT_ENCODING => "",
|
||||
CURLOPT_COOKIEJAR => "",
|
||||
CURLOPT_CONNECTTIMEOUT => 10,
|
||||
CURLOPT_TIMEOUT => 10,
|
||||
CURLOPT_SSL_VERIFYPEER => true,
|
||||
CURLINFO_HEADER_OUT => true,
|
||||
CURLOPT_VERBOSE => true,
|
||||
];
|
||||
curl_setopt_array($jfCurl, $jfCurlOptions);
|
||||
|
||||
$sessions = site()->makeRequest($jfCurl, $reqId, "get");
|
||||
$reqId++;
|
||||
curl_close($jfCurl);
|
||||
|
||||
$sessionsActive = 0;
|
||||
if (!is_null($sessions)) {
|
||||
foreach ($sessions as $session) {
|
||||
if (isset($session["NowPlayingItem"])) {
|
||||
if ($session["NowPlayingItem"]["Type"] !== "Audio") {
|
||||
$sessionsActive++;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if ($sessionsActive == 0) {
|
||||
// There are no sessions active. Set to maximum speed.
|
||||
$currentStreams = 0;
|
||||
$lastSeen = 0;
|
||||
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_download_speed" => $page->maxDownSpeed()->toInt()]]);
|
||||
$reqId++;
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_upload_speed" => $page->maxUpSpeed()->toInt()]]);
|
||||
} else {
|
||||
// There are sessions active. Set to minimum speed.
|
||||
$currentStreams = $sessionsActive;
|
||||
$lastSeen = time();
|
||||
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_download_speed" => $page->minDownSpeed()->toInt()]]);
|
||||
$reqId++;
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_upload_speed" => $page->minUpSpeed()->toInt()]]);
|
||||
}
|
||||
} else {
|
||||
// We couldn't access Jellyfin. Assume there's something wrong and that no sessions are active.
|
||||
$currentStreams = 0;
|
||||
$lastSeen = 0;
|
||||
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_download_speed" => $page->maxDownSpeed()->toInt()]]);
|
||||
$reqId++;
|
||||
site()->makeRequest($curl, $reqId, "core.set_config", [["max_upload_speed" => $page->maxUpSpeed()->toInt()]]);
|
||||
}
|
||||
}
|
||||
|
||||
// We should never have less than 0 streams active.
|
||||
$currentStreams = $currentStreams < 0 ? 0 : $currentStreams;
|
||||
|
||||
$page = kirby()->impersonate("kirby", function () use ($page, $currentStreams, $lastSeen) {
|
||||
return $page->update([
|
||||
"currentStreams" => $currentStreams,
|
||||
"lastSeen" => $lastSeen,
|
||||
]);
|
||||
});
|
||||
|
||||
curl_close($curl);
|
||||
|
||||
if (!($user = kirby()->user() and $user->role()->isAdmin())) {
|
||||
// Limit access to page to administrators only.
|
||||
echo new Response(Data::encode(["currentStreams" => $currentStreams, "lastSeen" => $lastSeen], "json"), "text/json");
|
||||
exit();
|
||||
}
|
||||
|
||||
return compact("page");
|
||||
};
|
||||
Reference in New Issue
Block a user