使用查询字符串的Rails路由

我有一个问题,我需要从GET请求传入的值,我不知道如何设置路由定义。

我的Category对象有一个类型(字符串),一个颜色(字符串)和许多产品。 我想创建一个简单的Web服务,让调用者通过传递Category的类型和颜色来获取所有Category的产品:

http://www.myapp.com/getProducts?catType=toy&color=red 

要么 ?

 http://www.myapp.com/categories/getProducts?catType=toy&color=red 

如何为这种情况定义正确的路由? 是否有更好的方法以宁静的方式做到这一点……因为我知道Rails是Restful,所以如果有一种方法可以“正确”地做到这一点那么那就更好了。

谢谢

你的第一个例子:

 map.getproduct '/getProduct', :controller => 'your_controller', :action => 'your_action' 

在控制器中,你将使用params hash中的catType和color:

 params[:catType] => 'toy' params[:color] => 'red' 

还有更好的方法吗? 可能是的,但这取决于您的需求。 如果你总是有catType和color参数,那么你可以像这样添加路由:

 map.getproduct '/getProduct/:catType/:color', :controller => 'your_controller', :action => 'your_action' 

您可以像上一个示例一样使用params hash访问这些参数。 你的url将如下所示:

 www.myapp.com/getProduct/toy/red 

如果您的参数可能会更改,您可以使用route globbing:

  map.getproduct '/getProduct/*query', :controller => 'your_controller', :action => 'your_action' 

然后它会在开始时捕获www.my.app.com/getProduct/...所有请求。 但是你将在控制器中有更多的工作。 您将有权访问此query

  params[:query] 

并为www.myapp.com/getProduct/color/red/catType/toy它将给出:

  params[:query] => ['color', 'red', 'catType', 'toy] 

所以你必须手动解析它。

一种RESTful方法可以将产品资源嵌套在类别资源下,如下所示:

http://www.myapp.com/categories/toy/products?color=red

您的routes.rb需要包含:

  map.resources :categories do |category| category.resources :products end 

由于我的url上面使用了Category的type属性进行路由,我暗示每个类型都是唯一的,就像id一样。 这意味着无论何时在类别控制器(或其他任何地方)加载类别,您都需要使用Category.find_by_type(params[:id])而不是Category.find_by_type(params[:id])加载类别Category.find(params[:id]) 。 我尽可能以这种方式路由类别。

您的ProductsController控制器索引操作将使用以下行来查找产品:

  @category = Category.find_by_type(params[:category_id]) @products = @category.products.find(:all, :conditions => { :color => params[:color]} ) 

请记住,您的类别模型必须包含以下行:

 has_many :products 

在带有validation的模型中强制执行该操作可能是个好主意:

 validates_presence_of :type validates_uniqueness_of :type 

要使路由工作,您还应该覆盖Category模型中的to_param方法以返回类型而不是id:

 def to_param self.type end