events 0.9.3 → 0.9.4

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (3) hide show
  1. data/lib/events.rb +60 -25
  2. data/readme.rdoc +7 -0
  3. metadata +4 -4
@@ -1,19 +1,6 @@
1
1
  module Events # :nodoc:
2
2
  UncaughtError = Class.new(StandardError)
3
3
 
4
- class OnceProxy # :nodoc:
5
- attr_reader :event, :caller, :delegate
6
-
7
- def initialize(event, caller, delegate)
8
- @event, @caller, @delegate = event, caller, delegate
9
- end
10
-
11
- def call(*args)
12
- caller.remove_listener(event, self)
13
- delegate.call(*args)
14
- end
15
- end
16
-
17
4
  # The Events::Emitter mixin provides a clone of the Node.js EventEmitter API
18
5
  # for Ruby.
19
6
  #
@@ -42,6 +29,24 @@ module Events # :nodoc:
42
29
  # they raise an Events::UncaughtError exception.
43
30
  #
44
31
  module Emitter
32
+ DEFAULT_MAX_LISTENERS = 10
33
+
34
+ def max_listeners
35
+ @max_listeners || DEFAULT_MAX_LISTENERS
36
+ end
37
+ private :max_listeners
38
+
39
+ # :call-seq: emitter.max_listeners = integer -> integer
40
+ #
41
+ # By default an EventEmitter will print a warning if more than 10 listeners
42
+ # are added to it. This is a useful default which helps finding memory
43
+ # leaks. Obviously not all Emitters should be limited to 10. This method
44
+ # allows that to be increased. Set to zero for unlimited.
45
+ #
46
+ def max_listeners=(value)
47
+ @max_listeners = value
48
+ end
49
+ alias set_max_listeners max_listeners=
45
50
 
46
51
  # :call-seq: emitter.listeners(event) -> array
47
52
  #
@@ -57,16 +62,18 @@ module Events # :nodoc:
57
62
  # Execute each of the listeners in order with the supplied arguments.
58
63
  #
59
64
  def emit(event, *args)
60
- listeners = listeners(event).dup
65
+ listeners = @listeners && @listeners.key?(event) && @listeners[event]
61
66
 
62
- if event == :error && listeners.empty?
67
+ if event == :error && (!listeners || listeners.empty?)
63
68
  raise args.first if args.first.kind_of?(Exception)
64
69
  raise Events::UncaughtError.new("Uncaught, unspecified 'error' event.")
70
+ elsif listeners
71
+ listeners.dup.each do |listener|
72
+ listener.call(*args)
73
+ end.any?
74
+ else
75
+ false
65
76
  end
66
-
67
- listeners.each do |listener|
68
- listener.call(*args)
69
- end.any?
70
77
  end
71
78
 
72
79
  # :call-seq: emitter.on(event) {|args...| block} -> emitter
@@ -81,13 +88,31 @@ module Events # :nodoc:
81
88
  # with a #call method).
82
89
  #
83
90
  def add_listener(event, proc=nil, &block)
84
- emit(:new_listener, event, proc || block)
85
- listeners(event).push(proc || block)
91
+ listener = proc || block
92
+ unless listener.respond_to?(:call)
93
+ raise ArgumentError.new("Listener must respond to #call")
94
+ end
95
+ emit(:new_listener, event, listener)
96
+
97
+ event_listeners = listeners(event)
98
+
99
+ current = event_listeners.length
100
+ if max_listeners && max_listeners > 0 && current > max_listeners &&
101
+ (!event_listeners.respond_to?(:warned?) || !event_listeners.warned?)
102
+ warn(caller[1] +
103
+ ": warning: possible EventEmitter memory leak detected. " <<
104
+ "#{current} listeners added. " <<
105
+ "Use Emitter#max_listeners = n to increase limit.")
106
+ def event_listeners.warned?
107
+ true
108
+ end
109
+ end
110
+
111
+ event_listeners.push(listener)
86
112
  self
87
113
  end
88
114
  alias on add_listener
89
115
 
90
-
91
116
  # :call-seq: emitter.once(event) {|args...| block} -> emitter
92
117
  # emitter.once(event, proc) -> emitter
93
118
  #
@@ -98,7 +123,11 @@ module Events # :nodoc:
98
123
  # end
99
124
  #
100
125
  def once(event, proc=nil, &block)
101
- add_listener(event, OnceProxy.new(event, self, proc || block))
126
+ once = Proc.new do |*args|
127
+ remove_listener(event, once)
128
+ (proc || block).call(args)
129
+ end
130
+ add_listener(event, once)
102
131
  end
103
132
 
104
133
  # :call-seq: emitter.remove_listener(event, proc) -> emitter
@@ -106,7 +135,10 @@ module Events # :nodoc:
106
135
  # Remove a listener from the listener array for the specified event.
107
136
  #
108
137
  def remove_listener(event, proc)
109
- listeners(event).delete(proc)
138
+ if @listeners && @listeners.key?(event)
139
+ @listeners[event].delete(proc)
140
+ @listeners.delete(event) if @listeners[event].empty?
141
+ end
110
142
  self
111
143
  end
112
144
 
@@ -115,7 +147,10 @@ module Events # :nodoc:
115
147
  # Removes all listeners from the listener array for the specified event.
116
148
  #
117
149
  def remove_all_listeners(event)
118
- listeners(event).clear
150
+ if @listeners && @listeners.key?(event)
151
+ @listeners[event].clear
152
+ @listeners.delete(event)
153
+ end
119
154
  self
120
155
  end
121
156
  end
@@ -49,6 +49,13 @@ first time the event is fired, after which it is removed.
49
49
 
50
50
  Remove a listener from the listener array for the specified event.
51
51
 
52
+ emitter.max_listeners = n
53
+
54
+ By default an EventEmitter will print a warning if more than 10 listeners
55
+ are added to it. This is a useful default which helps finding memory
56
+ leaks. Obviously not all Emitters should be limited to 10. This method
57
+ allows that to be increased. Set to zero for unlimited.
58
+
52
59
  emitter.listeners(event)
53
60
 
54
61
  Returns an array of listeners for the specified event. This array can be
metadata CHANGED
@@ -1,13 +1,13 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: events
3
3
  version: !ruby/object:Gem::Version
4
- hash: 61
4
+ hash: 51
5
5
  prerelease: false
6
6
  segments:
7
7
  - 0
8
8
  - 9
9
- - 3
10
- version: 0.9.3
9
+ - 4
10
+ version: 0.9.4
11
11
  platform: ruby
12
12
  authors:
13
13
  - Matthew Sadler
@@ -15,7 +15,7 @@ autorequire:
15
15
  bindir: bin
16
16
  cert_chain: []
17
17
 
18
- date: 2011-01-30 00:00:00 +00:00
18
+ date: 2011-02-05 00:00:00 +00:00
19
19
  default_executable:
20
20
  dependencies: []
21
21