Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Rails plugin for comparing two instances of a class.
Ruby JavaScript
tree: d0fbaf218c

Fetching latest commit…

Cannot retrieve the latest commit at this time

Failed to load latest commit information.
lib
test
.gitignore
MIT-LICENSE
README
Rakefile
VERSION
acts_as_diffable.gemspec
init.rb

README

ActsAsDiffable provides a dead-simple way to compare two instances of a class,
including any or all associations, or more complex relationships.

The return is a hash*, suitable for digestion by case-based textualizers, 
JSON processors, etc., in the form { 'attribute' => [from, to] }
* In the instance of no changes, a nil is returned
 
== Usage

  class Foo < ActiveRecord::Base
    acts_as_diffable
  end
  > Foo.first.diff(Foo.last) => { 'bar' => ['foo', nil] }

=== Associations

For plural associations, a :diff_key option needs to be added to the association,
defining how to relate disparate instances within each parent's collections.  
This can be a single field or a collection of fields in an array, and will be 
expressed as the key side of a hash with the value being the hash of attribute 
differences.

For singular association, there is no need to specify a way to organize and
compare, so we only need to express which associations to include in the diff,
by adding a :diff option to the association that evaluates to true.

  class Foo < ActiveRecord::Base
    acts_as_diffable
   
    has_one :bar, :diff => true
    has_many :fish, :diff_keypattern => :name
    has_and_belongs_to_many :users, :diff_keypattern => [:firstname, :lastname]
  end
  > Foo.first.diff(Foo.last) 
  => { 'bar'   => { 'attr1' => ['a', 'b'], 
                    'attr2' => [14, nil] },
       'fish   => { 'nemo'   => {'fish_attr1' => [nil, 'zip']   },
                    'goldie' => {'fish_attr1' => ['zap', 'zop'] } },
       'users' => { ['Jane', 'Doe'] => { 'firstname' => 'Jane',
                                         'lastname'  => 'Doe' },
                    ['John', 'Doe'] => { '_deleted' => true   } } }

=== More complex relationships

In addition to the marked associations, any method on the class that returns an
ActiveRecord-ish object can be included in the diff by adding a 
manual_diff_definiton.  For comparing collections of ActiveRecord objects, 
use the form:

  manual_diff_definition :name, :eval => 'instance_eval_code',
                                :diff_key => [:key, :pattern]
                                
For simpler singular comparisons, omit the diff_key option.


Have a lot of fun!
Something went wrong with that request. Please try again.