diff options
| author | ryan <ryan@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2008-10-10 01:17:21 +0000 |
|---|---|---|
| committer | ryan <ryan@b2dd03c8-39d4-4d8f-98ff-823fe69b080e> | 2008-10-10 01:17:21 +0000 |
| commit | 53ac5cd019a39d0a480407cab7cb6775fcda8039 (patch) | |
| tree | 063e9d8bb63224fa05c69fa427c54cbce61c4f6a /lib/test/unit/util/observable.rb | |
| parent | b001079cee3aca8387adeacaf33a78419e167a48 (diff) | |
| download | ruby-53ac5cd019a39d0a480407cab7cb6775fcda8039.tar.gz ruby-53ac5cd019a39d0a480407cab7cb6775fcda8039.tar.xz ruby-53ac5cd019a39d0a480407cab7cb6775fcda8039.zip | |
Restored test/unit
git-svn-id: http://svn.ruby-lang.org/repos/ruby/trunk@19739 b2dd03c8-39d4-4d8f-98ff-823fe69b080e
Diffstat (limited to 'lib/test/unit/util/observable.rb')
| -rw-r--r-- | lib/test/unit/util/observable.rb | 90 |
1 files changed, 90 insertions, 0 deletions
diff --git a/lib/test/unit/util/observable.rb b/lib/test/unit/util/observable.rb new file mode 100644 index 000000000..924c10f24 --- /dev/null +++ b/lib/test/unit/util/observable.rb @@ -0,0 +1,90 @@ +#-- +# +# Author:: Nathaniel Talbott. +# Copyright:: Copyright (c) 2000-2002 Nathaniel Talbott. All rights reserved. +# License:: Ruby license. + +require 'test/unit/util/procwrapper' + +module Test + module Unit + module Util # :nodoc: + + # This is a utility class that allows anything mixing + # it in to notify a set of listeners about interesting + # events. + module Observable + # We use this for defaults since nil might mean something + NOTHING = "NOTHING/#{__id__}" + + # Adds the passed proc as a listener on the + # channel indicated by channel_name. listener_key + # is used to remove the listener later; if none is + # specified, the proc itself is used. + # + # Whatever is used as the listener_key is + # returned, making it very easy to use the proc + # itself as the listener_key: + # + # listener = add_listener("Channel") { ... } + # remove_listener("Channel", listener) + def add_listener(channel_name, listener_key=NOTHING, &listener) # :yields: value + unless(block_given?) + raise ArgumentError.new("No callback was passed as a listener") + end + + key = listener_key + if (listener_key == NOTHING) + listener_key = listener + key = ProcWrapper.new(listener) + end + + channels[channel_name] ||= {} + channels[channel_name][key] = listener + return listener_key + end + + # Removes the listener indicated by listener_key + # from the channel indicated by + # channel_name. Returns the registered proc, or + # nil if none was found. + def remove_listener(channel_name, listener_key) + channel = channels[channel_name] + return nil unless (channel) + key = listener_key + if (listener_key.instance_of?(Proc)) + key = ProcWrapper.new(listener_key) + end + if (channel.has_key?(key)) + return channel.delete(key) + end + return nil + end + + # Calls all the procs registered on the channel + # indicated by channel_name. If value is + # specified, it is passed in to the procs, + # otherwise they are called with no arguments. + # + #-- + # + # Perhaps this should be private? Would it ever + # make sense for an external class to call this + # method directly? + def notify_listeners(channel_name, *arguments) + channel = channels[channel_name] + return 0 unless (channel) + listeners = channel.values + listeners.each { |listener| listener.call(*arguments) } + return listeners.size + end + + private + def channels # :nodoc: + @channels ||= {} + return @channels + end + end + end + end +end |
