简体   繁体   English

在polymorphic_path中使用块

[英]Using slugs in polymorphic_path

Is there a way I can use parameters in a polymorphic_path, to pass in a slug? 有没有办法我可以在polymorphic_path中使用参数来传递一个标签?

For instance, I have the following routes 例如,我有以下路线

routes.rb 的routes.rb

MyApp::Application.routes.draw do

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

end

And I have the following models: 我有以下模型:

Movie.rb 电影.rb

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

Series.rb Series.rb

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

CastMember.rb CastMember.rb

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

This works great, and I can reference my movie from the cast member, and vice-versa, just like a normal has_many/belongs_to relationship. 这很有效,我可以从演员中引用我的电影,反之亦然,就像正常的has_many / belongs_to关系一样。 I can also do this from within my cast_member view: 我也可以从我的cast_member视图中执行此操作:

*cast_members/show.html.erb* * cast_members / show.html.erb *

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

which returns "movie/movie-title" 返回“电影/电影标题”

and I can do 我可以做

*cast_members/show.html.erb* * cast_members / show.html.erb *

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

but this returns "/movies/24" 但这返回“ / movies / 24”

I've tried passing a slug as an item to polymorphic_path in different ways, like 我尝试以不同的方式将子弹作为项目传递给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]))

but these all return errors or the path with the id. 但是这些都返回错误或带有ID的路径。

How can I make the polymorphic_path use the movie.slug instead of the id? 如何使polymorphic_path使用movie.slug而不是id?

I switched over to using friendly_id to generate slugs. 我切换到使用friendly_id来生成弹头。 It magically handles all the slug<->id conversions magically in the background, and sosolves the issue. 它神奇地在后台处理所有slug <-> id转换,并解决了问题。

I do think that rails should have a baked-in way to do this, the same way you can pass a slug into the default *_path methods. 我确实认为,rails应该具有一种内置的方法来执行此操作,就像您可以将一个slug传递给默认的* _path方法一样。

I solved this by using Rails' built-in path helpers instead of polymorphic_path . 我通过使用Rails的内置路径助手而不是polymorphic_path解决了这个问题。 I really wanted to use that method, since it required use of the model's ID, I couldn't. 我真的很想使用该方法,因为它需要使用模型的ID,所以我不能。

In my app, I have a lot of models that are "slugable", so it made sense to include a #to_path method in the slugable mixin. 在我的应用程序中,我有很多“可投放”模型,因此在可投放的mixin中包含#to_path方法是有意义的。

# 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

then in the templates: 然后在模板中:

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

If you have nested resources in your routes, then you'll need to adjust the code for that resource. 如果您的路线中嵌套了资源,则需要调整该资源的代码。

something like this (untested): 像这样(未经测试):

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

Good luck! 祝好运!

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM