Question

I'm using the following:

gem 'friendly_id', github: 'FriendlyId/friendly_id', branch: 'master'

I am creating an Article section on my Rails 4 website. The problem I am having is that when I change a existing article's name the slug is not updated.

This is what I have so far:

extend FriendlyId
friendly_id :name, use: :slugged

add_column :articles, :slug, :string
add_index :articles, :slug, unique: true
Was it helpful?

Solution

In FriendlyId 4 (Rails 3 compatible) there was a method

should_generate_new_friendly_id?

and you could define it on your model to control when slug is regenerated. Try

def should_generate_new_friendly_id?
  name_changed?
end

to regenerate slug when name changes.

EDIT

FriendlyId version 5 (Rails 4 compatible) doesn't regenerate slugs on save anymore. To restore this functionality you can either set slug column to nil before saving or use the solution provided above.

EDIT 2

You need to override the slug setter for your saves to work for Rails <5 & FriendlyId > 5 as referenced in this issue.

Add this to the model file

  def slug=(value)
    if value.present?
      write_attribute(:slug, value)
    end
  end

OTHER TIPS

I have this issues and just want to point out what I've noticed.

if you only do as in docs

class Post < ActiveRecord::Base
 extend FriendlyId
 friendly_id :title, use: :slugged
end

and then run Post.find_each(&:save) - slug is gonna get updated...

However in my case, I also have these in my model

class Post < ActiveRecord::Base
 extend FriendlyId
 friendly_id :title, use: :slugged

 def normalize_friendly_id(text)
   text.to_slug.normalize(transliterations: :russian).to_s
 end

 def should_generate_new_friendly_id?
   title_changed?
 end
end

with the code above it won't do anything when you run Post.find_each(&:save) I assume since your title doesn't change. (first method handles russian language)

so when working with the first model all worked great, but then when I copied ready code to next model I wanted to slugify, I run into some issues. Hope it helps someone.

I was facing a similar issue where the slug don't want to change on update even though I had the following in my model:

def should_generate_new_friendly_id?
  slug.blank? || title_changed?
end

In my case I wasn't setting the title directly via the form but in a before_save callback, and that was the reason, because it seems that FriendlyID needs the change to happen not only before saving but even before_validation so I changed my code to:

before_validation :set_title

def set_title
  self.title = 'some dynamic way of getting title'
end

And, that worked for me!

I really spent too much time trying to figure out why it wasn't working, so I'm posting this case here for anyone who may get stuck in the same situation (and hopefully save you long hours of debugging)

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top