リスナー

rubyでリスナーによるコールバックを行うにはどのようにすればいいのだろう?
こんなのでいいのかな?

# 登録したリスナーを実行する機能を提供するモジュール
# addメソッドでコードブロックをリスナーとして登録。fireメソッドで登録されたリスナーを実行。
module Listenable
  
  # リスナーとなるコードブロックを追加する。イベントに対するシンボルを引数に指定する。
  def add(event, &callback)
    @listeners ||= {}
    @listeners[event] ||= []
    @listeners[event].push(callback)
  end

  # リスナーとして登録されているブロックを実行する。引数eventには登録時のシンボルを指定。
  # 第2引数以降は、コードブロックへの引数。
  def fire(event, *args)
    return nil unless @listeners.include?(event)
    @listeners[event].each do |m|
      if m.respond_to? :call then
        m.call(*args) 
      end
    end
    return nil
  end
  
end
    • addメソッドでイベント名(シンボル)とコードブロックをわたしてリスナー登録。
    • fireメソッドが呼ばれると登録していたコードブロックが実行される。

以下のようにテスト

class ListenerTest

  include Listenable
  
  def hoo(args)
    puts "do hoo"
    fire(:action, args)
  end
  
end

test = ListenerTest.newa
test.add(:action) do |arg| 
   puts "do action1 - #{arg}"
end
action2 = lambda { |arg| puts "do action2  #{arg}"}
test.add(:action, &action2)

test.hoo("args ")

で、結果

do hoo
do action1  args 
do action2  args