在Ruby on Rails中验证slug时排除方法名称?

时间:2011-10-24 11:05:39

标签: ruby ruby-on-rails-3 validation

我想知道如何针对控制器的所有方法名称(不一定是self中的那些)来验证slug(来自用户输入)而不是硬编码,所以说tag/tomato是有效的,但/tag/all不是,因为控制器all中有Tag方法?使用反射?

还是有更好的做法?

2 个答案:

答案 0 :(得分:2)

听起来你真的想要防止路由冲突,而且只是松散地连接到控制器中的方法名称。

您可以从

运行时获取所有路线
Rails.application.routes.routes

它为您提供了一个ActionDispatch::Routing::Route实例数组。然后,获得GET路线:

gettable = Rails.application.routes.routes.select do |r|
    r.verb == 'GET' || r.verb == '' # Watch out for "no verb" -> "all verbs"
end

从那里你可以提取路径并检查你的标签是否与其中任何一个都不匹配:

paths = Rails.application.routes.routes.
        select { |r| r.verb == 'GET' || r.verb == '' }.
        map    { |r| r.path                          }

这会在/this/:that(.:format)中为您提供paths样式路径列表。

一旦完成所有这些,您将需要一个应用程序初始化程序来检查您是否没有添加任何恰好与标记数据库的当前状态匹配的/tag/命名空间的路由;否则,冲突可能会在发展过程中蔓延。

这应该说服你最好保留正常的路线,以便在人/ SEO友好/tag/pancakes路线的单独命名空间中创建,查看等。您可以将常用的内容保留在/tag中,但将友好的内容移至/taxonomy//category/或类似内容。

答案 1 :(得分:1)

您可以获取控制器中定义的方法列表,如下所示:

TagController.instance_methods(false)

请注意,通过将false作为参数传递给instance_methods,您将获得继承的方法列表。