diff --git a/.gitignore b/.gitignore index 9bd9aa6..4895b70 100644 --- a/.gitignore +++ b/.gitignore @@ -143,6 +143,7 @@ venv/ ENV/ env.bak/ venv.bak/ +.python-version # Spyder project settings .spyderproject diff --git a/src/main.py b/src/main.py index 0826dd6..42b98a3 100644 --- a/src/main.py +++ b/src/main.py @@ -1,4 +1,3 @@ -from network.libtorrent_misc import send_notification, update_log, check_deleted_files from utils.logging.loghandler import split_data, check_completed, check_downloads from network.interface import list_interfaces, init_interfaces from PySide6.QtNetwork import QLocalServer, QLocalSocket @@ -9,6 +8,7 @@ from utils.general.shutdown import closehelper from utils.general.wrappers import run_thread from interface.assets.base64_icons import logo_base64 from PySide6.QtWidgets import QSystemTrayIcon, QMenu +from network.libtorrent_misc import AppDaemons from utils.general.shutdown import force_exit from utils.config.config import read_config from PySide6.QtGui import QAction, QPixmap @@ -142,9 +142,8 @@ def main(): init_interfaces() consoleLog(f"Current Bound: {state.bound_interface}") # Start background daemon threads - run_thread(threading.Thread(target=send_notification, args=(state.shutdown_event,), daemon=True)) - run_thread(threading.Thread(target=update_log, args=(state.shutdown_event,), daemon=True)) - run_thread(threading.Thread(target=check_deleted_files, args=(state.shutdown_event,), daemon=True)) + app._daemons = AppDaemons() + app._daemons.start_all() # Start background non-daemon threads run_thread(threading.Thread(target=check_completed, args=(downloads, state.autoresume))) run_thread(threading.Thread(target=check_downloads, args=(downloads,))) diff --git a/src/network/libtorrent_misc.py b/src/network/libtorrent_misc.py index 8eb50ef..6b05e3e 100644 --- a/src/network/libtorrent_misc.py +++ b/src/network/libtorrent_misc.py @@ -1,5 +1,6 @@ from utils.logging.logs import update_download_completed_by_hash from utils.logging.logs import consoleLog +from PySide6.QtCore import QObject, QTimer from utils.data.state import state from plyer import notification import libtorrent as lt @@ -19,56 +20,26 @@ def cleanup_session(): with state.downloads_lock: state.active_downloads.clear() -def send_notification(shutdown_event): - notified = set() - while not shutdown_event.is_set(): - try: - with state.downloads_lock: - items = list(state.active_downloads.items()) - for magnet_uri, magnetdl in items: - if isinstance(magnetdl, dict): - continue - - status = magnetdl.status() - - if status.state == lt.torrent_status.seeding and magnet_uri not in notified: - notification.notify( - title="Download finished", - message=f"{status.name} has finished downloading.", - timeout=4 - ) - notified.add(magnet_uri) - except Exception as e: - consoleLog(f"Exception while sending notification: {e}") - time.sleep(5) +class AppDaemons(QObject): + def __init__(self): + super().__init__() -def update_log(shutdown_event): - updated = set() - while not shutdown_event.is_set(): - try: - with state.downloads_lock: - items = list(state.active_downloads.items()) - seeded = set(state.seeded_magnets) - for magnet_uri, magnetdl in items: - if isinstance(magnetdl, dict): - continue - - status = magnetdl.status() - - if status.state == lt.torrent_status.seeding and magnet_uri not in updated and magnet_uri not in seeded: - consoleLog(f"Marking {status.name} as completed") - if hasattr(status, 'info_hashes'): - info_hash = str(status.info_hashes.v1) - else: - info_hash = str(status.info_hash) - update_download_completed_by_hash(info_hash, True) - updated.add(magnet_uri) - except Exception as e: - consoleLog(f"Exception while updating log file: {e}") - time.sleep(5) + self.notified_magnets = set() + self.updated_magnets = set() -def check_deleted_files(shutdown_event): - while not shutdown_event.is_set(): + # Create Timers + self.deleted_files_timer = QTimer() + self.completed_downloads_timer = QTimer() + + # Connect Timer Signals + self.deleted_files_timer.timeout.connect(self.check_deleted_files) + self.completed_downloads_timer.timeout.connect(self.check_completed_downloads) + + def start_all(self): + self.deleted_files_timer.start(5000) + self.completed_downloads_timer.start(5000) + + def check_deleted_files(self): try: with state.downloads_lock: items = list(state.active_downloads.items()) @@ -88,4 +59,36 @@ def check_deleted_files(shutdown_event): del state.active_downloads[magnet_uri] except Exception as e: consoleLog(f"Exception while checking for file deletions: {e}") - time.sleep(5) \ No newline at end of file + + def check_completed_downloads(self): + try: + with state.downloads_lock: + items = list(state.active_downloads.items()) + seeded = set(state.seeded_magnets) + for magnet_uri, magnetdl in items: + if isinstance(magnetdl, dict): + continue + + status = magnetdl.status() + + if status.state == lt.torrent_status.seeding: + + if magnet_uri not in self.updated_magnets and magnet_uri not in seeded: + consoleLog(f"Marking {status.name} as completed") + if hasattr(status, 'info_hashes'): + info_hash = str(status.info_hashes.v1) + else: + info_hash = str(status.info_hash) + update_download_completed_by_hash(info_hash, True) + self.updated_magnets.add(magnet_uri) + + if magnet_uri not in self.notified_magnets: + notification.notify( + title="Download finished", + message=f"{status.name} has finished downloading.", + timeout=4 + ) + self.notified_magnets.add(magnet_uri) + + except Exception as e: + consoleLog(f"Exception while checking downloads: {e}") \ No newline at end of file