2009-09-19 77 views
1

我有一个字符串,其中包含一个类名。例如,它是一个包含“Article”的字符串。该字符串来自params []。我应该如何处理这个字符串,就好像它是一个类名?例如,我想做:在字符串和类名字之间施放字符串

Article.all 

等等。

有什么想法?

回答

4

该解决方案优于EVAL你正在评估PARAMS哈希可能由用户来操作,并可能含有对人体有害的行为。作为一般规则:不要直接评估用户输入,这是一个很大的安全漏洞。

# Monkey patch for String class 
    class String 
     def to_class 
     klass = Kernel.const_get(self) 
     klass.is_a?(Class) ? klass : nil 
     rescue NameError 
     nil 
     end 
    end 

# Examples 
"Fixnum".to_class #=> Fixnum 
"Something".to_class #=> nil 

更新 - 一个更好的版本和命名空间的工作原理:

# Monkey patch for String class 
    class String 
     def to_class 
     chain = self.split "::" 
     klass = Kernel 
     chain.each do |klass_string| 
      klass = klass.const_get klass_string 
     end 
     klass.is_a?(Class) ? klass : nil 
     rescue NameError 
     nil 
     end 
    end 
+2

这不会对名称空间类无效,如'MyModule :: MyClass'。为此,你必须分割“::”,然后,例如,使用const_get注入。 – sepp2k 2009-09-19 13:25:54

+0

是的,它需要进一步完善......谢谢! – khelll 2009-09-19 14:04:15

+0

好点。我添加了active_support def,这更符合你的(更好的)建议。 – 2009-09-19 15:41:54

3
class Abc 
end #=> nil 
klass = eval("Abc") #=> Abc 
klass.new #=> #<Abc:0x37643e8> 

假设真的有与所提供的名称类...

在的ActiveSupport,有String#constantize,它也做了同样的事情,但我相信这是2.1后废弃。

编辑:这是constantize从2.1.2的ActiveSupport实施:

def constantize(camel_cased_word) 
    names = camel_cased_word.split('::') 
    names.shift if names.empty? || names.first.empty? 

    constant = Object 
    names.each do |name| 
     constant = constant.const_defined?(name) ? constant.const_get(name) : constant.const_missing(name) 
    end 
    constant 
    end 
+1

这是一个有点危险使用eval为PARAMS原因它可能包含有害代码。我不推荐这个解决方案 – khelll 2009-09-19 11:13:18

+0

哇!非常感谢! – gmile 2009-09-19 11:13:42

+0

khell,任何安全的解决方案? – gmile 2009-09-19 11:14:15

0

我不知道我是否正确地理解你的意图。这里我假设all是一个Article的类方法,all返回一组文章。

class Article 
    def self.all 
     ["Peopleware" , "The Mythical Man-Month"] 
    end 

end 

s = "Article" 
all_of_article = [] 
eval("all_of_article = #{s + ".all"}") 
puts all_of_article.inspect # ["Peopleware", "The Mythical Man-Month"] 
相关问题