| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146 |
- import threading
- import time
- from utils.logger_config import logger
- from hardware.kodi_module import KodiClientManager
- class KodiAliveThreadSingleton:
- """Kodi心跳检测线程单例类,每秒检查一次心跳,如果检测不到Kodi在线则启动Kodi应用"""
-
- _instance = None
- _lock = threading.Lock()
-
- def __new__(cls):
- if cls._instance is None:
- with cls._lock:
- if cls._instance is None:
- cls._instance = super(KodiAliveThreadSingleton, cls).__new__(cls)
- return cls._instance
-
- def __init__(self):
- # 避免重复初始化
- if hasattr(self, '_initialized'):
- return
-
- self._initialized = True
- self.thread = None
- self.is_running = False
- self._should_stop = False
- self.manager: KodiClientManager = None
-
- # 配置参数
- self.check_interval_seconds = 1 # 每秒检查一次
-
- # 启动工作线程
- self._start_worker_thread()
-
- def _start_worker_thread(self):
- """启动工作线程"""
- if self.thread is None or not self.thread.is_alive():
- self.is_running = True
- self._should_stop = False
- self.thread = threading.Thread(target=self._worker_loop, daemon=True)
- self.thread.start()
- logger.info("Kodi心跳检测线程已启动")
-
- def _initialize_manager(self):
- """初始化KodiClientManager"""
- if self.manager is None:
- self.manager = KodiClientManager()
- logger.info("KodiClientManager 初始化成功")
-
- def _worker_loop(self):
- """工作线程主循环"""
- logger.info("Kodi心跳检测线程开始运行,每秒检查一次心跳")
-
- try:
- # 确保Manager已初始化
- self._initialize_manager()
-
- while self.is_running and not self._should_stop:
- try:
- # 检查所有Kodi客户端是否在线
- offline_client_indices = self.manager.check_all_kodi_clients_online()
-
- if offline_client_indices:
- # 检测到不在线的客户端,启动对应的Kodi应用
- logger.warning(f"检测到 {len(offline_client_indices)} 个Kodi客户端不在线,索引: {offline_client_indices},尝试启动Kodi应用")
-
- for offline_client_index in offline_client_indices:
- try:
- # 根据client_index获取对应的客户端并启动
- if offline_client_index < len(self.manager.kodi_clients):
- client = self.manager.kodi_clients[offline_client_index]
- result = client.start_kodi()
- logger.info(f"已尝试启动客户端 {offline_client_index} 的Kodi应用,响应: {result}")
- else:
- logger.error(f"客户端索引 {offline_client_index} 超出范围,客户端总数: {len(self.manager.kodi_clients)}")
- except Exception as e:
- logger.error(f"启动客户端 {offline_client_index} 的Kodi应用时发生异常: {e}")
- else:
- # 所有客户端都在线
- logger.debug("所有Kodi客户端在线")
-
- # 等待指定时间后再次检查
- time.sleep(self.check_interval_seconds)
-
- if self._should_stop:
- logger.info("收到停止信号,退出循环")
- break
-
- except Exception as e:
- logger.error(f"工作线程循环异常: {e}")
- time.sleep(self.check_interval_seconds)
-
- except Exception as e:
- logger.error(f"工作线程异常: {e}")
- finally:
- self.is_running = False
- logger.info("Kodi心跳检测线程结束")
-
- def stop(self):
- """停止线程"""
- self._should_stop = True
- self.is_running = False
- logger.info("停止Kodi心跳检测线程")
- # 全局单例实例
- _kodi_alive_thread = KodiAliveThreadSingleton()
- def start_kodi_alive_check() -> bool:
- """
- 启动Kodi心跳检测
-
- 启动后,线程会每秒自动检查所有Kodi客户端的心跳
- 如果检测到不在线的客户端,会自动尝试启动对应的Kodi应用
-
- Returns:
- bool: 启动是否成功
- """
- if not _kodi_alive_thread.is_running:
- _kodi_alive_thread._start_worker_thread()
- return _kodi_alive_thread.is_running
- def stop_kodi_alive_check() -> bool:
- """
- 停止Kodi心跳检测
-
- Returns:
- bool: 停止是否成功
- """
- _kodi_alive_thread.stop()
- return True
- def is_alive_check_running() -> bool:
- """
- 检查心跳检测线程是否正在运行
-
- Returns:
- bool: 线程是否正在运行
- """
- return _kodi_alive_thread.is_running
|