Editing @HarsHarl's answer would probably have made more sense since this answer is very much similar.
With the Thread.current[:current_user]
approach, you would have to make this call to set the User
for every request. You've said that you don't like the idea of setting a variable for every single request that is only used so seldom; you could chose to use skip_before_filter
to skip setting the User or instead of placing the before_filter
in the ApplicationController
set it in the controllers where you need the current_user
.
A modular approach would be to move the setting of created_by_id
and updated_by_id
to a concern and include it in models you need to use.
Auditable module:
# app/models/concerns/auditable.rb
module Auditable
extend ActiveSupport::Concern
included do
# Assigns created_by_id and updated_by_id upon included Class initialization
after_initialize :add_created_by_and_updated_by
# Updates updated_by_id for the current instance
after_save :update_updated_by
end
private
def add_created_by_and_updated_by
self.created_by_id ||= User.current.id if User.current
self.updated_by_id ||= User.current.id if User.current
end
# Updates current instance's updated_by_id if current_user is not nil and is not destroyed.
def update_updated_by
self.updated_by_id = User.current.id if User.current and not destroyed?
end
end
User Model:
#app/models/user.rb
class User < ActiveRecord::Base
...
def self.current=(user)
Thread.current[:current_user] = user
end
def self.current
Thread.current[:current_user]
end
...
end
Application Controller:
#app/controllers/application_controller
class ApplicationController < ActionController::Base
...
before_filter :authenticate_user!, :set_current_user
private
def set_current_user
User.current = current_user
end
end
Example Usage: Include auditable
module in one of the models:
# app/models/foo.rb
class Foo < ActiveRecord::Base
include Auditable
...
end
Including Auditable
concern in Foo
model will assign created_by_id
and updated_by_id
to Foo
's instance upon initialization so you have these attributes to use right after initialization, and they are persisted into the foos
table on an after_save
callback.
created_by_id
andupdated_by_id
attributes? – FrescoThread.current
. If you are willing to go that route, I can come up with an answer. – Mascagni