ntfy-waiter: never drop notifications, but rather sleep until client is ready to receive them

This commit is contained in:
Colin 2023-10-22 12:10:52 +00:00
parent 7541d5466e
commit b10425f6b6

View File

@ -24,15 +24,15 @@ class Client:
def __cmp__(self, other: 'Client'):
return cmp(self.addr_info, other.addr_info)
def maybe_notify(self, message: bytes) -> bool:
def try_notify(self, message: bytes) -> bool:
"""
returns false if we wanted to notify the client but failed (e.g. socket died).
true otherwise.
returns true if we send a packet to notify client.
fals otherwise (e.g. the socket is dead).
"""
if time.time() < self.live_after:
# TODO: we want to still notify, just with a delay!
logger.debug(f"not notifying client because it's not ready: {self.addr_info}")
return True
ttl = self.live_after - time.time()
if ttl > 0:
logger.debug(f"sleeping {ttl:.2f}s until client {self.addr_info} is ready to receive notification")
time.sleep(ttl)
try:
self.sock.sendall(message)
@ -77,12 +77,13 @@ class Adapter:
self.add_client(Client(conn, addr_info, live_after = time.time() + self.silence))
def notify_clients(self, message: bytes = WAKE_MESSAGE):
# notify every client, and drop any which have disconnected
# XXX: paranoia about me not knowing Python's guarantees for mutation during set iteration
clients = set(self.clients)
# notify every client, and drop any which have disconnected.
# note that we notify based on age (oldest -> youngest)
# because notifying young clients might entail sleeping until they're ready.
clients = sorted(self.clients, key=lambda c: (c.live_after, c.addr_info))
dead_clients = [
c for c in clients if not c.maybe_notify(message)
c for c in clients if not c.try_notify(message)
]
for c in dead_clients:
self.clients.remove(c)