139

I have the name of a class and I want to create an instance of that class so that I can loop through each rails attribute that is present in the schema of that class.

How would I go about doing that?

  1. I have the name as a string of the class I want to check
  2. I guess I need to instantiate a class instance so that I can
  3. Loop through it's attributes and print them.
mhenrixon
  • 6,179
  • 4
  • 40
  • 64

4 Answers4

255

In rails you can just do:

clazz = 'ExampleClass'.constantize

In pure ruby:

clazz = Object.const_get('ExampleClass')

with modules:

module Foo
  class Bar
  end
end

you would use

> clazz = 'Foo::Bar'.split('::').inject(Object) {|o,c| o.const_get c}
  => Foo::Bar 
> clazz.new
  => #<Foo::Bar:0x0000010110a4f8> 
Wes
  • 6,455
  • 3
  • 22
  • 26
19

Very simple in Rails: use String#constantize

class_name = "MyClass"
instance = class_name.constantize.new
edgerunner
  • 14,873
  • 2
  • 57
  • 69
  • 6
    For Rails not Ruby :( – ethicalhack3r Sep 17 '13 at 12:28
  • 1
    Shamelessly copy the [ActiveSupport implementation](https://github.com/rails/rails/blob/375a4143cf5caeb6159b338be824903edfd62836/activesupport/lib/active_support/inflector/methods.rb#L271) if you're not using Rails already – edgerunner Apr 17 '18 at 10:00
6
module One
  module Two
    class Three
      def say_hi
        puts "say hi"
      end
    end
  end
end

one = Object.const_get "One"

puts one.class # => Module

three = One::Two.const_get "Three"

puts three.class # => Class

three.new.say_hi # => "say hi"

In ruby 2.0 and, possibly earlier releases, Object.const_get will recursively perform a lookup on a namespaces like Foo::Bar. The example above is when the namespace is known ahead of time and highlights the fact that const_get can be called on modules directly as opposed to exclusively on Object.

A-Dubb
  • 1,670
  • 2
  • 17
  • 22
6

Try this:

Kernel.const_get("MyClass").new

Then to loop through an object's instance variables:

obj.instance_variables.each do |v|
  # do something
end
mbreining
  • 7,739
  • 2
  • 33
  • 35
  • Thank you, since I really have to loop through the columns of the active record model this won't work for me but it will be useful in my "pure" ruby apps :) – mhenrixon May 07 '11 at 23:12
  • 1
    Check out ActiveRecord#attributes() and/or ActiveRecord#attribute_names(). – mbreining May 07 '11 at 23:18
  • Awesome! http://api.rubyonrails.org/classes/ActiveRecord/Base.html#method-i-attributes – mhenrixon May 08 '11 at 05:57