require 'moosex' class ProxyToTarget include MooseX has target: { is: :ro, default: lambda { Target.new }, # default, new instace of Target handles: { # handles is for delegation, my_method_x: :method_x, # inject methods with new names my_method_y: :method_y, # old => obj.target.method_x }, # now => obj.my_method_x } end module TargetModule def method_x; 1024; end # works with simple methods def method_y(a,b,c); a + b + c; end # or methods with arguments end class Target include TargetModule end describe "ProxyToTarget" do it "should delegate method_x to the target" do p = ProxyToTarget.new p.target.method_x.should == 1024 p.my_method_x.should == 1024 end it "should delegate method_y to the target" do p = ProxyToTarget.new p.target.method_y(1,2,3).should == 6 p.my_method_y(1,2,3).should == 6 end it "should inject method_y" do p = ProxyToTarget.new p.respond_to?(:my_method_y).should be_true ProxyToTarget.instance_methods.member?(:my_method_y).should be_true end end class ProxyToTargetUsingArrayOfMethods include MooseX has targetz: { is: :ro, default: lambda { Target.new }, handles: [ :method_x, :method_y # will inject all methods with same name ] } end describe "ProxyToTargetUsingArrayOfMethods" do it "should delegate method_x to the target" do p = ProxyToTargetUsingArrayOfMethods.new p.targetz.method_x.should == 1024 p.method_x.should == 1024 end it "should delegate method_y to the target" do p = ProxyToTargetUsingArrayOfMethods.new p.targetz.method_y(1,2,3).should == 6 p.method_y(1,2,3).should == 6 end end class ProxyToTargetUsingSingleMethod include MooseX has target: { is: :ro, default: lambda { Target.new }, handles: "method_x" # coerce to an array of symbols } end describe "ProxyToTargetUsingSingleMethod" do it "should delegate method_x to the target" do p = ProxyToTargetUsingSingleMethod.new p.target.method_x.should == 1024 p.method_x.should == 1024 end end class ProxyToTargetUsingModule include MooseX has target: { is: :ro, default: lambda { Target.new }, handles: TargetModule # will import all methods from module } end describe "ProxyToTargetUsingModule" do it "should delegate method_x to the target" do p = ProxyToTargetUsingModule.new p.target.method_x.should == 1024 p.method_x.should == 1024 end it "should delegate method_y to the target" do p = ProxyToTargetUsingModule.new p.target.method_y(1,2,3).should == 6 p.method_y(1,2,3).should == 6 end end class ProxyToTargetUsingClass include MooseX has target: { is: :ro, default: lambda { Target.new }, handles: Target # will use only public methods on Target class } # exclude methods from superclass end describe "ProxyToTargetUsingClass" do it "should delegate method_x to the target" do p = ProxyToTargetUsingClass.new p.target.method_x.should == 1024 p.method_x.should == 1024 end it "should delegate method_y to the target" do p = ProxyToTargetUsingClass.new p.target.method_y(1,2,3).should == 6 p.method_y(1,2,3).should == 6 end end