Skip to content

Commit

Permalink
Added a 'generates_subclass' class method
Browse files Browse the repository at this point in the history
Allows abstract parent classes to specify which concrete subclass
should be generated by default.
  • Loading branch information
pdcawley authored and ymendel committed Apr 23, 2009
1 parent fbbf38b commit 72fb526
Show file tree
Hide file tree
Showing 2 changed files with 29 additions and 1 deletion.
9 changes: 9 additions & 0 deletions lib/object_daddy.rb
Expand Up @@ -26,6 +26,11 @@ module ClassMethods
# Creates a valid instance of this class, using any known generators. The
# generated instance is yielded to a block if provided.
def spawn(args = {})
if @concrete_subclass_name
return block_given? \
? const_get(@concrete_subclass_name).spawn(args) {|instance| yield instance} \
: const_get(@concrete_subclass_name).spawn(args)
end
gather_exemplars
generate_values(args)
instance = new(args)
Expand Down Expand Up @@ -78,6 +83,10 @@ def generator_for(handle, args = {}, &block)
raise ArgumentError, "a block, :class generator, :method generator, or value must be specified to generator_for"
end
end

def generates_subclass(subclass_name)
@concrete_subclass_name = subclass_name.to_s
end

def gather_exemplars
return if exemplars_generated
Expand Down
21 changes: 20 additions & 1 deletion spec/object_daddy_spec.rb
Expand Up @@ -438,6 +438,25 @@ def self.generator_value_method(prev)
@class.generator_for :foo => 5
@class.spawn(:foo => false).foo.should be(false)
end

describe 'for an abstract parent class' do
before :each do
Widget = Class.new(OpenStruct) { include ObjectDaddy }
SubWidget = Class.new(Widget) {include ObjectDaddy }
Widget.stubs(:exemplar_path).returns(@file_path)
SubWidget.stubs(:exemplar_path).returns(File.join(@file_path, 'sub_widget_exemplar.rb'))
end

it 'should generate an instance of a specified concrete subclass (specced using a symbol)' do
Widget.generates_subclass :SubWidget
Widget.spawn.should be_instance_of SubWidget
end

it 'should generate an instance of a specified concrete subclass (specced using a string)' do
Widget.generates_subclass 'SubWidget'
Widget.spawn.should be_instance_of SubWidget
end
end

describe 'for a subclass' do
before :each do
Expand Down Expand Up @@ -478,7 +497,7 @@ def self.generator_value_method(prev)
SubWidget.spawn.blah.should == 'blip'
end
end

describe 'using generators called directly' do
it 'should use generators from the parent class' do
@class.generator_for :blah do |prev| 'blah'; end
Expand Down

0 comments on commit 72fb526

Please sign in to comment.