What is the PaperTrail gem?

The paper trail gem is a wonderful Ruby on Rails gem for tracking all the changes in the model’s data for editing or versioning. After upgrading papertrail gem for an application, you can use it to see how your data looks across different periods. You can take it back to any version of model data. The Ruby on Rails gem “paper_trail_ allows you to undo all the changes after a record has been destroyed so that you can restore it totally. 

Here are a few features of Paper Trail Ggem:- 

  • The PaperTrail gem allows you to track changes made to your Rails models over time. 
  • Any time a tracked record in your database is changed, it creates a corresponding entry in a PaperTrail::Version table. 
  • It accomplishes this by tying into the ActiveRecord callback chain and storing a new version when the record is created, updated, or destroyed.

In this article, we will learn how to use papertrail gem. This guide will take you through the process of installation, and using it in a basic app.

Also Read: 10 best Ruby on Rails Gems for Web Development

Installation and Configuration of PaperTrail:

  • Add PaperTrail to your gemfile

# Gemfile
gem 'paper_trail', '~> 10.3', '>= 10.3.1'

  • Next, create a special table for storing the versions. And run following commands.

bundle exec rails generate paper_trail:install
bundle exec rake db:migrate

  • Declare has_paper_trail method in your model to track create, update and destroy.

class User < ActiveRecord::Base

  • If you have current_user method, you can easily track who is responsible for changes by adding a controller callback.

class User < ActiveRecord::Base
Before_action: set_paper_trail_whodunnit

  • Basic Usage 
    • When you declare a has_paper_trail method you get the following methods.
      • user.versions
        • Returns users versions.
      • user.version
        • Returns user version was reified from, or nil if user live. 
      • user.paper_trail.live?
        • Returns true if this user is current, or false if it is from the previous version.
      • user.paper_trail.originator
        • Returns who put the user into current state.
      • user.paper_trail.version_at(timestamp)
        • It will return the user as it looked at a given timestamp.
      • User.paper_trail.previous_version
        • Returns the user as it was most recently.
      • User.paper_trail.next_version
        • Returns the user as it became next.
  • Configurations
    • PaperTrail has some aspects which are configurable for a specific model by passing the has_paper_trail method in the given model.
    • Some aspects are configured globally for all models.These settings are assigned directly on paperTrail.config object.
    • Put these settings in a rails initializer file such as config/initializers/paper_trail.rb, or in an environment specific file such as config/initializers/test.rb.
      • Global configurations options.

# config/initializers/paper_trail.rb
PaperTrail.config.enabled = true
PaperTrail.config.has_paper_trail_defaults = {on: %i[create update destroy]}
PaperTrail.config.version_limit = 3

  • What is tracked and when
    • You can track an event using on option.
    • has_paper_trails installs callbacks for the specified lifecycle events.
    • There are four default callbacks which is [:create, :update, :touch, :destroy]
    • If there are other callbacks in your model, their order relative to those installed by has_paper_trail may matter. If you need to control their order, use the paper_trail_on_* methods.
    • Include PaperTrail, but do not install any callbacks. Passing the empty array to “:on” omits callbacks.

class User< ActiveRecord::Base
has_paper_trail on: []

  • The paper_trail.on_destroy method can be further configured to happen :before or :after the destroy event. In PaperTrail 4, the default is :after. In PaperTrail 5, the default will be :before.
  • Choosing when to save a new version
    • You can choose when to save the new version with if and unless option.
    • PaperTrail 4.0 versions are saved on during after-callback. If you want to save a version based on change attributes use attribute_name_was instead of attribute_name.
  • Choosing attributes to monitor 
    • Ignore changes to certain attributes

class Article < ActiveRecord::Base
has_paper_trail ignore: [:phone_number]

  • Changes on phone_number attribute will not create a version record.
  • Also you can specify attributes which you care about using only options.

class User< ActiveRecord::Base
has_paper_trail only: [:phone_number]

  • Now only changes on phone_number will create a version record.
  • You can also skip attributes completely with the skip option. When using ignore if version record created due to some other reasons, these attributes will persist.

Class User < ActiveRecord::Base
has_paper_trail skip: [:image_upload]

  • Turn PaperTrail off
    • PaperTrail is on by default but in some cases you don’t want to record versions. At that time turn-off for all threads in the ruby process.

PaperTrail.enabled = false

  • Do not use this in production unless you have a good understanding of threads vs. processes.


So far we have learned how to install PaperTrail gem and use it in a system to keep an eye on records via track. We have seen some basic methods and options given by PaperTrail which are used to. 

For more functionality of PaperTrail refer following link: