Class: DjangoSignal
- Inherits:
-
Object
- Object
- DjangoSignal
- Defined in:
- lib/django_signal.rb
Overview
DjangoSignal See docs.djangoproject.com/en/dev/topics/signals/#defining-and-sending-signals
Obviously, I didn’t wire this signals to ActiveRecord.
Also, I took the liberty to make some adaptations. Namely:
-
No explicit weakref stuff. Want a weakref? Build if yourself. Invalid refs are handled gracefuly.
-
No providing_args, since they had no functional relevance.
Defined Under Namespace
Classes: InvalidReceiver
Instance Method Summary collapse
-
#connect(receiver, sender = nil, dispatch_uid = nil) ⇒ Object
Connect receiver to sender for signal.
-
#disconnect(receiver, sender = nil, dispatch_uid = nil) ⇒ Object
Disconnect receiver from sender for signal.
-
#initialize ⇒ DjangoSignal
constructor
Create a new signal.
-
#send(sender, *args) ⇒ Object
Send signal from sender to all connected receivers.
-
#send_robust(sender, *args) ⇒ Object
Send signal from sender to all connected receivers catching errors.
Constructor Details
#initialize ⇒ DjangoSignal
Create a new signal.
20 21 22 23 |
# File 'lib/django_signal.rb', line 20 def initialize @receivers = {} @lock = Mutex.new end |
Instance Method Details
#connect(receiver, sender = nil, dispatch_uid = nil) ⇒ Object
Connect receiver to sender for signal.
receiver
-
A callable which is to receive signals. The receiver must be able to handler 2+ arguments (+signal, sender, *send_args+).
If dispatch_uid is given, the receiver will not be added if
another receiver already exists with that dispatch_uid.
sender
-
The sender to which the receiver should respond or nil to receive events from any sender.
dispatch_uid
-
An identifier used to uniquely identify a particular instance of a receiver. This will usually be a symbol, though it may be anything with an object_id.
38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 |
# File 'lib/django_signal.rb', line 38 def connect(receiver, sender=nil, dispatch_uid=nil) lookup_key = make_key(receiver, sender, dispatch_uid) begin receiver.method(:call) rescue nil or raise NoMethodError if -1 < receiver.arity && receiver.arity < 2 raise InvalidReceiver, 'Receiver must be able to handle 2+ arguments.' end rescue NoMethodError raise InvalidReceiver, 'Receiver must be a callable (and respond to arity method).' end @lock.synchronize { @receivers[lookup_key] ||= receiver } end |
#disconnect(receiver, sender = nil, dispatch_uid = nil) ⇒ Object
Disconnect receiver from sender for signal.
If weak references are used, disconnect need not be called. The receiver will be remove from dispatch automatically.
receiver
-
The registered receiver to disconnect. May be nil if dispatch_uid is specified.
sender
-
The registered sender to disconnect
dispatch_uid
-
the unique identifier of the receiver to disconnect
67 68 69 70 71 72 73 |
# File 'lib/django_signal.rb', line 67 def disconnect(receiver, sender=nil, dispatch_uid=nil) lookup_key = make_key(receiver, sender, dispatch_uid) @lock.synchronize { @receivers.delete(lookup_key) } end |
#send(sender, *args) ⇒ Object
Send signal from sender to all connected receivers.
If any receiver raises an error, the error propagates back through send, terminating the dispatch loop, so it is quite possible to not have all receivers called if a raises an error.
sender
-
The sender of the signal. Either a specific object or nil.
args
-
Args which will be passed to receivers.
Returns a hash {receiver => response, … }.
87 88 89 |
# File 'lib/django_signal.rb', line 87 def send(sender, *args) self.mapper(self.method(:simple_call), sender, *args) end |
#send_robust(sender, *args) ⇒ Object
Send signal from sender to all connected receivers catching errors.
If any receiver raises an error (specifically any subclass of Exception), the error instance is returned as the result for that receiver.
sender
-
The sender of the signal. Either a specific object or nil.
args
-
Args which will be passed to receivers.
Returns a hash {receiver => response, … }.
102 103 104 |
# File 'lib/django_signal.rb', line 102 def send_robust(sender, *args) self.mapper(self.method(:robust_call), sender, *args) end |