FriendlyId is an awesome gem for slugging and permalinking for Active Record. It works like a charm except one case: when you set friendly_id field in a before_validation callback.
Here's an example:
class User < ActiveRecord::Base
extend FriendlyId
friendly_id :login, use: %i( history finders )
before_validation :set_login
def set_login
# This weird method will just generate a random string
self.login = (0...8).map { (65 + rand(26)).chr }.join
end
end
User.new.save!
User.last.login #=> 'bhkcjvrd'
User.last.to_param #=> user id
User.last.slug #=> ''
It happens because FriendlyId uses a before_validation callback to set a slug. This method is invoked before any before_validation callbacks that you define in your class.
To fix this you can either invoke friendly_id after you set your before_validation callbacks, or you can just prepend your method before friendly_id:
class User < ActiveRecord::Base
extend FriendlyId
friendly_id :login, use: %i( history finders )
before_validation :set_login
prepend: true
def set_login
# This weird method will just generate a random string
self.login = (0...8).map { (65 + rand(26)).chr }.join
end
end
User.new.save!
User.last.login #=> 'bhkcjvrd'
User.last.to_param #=> 'bhkcjvrd'
User.last.slug #=> 'bhkcjvrd'