# Dynamic Object Instantiation

**URL:** <https://www.ruby-forum.com/t/dynamic-object-instantiation/75530>\
**Category:** Ruby\
**Created:** [March 2, 2006, 12:30am UTC](https://www.ruby-forum.com/t/dynamic-object-instantiation/75530 "2006-03-02T00:30:14Z")\
**Posts on this page:** 3\
**Page:** 1

<div class="post-metadata">

**Author:** ![Troy\_D](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/t/d07c76/32.png) [@Troy\_D](https://www.ruby-forum.com/u/Troy_D)\
**Post date:** [March 2, 2006, 12:30am UTC](https://www.ruby-forum.com/t/dynamic-object-instantiation/75530/1 "2006-03-02T00:30:14Z")

</div>

I’m sure this question has been asked and answered in the past, but  
googling  
and searching the list archives isn’t getting me much. It’s probably a  
case  
of me not searching correctly. So, if someone has a pointer on that  
front,  
let me know.

Basically, I want a class to dynamically load and instantiate objects.  
Here’s the code that is supposed to do that:

## ComponentGatherer.rb

class ComponentGatherer

def initialize()  
@@components = []  
Dir.foreach( File.dirname( **FILE** ) ){|x|  
next unless x =~ /component.rb$/i  
x.gsub!( “.rb”, “” )  
require “#{x}”  
@@components.push( x )  
}  
end

def components  
@@components.each{ |x|  
test = x.new()  
# Blah, blah, blah  
}  
end  
end

Locating and requring the files seems to be working fine, it’s when the  
component() call is made that I’m a bit lost. I have to  
\*Component.rbfiles, they look like this:

## MyOtherComponent.rb

class MyOtherTestComponent

attr :test

def initialize()  
self.test = 2  
end  
end

The error I get from the components() method is:

undefined method `new’ for “MyOtherTestComponent”:String  
(NoMethodError)

I understand what the error is saying, but I’m not sure how to call  
new() on  
“x” above such that it returns an object of the requested class. Any  
help  
is appreciated.

Regards,

Troy D.

---

<div class="post-metadata">

**Author:** ![Troy\_D](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/t/d07c76/32.png) [@Troy\_D](https://www.ruby-forum.com/u/Troy_D)\
**Post date:** [March 2, 2006, 1:29am UTC](https://www.ruby-forum.com/t/dynamic-object-instantiation/75530/2 "2006-03-02T01:29:44Z")

</div>

Troy D. wrote:

> end  
> Locating and requring the files seems to be working fine, it’s when the  
> self.test = 2
> 
> Regards,
> 
> Troy D.

If there is a way to map from the file name to the class name (in this  
example, it would map “MyOtherComponent.rb” to “MyOtherTestComponent”),  
then you can do this first, and then use const\_get to get the class:

x = “MyOtherComponent.rb”  
x.gsub(/.rb$/, “”)  
x.gsub(/Component/, “TestComponent”)  
cl = Kernel.const\_get x  
obj = cl.new

But it’s sometimes difficult to enforce this filename/classname  
consistency.

I prefer something like this:

[http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/181735](http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/181735)

It still uses const\_get, but it wraps the component inside a module, so  
that the global namespace doesn’t get polluted, and you can query for  
the class that was defined in a file without mucking around with the  
file name.

HTH.

---

<div class="post-metadata">

**Author:** ![Troy\_D](https://www.ruby-forum.com/letter_avatar_proxy/v4/letter/t/d07c76/32.png) [@Troy\_D](https://www.ruby-forum.com/u/Troy_D)\
**Post date:** [March 3, 2006, 7:17pm UTC](https://www.ruby-forum.com/t/dynamic-object-instantiation/75530/3 "2006-03-03T19:17:18Z")

</div>

Thanks for the followup. I also figured out how to search and found  
this:

[http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/13414?help-en](http://blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/13414?help-en)

Which also helps.

Thanks.
