Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How do I convert a Ruby class name to a underscore-delimited symbol?

How can I programmatically turn a class name, FooBar, into a symbol, :foo_bar? e.g. something like this, but that handles camel case properly?

FooBar.to_s.downcase.to_sym 
like image 246
Josh Glover Avatar asked Apr 11 '11 14:04

Josh Glover


People also ask

How do I convert a string to a symbol in Ruby?

Converting between symbols to strings is easy - use the . to_s method. Converting string to symbols is equally easy - use the . to_sym method.

How to convert string into float in Ruby?

Converting Strings to Numbers Ruby provides the to_i and to_f methods to convert strings to numbers. to_i converts a string to an integer, and to_f converts a string to a float.

How do you change Camelcase to snake case in Ruby?

Method: String#snakecase Underscore a string such that camelcase, dashes and spaces are replaced by underscores. This is the reverse of #camelcase, albeit not an exact inverse. Note, this method no longer converts `::` to `/`, in that case use the #pathize method instead.

What is snake case in Ruby?

Snake case is a naming convention in which a developer replaces spaces between words with an underscore. Most object-oriented programming languages don't allow variable, method, class and function names to contain spaces.


2 Answers

Rails comes with a method called underscore that will allow you to transform CamelCased strings into underscore_separated strings. So you might be able to do this:

FooBar.name.underscore.to_sym 

But you will have to install ActiveSupport just to do that, as ipsum says.

If you don't want to install ActiveSupport just for that, you can monkey-patch underscore into String yourself (the underscore function is defined in ActiveSupport::Inflector):

class String   def underscore     word = self.dup     word.gsub!(/::/, '/')     word.gsub!(/([A-Z]+)([A-Z][a-z])/,'\1_\2')     word.gsub!(/([a-z\d])([A-Z])/,'\1_\2')     word.tr!("-", "_")     word.downcase!     word   end end 
like image 72
kikito Avatar answered Nov 08 '22 23:11

kikito


Rails 4 .model_name

In Rails 4, it returns an ActiveModel::Name object which contains many useful more "semantic" attributes such as:

FooBar.model_name.param_key #=> "foo_bar"  FooBar.model_name.route_key #=> "foo_bars"  FooBar.model_name.human #=> "Foo bar" 

So you should use one of those if they match your desired meaning, which is likely the case. Advantages:

  • easier to understand your code
  • your app will still work even in the (unlikely) event that Rails decides to change a naming convention.

BTW, human has the advantage of being I18N aware.