diff options
| author | Mike Bayer <mike_mp@zzzcomputing.com> | 2010-10-02 13:31:07 -0400 |
|---|---|---|
| committer | Mike Bayer <mike_mp@zzzcomputing.com> | 2010-10-02 13:31:07 -0400 |
| commit | d46985d699e6ebffe45c94d91cfa842271e06bb0 (patch) | |
| tree | b04fbb7dcc96afc2c0c3973e77e53ef2cbcc7643 /lib/sqlalchemy/event.py | |
| parent | 25c08f6def19e1034a887e972ad286ef122473d0 (diff) | |
| download | sqlalchemy-d46985d699e6ebffe45c94d91cfa842271e06bb0.tar.gz | |
- add instrumentation events
- simplify listen_for_events example with new system
- add "propagate", "retval", "raw" flags to attribute events. this solves the "return value"
issue as well as the "subclass" issue.
- begin thinking about event removal. Each listen() method will have a corresponding remove().
Custom listen() methods will have to package all the info onto the event function that is needed
to remove its state.
Diffstat (limited to 'lib/sqlalchemy/event.py')
| -rw-r--r-- | lib/sqlalchemy/event.py | 33 |
1 files changed, 26 insertions, 7 deletions
diff --git a/lib/sqlalchemy/event.py b/lib/sqlalchemy/event.py index c1bc54b17..c7df2bf48 100644 --- a/lib/sqlalchemy/event.py +++ b/lib/sqlalchemy/event.py @@ -29,7 +29,20 @@ def listen(fn, identifier, target, *args, **kw): return raise exc.InvalidRequestError("No such event %s for target %s" % (identifier,target)) + +def remove(fn, identifier, target): + """Remove an event listener. + + Note that some event removals, particularly for those event dispatchers + which create wrapper functions and secondary even listeners, may not yet + be supported. + """ + for evt_cls in _registrars[identifier]: + for tgt in evt_cls.accept_with(target): + tgt.dispatch.remove(fn, identifier, tgt, *args, **kw) + + _registrars = util.defaultdict(list) class _Dispatch(object): @@ -105,13 +118,11 @@ class Events(object): @classmethod def listen(cls, fn, identifier, target): getattr(target.dispatch, identifier).append(fn, target) - -# def update(self, other): -# """Populate from the listeners in another :class:`Events` object.""" - -# for ls in other.events: -# getattr(self, ls.name).listeners.extend(ls.listeners) + @classmethod + def remove(cls, fn, identifier, target): + getattr(target.dispatch, identifier).remove(fn, target) + class _DispatchDescriptor(object): """Class-level attributes on _Dispatch classes.""" @@ -127,6 +138,10 @@ class _DispatchDescriptor(object): for cls in [target] + target.__subclasses__(): self._clslevel[cls].append(obj) + def remove(self, obj, target): + for cls in [target] + target.__subclasses__(): + self._clslevel[cls].remove(obj) + def __get__(self, obj, cls): if obj is None: return self @@ -180,7 +195,11 @@ class _ListenerCollection(object): def append(self, obj, target): if obj not in self.listeners: self.listeners.append(obj) - + + def remove(self, obj, target): + if obj in self.listeners: + self.listeners.remove(obj) + class dispatcher(object): """Descriptor used by target classes to deliver the _Dispatch class at the class level |
