自定义 Mongoid 4.0.0 _id 包含 . (点)不能通过参数查询(Rails 4)

Posted

技术标签:

【中文标题】自定义 Mongoid 4.0.0 _id 包含 . (点)不能通过参数查询(Rails 4)【英文标题】:Custom Mongoid 4.0.0 _id that contains . (dot) can't be queried throught params (Rails 4) 【发布时间】:2013-12-26 09:58:39 【问题描述】:

我有一个模型,它用唯一的url 属性覆盖_id 属性:

class Website
  include Mongoid::Document
  include Mongoid::Timestamps
  field :_id, type: String, default: -> url 
  field :url, type: String
  validates_uniqueness_of :url
end

我的控制器很标准:

class WebsitesController < ApplicationController
  def show
    @website = Website.find(params[:id])
  end
end

我的视图文件中的链接生成是:

Website.all.each do |website|
  %p= link_to website.url, website_path(:id => website._id)

到目前为止一切顺利。但是假设我有一个带有_id"example.com" 的网站。当我单击指向website_path(:id =&gt; "example.com") 的链接时,参数:id.(点)之前被删除。所以,我自然会得到这个错误:

Started GET "/websites/example.com" for 127.0.0.1 at 2013-12-26 10:36:10 +0100
Processing by WebsitesController#show as 
  Parameters: "id"=>"example"
  MOPED: 127.0.0.1:27017 QUERY        database=myapp_development collection=websites selector="_id"=>"example" flags=[] limit=0 skip=0 batch_size=nil fields=nil runtime: 0.5150ms

Mongoid::Errors::DocumentNotFound - 
...
...

我该如何解决这个问题?

【问题讨论】:

【参考方案1】:

您遇到了路由问题。来自Routing Guide:

默认情况下,动态段不接受点 - 这是因为点被用作格式化路线的分隔符。如果您需要在动态段中使用点,请添加一个覆盖它的约束——例如,id: /[^\/]+/ 允许除斜线之外的任何内容

所以你需要将你的路线调整成这样:

get '/websites/:id' => 'websites#show', :id => /[^\/]+/
# --------------------------------------^^^^^^^^^^^^^^^

这样 Rails 路由系统就不会认为 .com 是像 .html.js、...这样的格式扩展名。

【讨论】:

以上是关于自定义 Mongoid 4.0.0 _id 包含 . (点)不能通过参数查询(Rails 4)的主要内容,如果未能解决你的问题,请参考以下文章

自定义Realm

删除 MongoID 文档中数组的最后一个元素 - Rails

rails mongoid中的多键索引

Mongoid 聚合 $match 与 Date 对象不起作用?

在 Mongoid 中检索 id 数组

rails 4 gem 'mongoid_slug' 无法按 id 搜索