improve shutdown handling
This commit is contained in:
parent
17a362fe7a
commit
a85a6c694c
@ -2,7 +2,7 @@ from http.server import HTTPServer
|
||||
from owrx.http import RequestHandler
|
||||
from owrx.config import PropertyManager
|
||||
from owrx.feature import FeatureDetector
|
||||
from owrx.source import SdrService
|
||||
from owrx.source import SdrService, ClientRegistry
|
||||
from socketserver import ThreadingMixIn
|
||||
from owrx.sdrhu import SdrHuUpdater
|
||||
|
||||
@ -45,4 +45,8 @@ Author contact info: Andras Retzler, HA7ILM <randras@sdr.hu>
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
try:
|
||||
main()
|
||||
except KeyboardInterrupt:
|
||||
for c in ClientRegistry.getSharedInstance().clients:
|
||||
c.close()
|
||||
|
@ -1,5 +1,5 @@
|
||||
from owrx.config import PropertyManager
|
||||
from owrx.source import DspManager, CpuUsageThread, SdrService, ClientReporterThread
|
||||
from owrx.source import DspManager, CpuUsageThread, SdrService, ClientRegistry
|
||||
import json
|
||||
|
||||
import logging
|
||||
@ -14,7 +14,7 @@ class OpenWebRxClient(object):
|
||||
def __init__(self, conn):
|
||||
self.conn = conn
|
||||
|
||||
ClientReporterThread.getSharedInstance().addClient(self)
|
||||
ClientRegistry.getSharedInstance().addClient(self)
|
||||
|
||||
self.dsp = None
|
||||
self.sdr = None
|
||||
@ -68,10 +68,8 @@ class OpenWebRxClient(object):
|
||||
def close(self):
|
||||
self.stopDsp()
|
||||
CpuUsageThread.getSharedInstance().remove_client(self)
|
||||
try:
|
||||
ClientReporterThread.getSharedInstance().removeClient(self)
|
||||
except ValueError:
|
||||
pass
|
||||
ClientRegistry.getSharedInstance().removeClient(self)
|
||||
self.conn.close()
|
||||
logger.debug("connection closed")
|
||||
|
||||
def stopDsp(self):
|
||||
|
@ -3,7 +3,7 @@ import mimetypes
|
||||
from datetime import datetime
|
||||
from owrx.websocket import WebSocketConnection
|
||||
from owrx.config import PropertyManager
|
||||
from owrx.source import ClientReporterThread
|
||||
from owrx.source import ClientRegistry
|
||||
from owrx.connection import WebSocketMessageHandler
|
||||
from owrx.version import openwebrx_version
|
||||
|
||||
@ -41,7 +41,7 @@ class StatusController(Controller):
|
||||
"status": "active",
|
||||
"name": pm["receiver_name"],
|
||||
"op_email": pm["receiver_admin"],
|
||||
"users": ClientReporterThread.getSharedInstance().clientCount(),
|
||||
"users": ClientRegistry.getSharedInstance().clientCount(),
|
||||
"users_max": pm["max_clients"],
|
||||
"gps": pm["receiver_gps"],
|
||||
"asl": pm["receiver_asl"],
|
||||
|
@ -10,7 +10,7 @@ logger = logging.getLogger(__name__)
|
||||
class SdrHuUpdater(threading.Thread):
|
||||
def __init__(self):
|
||||
self.doRun = True
|
||||
super().__init__()
|
||||
super().__init__(daemon = True)
|
||||
|
||||
def update(self):
|
||||
pm = PropertyManager.getSharedInstance()
|
||||
|
@ -467,6 +467,8 @@ class CpuUsageThread(threading.Thread):
|
||||
c.write_cpu_usage(cpu_usage)
|
||||
time.sleep(3)
|
||||
logger.debug("cpu usage thread shut down")
|
||||
if CpuUsageThread.sharedInstance == self:
|
||||
CpuUsageThread.sharedInstance = None
|
||||
|
||||
def get_cpu_usage(self):
|
||||
try:
|
||||
@ -499,42 +501,49 @@ class CpuUsageThread(threading.Thread):
|
||||
self.shutdown()
|
||||
|
||||
def shutdown(self):
|
||||
if self.doRun:
|
||||
if CpuUsageThread.sharedInstance == self:
|
||||
CpuUsageThread.sharedInstance = None
|
||||
self.doRun = False
|
||||
self.doRun = False
|
||||
|
||||
class ClientReportingThread(threading.Thread):
|
||||
def __init__(self, registry):
|
||||
self.doRun = True
|
||||
self.registry = registry
|
||||
super().__init__()
|
||||
def run(self):
|
||||
while self.doRun:
|
||||
self.registry.broadcast()
|
||||
time.sleep(3)
|
||||
def stop(self):
|
||||
self.doRun = False
|
||||
|
||||
class TooManyClientsException(Exception):
|
||||
pass
|
||||
|
||||
class ClientReporterThread(threading.Thread):
|
||||
class ClientRegistry(object):
|
||||
sharedInstance = None
|
||||
@staticmethod
|
||||
def getSharedInstance():
|
||||
if ClientReporterThread.sharedInstance is None:
|
||||
ClientReporterThread.sharedInstance = ClientReporterThread()
|
||||
ClientReporterThread.sharedInstance.start()
|
||||
ClientReporterThread.sharedInstance.doRun = True
|
||||
return ClientReporterThread.sharedInstance
|
||||
if ClientRegistry.sharedInstance is None:
|
||||
ClientRegistry.sharedInstance = ClientRegistry()
|
||||
return ClientRegistry.sharedInstance
|
||||
|
||||
def __init__(self):
|
||||
self.doRun = True
|
||||
self.clients = []
|
||||
self.reporter = None
|
||||
super().__init__()
|
||||
|
||||
def run(self):
|
||||
while (self.doRun):
|
||||
n = self.clientCount()
|
||||
for c in self.clients:
|
||||
c.write_clients(n)
|
||||
time.sleep(3)
|
||||
ClientReporterThread.sharedInstance = None
|
||||
def broadcast(self):
|
||||
n = self.clientCount()
|
||||
for c in self.clients:
|
||||
c.write_clients(n)
|
||||
|
||||
def addClient(self, client):
|
||||
pm = PropertyManager.getSharedInstance()
|
||||
if len(self.clients) >= pm["max_clients"]:
|
||||
raise TooManyClientsException()
|
||||
self.clients.append(client)
|
||||
if self.reporter is None:
|
||||
self.reporter = ClientReportingThread(self)
|
||||
self.reporter.start()
|
||||
|
||||
def clientCount(self):
|
||||
return len(self.clients)
|
||||
@ -544,5 +553,6 @@ class ClientReporterThread(threading.Thread):
|
||||
self.clients.remove(client)
|
||||
except ValueError:
|
||||
pass
|
||||
if not self.clients:
|
||||
self.doRun = False
|
||||
if not self.clients and self.reporter is not None:
|
||||
self.reporter.stop()
|
||||
self.reporter = None
|
||||
|
@ -72,5 +72,20 @@ class WebSocketConnection(object):
|
||||
else:
|
||||
logger.warning("unsupported opcode: {0}".format(opcode))
|
||||
|
||||
def close(self):
|
||||
try:
|
||||
header = self.get_header(0, 8)
|
||||
self.handler.wfile.write(header)
|
||||
self.handler.wfile.flush()
|
||||
except ValueError:
|
||||
logger.exception("while writing close frame:")
|
||||
|
||||
try:
|
||||
self.handler.finish()
|
||||
self.handler.connection.close()
|
||||
except Exception:
|
||||
logger.exception("while closing connection:")
|
||||
|
||||
|
||||
class WebSocketException(Exception):
|
||||
pass
|
||||
|
Loading…
Reference in New Issue
Block a user