Skip to content

Instantly share code, notes, and snippets.

@nakajima
Created September 24, 2008 00:33
Show Gist options
  • Save nakajima/12445 to your computer and use it in GitHub Desktop.
Save nakajima/12445 to your computer and use it in GitHub Desktop.
require 'rubygems'
require 'activesupport'
module ConditionalEvaluator
def evaluate_conditional(conditional)
case conditional
when Symbol then send(conditional)
when Proc then conditional.call
end
end
end
class Module
def alias_method_chain_with_conditional(target, feature, options={})
include ConditionalEvaluator unless included_modules.include?(ConditionalEvaluator)
condition = options[:if]
return alias_method_chain_without_conditional(target, feature) unless condition
define_method("#{target}_with_#{feature}_with_conditional") do |*args|
return send("#{target}_without_#{feature}", *args) unless evaluate_conditional(condition)
send("#{target}_with_#{feature}_without_conditional", *args)
end
alias_method_chain("#{target}_with_#{feature}", :conditional)
alias_method_chain_without_conditional(target, feature)
end
alias_method_chain :alias_method_chain, :conditional
end
require 'spec'
describe "alias_method_chain" do
before(:each) do
@klass = Class.new { attr_accessor(:allowed); def foo; :foo end }
@module = Module.new { def foo_with_fizz; [foo_without_fizz, :fizz] end }
@object = @klass.new
end
it "should work without chaining" do
@object.foo.should == :foo
end
it "should work as default" do
@klass.send :include, @module
@klass.alias_method_chain :foo, :fizz
@object.foo.should == [:foo, :fizz]
end
describe "with conditionals" do
before(:each) do
@klass.send :include, @module
@klass.alias_method_chain :foo, :fizz, :if => :allowed
end
it "should allow conditional support" do
@object.foo.should == :foo
end
it "should be affected by conditional" do
@object.foo.should == :foo
@object.allowed = true
@object.foo.should == [:foo, :fizz]
end
it "should let conditional toggle results" do
@object.allowed = true
@object.foo.should == [:foo, :fizz]
@object.allowed = false
@object.foo.should == :foo
end
end
describe "with conditional as proc" do
before(:each) do
@allowed = false
@klass.send :include, @module
@klass.alias_method_chain :foo, :fizz, :if => proc { @allowed }
end
it "should still work" do
@object.foo.should == :foo
@allowed = true
@object.foo.should == [:foo, :fizz]
end
end
end
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment