代码之家  ›  专栏  ›  技术社区  ›  carpeliam

最好的方法是在Rails中执行“/blogs/:year/:month/:day/:permalink”路由?

  •  6
  • carpeliam  · 技术社区  · 16 年前

    我有一个博客控制器和一个博客资源,所以我现在有你的典型路线如下:

    /blogs/new
    /blogs/1
    /blogs/1/edit #etc
    

    但我想要的是:

    /blogs/new
    /blogs/2010/01/08/1-to_param-or-something
    /blogs/2010/01/08/1-to_param-or-something/edit #etc
    ...
    /blogs/2010/01 # all posts for January 2010, but how to specify custom action?
    

    我知道我可以通过map.resources和map.connect的组合来实现这一点,但是我有很多视图可以通过“新博客路径”等链接到其他页面,我不想去编辑它们。仅使用map.resources就可以做到这一点吗?这也许不容易,但我并不反对聪明。我在想:

    map.resources :blogs, :path_prefix => ':year/:month/:day', :requirements => {:year => /\d{4}/, :month => /\d{1,2}/, :day => /\d{1,2}/}
    

    但我不确定这是如何与“新建”或“创建”这样的操作一起工作的,它也给了我一条类似的路径 /2010/01/08/blogs/1-to_param-etc 在URL中间有博客。

    那么,有没有一个聪明的解决方案我找不到,或者我需要走地图连接路线?

    2 回复  |  直到 16 年前
        1
  •  13
  •   Jay Mendoza    16 年前

    我最近遇到了同样的问题,虽然这可能不是你想要的,但这是我为解决它所做的:

    配置/路由.rb :

    map.entry_permalink 'blog/:year/:month/:day/:slug',
                        :controller => 'blog_entries',
                        :action     => 'show',
                        :year       => /(19|20)\d{2}/,
                        :month      => /[01]?\d/,
                        :day        => /[0-3]?\d/
    

    blog_entries_controller.rb:

    def show
      @blog_entry = BlogEntry.find_by_permalink(params[:slug])
    end
    

    blog_entries_helper.rb:

    def entry_permalink(e)
      d = e.created_at
      entry_permalink_path :year => d.year, :month => d.month, :day => d.day, :slug => e.permalink
    end
    

    _ entry.html.erb:

    <h2><%= link_to(entry.title, entry_permalink(entry)) %></h2>
    

    为了完整起见:

    博客:

    before_save :create_permalink
    
    #...
    
    private
    
    def create_permalink
      self.permalink = title.to_url
    end
    

    “to”URL方法来自RSL Stringex .

    我对Rails(和编程)还是个新手,但这可能是最简单的方法。不幸的是,这不是一种安逸的做事方式,所以你不会从map.resources中获益。

    我不确定(因为我没有尝试过),但您可以在 application_helper.rb 覆盖blog_path等的默认路由帮助程序。如果可以,那么您就不必更改任何视图代码。

    如果你有冒险精神,你可以去看看 Routing Filter . 我考虑过使用它,但这项任务似乎太过分了。

    此外,如果您不知道,可以做两件事来测试脚本/控制台中的路由/路径:

    rs = ActionController::Routing::Routes
    rs.recognize_path '/blog/2010/1/10/entry-title'
    

    app.blog_entry_path(@entry)
    

    祝你好运!

        2
  •  2
  •   Jarrett Meyer    16 年前

    API Docs 以下内容:

    map.connect 'articles/:year/:month/:day',
                :controller => 'articles',
                :action     => 'find_by_date',
                :year       => /\d{4}/,
                :month      => /\d{1,2}/,
                :day        => /\d{1,2}/
    

    使用上面的路由,URL“localhost:3000/articles/2005/11/06”映射到

    params = { :year => '2005', :month => '11', :day => '06' }
    

    看起来你想做同样的事情,但后缀一个后段塞。您的新链接和编辑链接仍然是“老学校”链接,如“localhost:3000/articles/1/edit”和“localhost:3000/articles/new”。只是“显示”链接应该用这个更新。