问题描述
我在 Page
中有一个基本的 Rails
模型,我将它与 FriendlyId 一起使用,以允许管理员创建 "/about"
或 "/contact"
之类的页面。
我的路由文件 (config/routes.rb
) 中有以下内容,以确保每个页面的 slug 出现在站点的根目录中,例如 https://example.com/about 等:
resources :pages,except: [:show]
resources :pages,only: [:show],path: "/"
问题是,使用这种方法,我不能在我的视图(或测试或控制器)中使用像 page_path(@page)
这样的普通命名路由,因为它路由到 "/pages/about"
并且我得到"No route matches [GET] pages/about" error.
我可以在我的路由文件中执行这两个路由,以便 "/pages/about"
和 "/about"
像这样工作:
resources :pages
resources :pages,path: "/"
但是,这会产生 SEO
重复的内容问题。我想我可以创建一个帮助程序,为 rel="canonical"
标题中的每个页面设置 html
url,但这也感觉像是一个黑客。我希望根目录下的每个页面只有 1 个版本,并且还有一个命名路由,例如 "page_path"
或 "root_page_path"
,我可以在整个应用程序中使用。
我暂时想到的 hack 是 <%= link_to "#{page.slug}" %>
,但没有命名路由似乎很脆弱。
在 Rails
中执行此操作的更“正确”方法是什么?
我希望这样的事情能奏效:
resources :pages,path: "/",as: "page"
但这也行不通。 Rails guide on routing 中的任何内容也没有真正的帮助。
解决方法
你需要 top 切换它们的定义顺序:
resources :pages,only: [:show],path: "/"
resources :pages,except: [:show]
resources
只为具有给定 url 的第一个路径命名。但是 - 您现在会遇到问题,因为 pages/:id
路径(用于删除和更新)现在没有路由助手(因为它通常与 show
相同)。
编辑:如评论中所述 - 它还会自动将 /pages
路径与 id
等于 pages
的显示操作匹配 - 不是一个好主意!这会导致更好的选择:
resources :pages,except: [:show]
get :id,to: "pages#show",as: :root_page
这为您提供了 root_page_path(@page)
操作的 :show
助手和 page_path(@page)
和 :update
的 :delete