1

有没有办法可以在 polymorphic_path 中使用参数来传递 slug?

例如,我有以下路线

路线.rb

MyApp::Application.routes.draw do

  match "movies/:slug" => 'movies#show', :as=>:movie
  match "series/:slug" => 'series#show', :as=>:series

end

我有以下型号:

电影.rb

class Movie < ActiveRecord::Base
    has_many :cast_members, :as=>:media_item
end

系列.rb

class Series < ActiveRecord::Base
    has_many :cast_members, :as=>:media_item
end

演员表.rb

class CastMember < ActiveRecord::Base
  belongs_to :media_item, :polymorphic=>true
end

这很好用,我可以从演员那里引用我的电影,反之亦然,就像正常的 has_many/belongs_to 关系一样。我也可以在我的 cast_member 视图中执行此操作:

*cast_members/show.html.erb*

link_to (@cast_member.movie.title, movie_path(@cast_member.movie.slug))

返回“电影/电影标题”

我能做到

*cast_members/show.html.erb*

link_to (@cast_member.movie.title, polymorphic_path(@cast_member.media_item))

但这会返回“/movies/24”

我尝试以不同的方式将 slug 作为项目传递给 polymorphic_path,例如

link_to (@cast_member.movie.title, polymorphic_path(@cast_member.media_item, @cast_member.media_item.slug))
link_to (@cast_member.movie.title, polymorphic_path(@cast_member.media_item, :slug=>@cast_member.media_item.slug))
link_to ([@cast_member.movie.title, polymorphic_path(@cast_member.media_item, @cast_member.media_item.slug]))

但这些都返回错误或带有 id 的路径。

如何让 polymorphic_path 使用 movie.slug 而不是 id?

4

2 回答 2

1

我切换到使用friendly_id 生成蛞蝓。它神奇地在后台神奇地处理所有 slug<->id 转换,并解决了这个问题。

我确实认为 rails 应该有一种内置的方式来做到这一点,就像你可以将 slug 传递给默认的 *_path 方法一样。

于 2013-02-27T20:07:45.977 回答
0

我通过使用 Rails 的内置路径助手而不是polymorphic_path. 我真的很想用那个方法,因为它需要使用模型的 ID,我不能。

在我的应用程序中,我有很多“slugable”模型,因此#to_path在 slugable mixin 中包含一个方法是有意义的。

# app/models/concerns/slugable.rb
module Slugable
  extend ActiveSupport::Concern

  included do
    validates :slug, presence: true, uniqueness: {case_sensitive: false}
  end

  def to_path
    path_method = "#{ActiveModel::Naming.singular_route_key(self)}_path"
    Rails.application.routes.url_helpers.send(path_method, slug)
  end

  def slug=(value)
    self[:slug] = value.blank? ? nil : value.parameterize
  end
end

然后在模板中:

<%= link_to my_slugable_model.name, my_slugable_model.to_path %>

如果您的路线中有嵌套资源,则需要调整该资源的代码。

像这样的东西(未经测试):

def to path(my_has_many_model_instance)
   class_path = self.class.to_s.underscore
   has_many_class_path = my_has_many_model_instance.class.to_s.underscore
   path_method = "#{self_path}_#{has_many_class_path}_path"
   Rails.application.routes.url_helpers.send(path_method, slug, my_has_many_model)
end

祝你好运!

于 2018-06-25T20:02:22.363 回答