[FIX] bus: gc event at the end of a polling

When making a poll, an event is registered on each channel. Once
a notification is sent on a channel, only the events of the
notified channel are removed. A pointer to the event is kept
in all other channel the user subscribes to until those channel
are notified.

Since a user usually has many mail.channels but only a few active ones,
a new event and a bunch of pointers are created at each poll and
never removed.

This fix simply remove the pointers to the current event at the
end of a poll.

closes odoo/odoo#31215

Signed-off-by: Toufik Benjaa (tbe) <tbe@odoo.com>
This commit is contained in:
XavierDo
2019-02-28 15:49:04 +00:00
parent 6edd699ee9
commit a95756faac
+8 -2
View File
@@ -141,7 +141,7 @@ class ImDispatch(object):
event = self.Event()
for channel in channels:
self.channels.setdefault(hashable(channel), []).append(event)
self.channels.setdefault(hashable(channel), set()).add(event)
try:
event.wait(timeout=timeout)
with registry.cursor() as cr:
@@ -150,6 +150,12 @@ class ImDispatch(object):
except Exception:
# timeout
pass
finally:
# gc pointers to event
for channel in channels:
channel_events = self.channels.get(hashable(channel))
if channel_events and event in channel_events:
channel_events.remove(event)
return notifications
def loop(self):
@@ -170,7 +176,7 @@ class ImDispatch(object):
# dispatch to local threads/greenlets
events = set()
for channel in channels:
events.update(self.channels.pop(hashable(channel), []))
events.update(self.channels.pop(hashable(channel), set()))
for event in events:
event.set()