Module: DataMapper::Is::Revisioned

Included in:
Resource::ClassMethods
Defined in:
lib/dm-is-revisioned/is/revisioned.rb,
lib/dm-is-revisioned/is/version.rb

Overview

Is Revisioned

The Revisioned module is similar to Versioned but is sufficiently different that it justified a fork.

Just like with Versioned, there is not an incrementing ‘version’ field, but rather, any field of your choosing which will be unique on update. However, Revisioned will let you specify exactly when a new version should be created. By default, this happens when the record is created or whenever the field you specified changes.

Setup

For simplicity, I will assume that you have loaded dm-timestamps to automatically update your :updated_at field. See versioned_spec for and example of updating the versioned field yourself.

class Story
  include DataMapper::Resource
  property :id, Serial
  property :title, String
  property :updated_at, DateTime

  is_revisioned :on => :updated_at
end

Auto Upgrading and Auto Migrating

Story.auto_migrate! # => will run auto_migrate! on Story::Version, too
Story.auto_upgrade! # => will run auto_upgrade! on Story::Version, too

Usage

story = Story.crreate(:title => "A Title") # Creates a new version
story.versions.size # => 1
story = Story.get(1)
story.title = "New Title"
story.save # Saves this story and creates a new version 
story.versions.size # => 2

story.title = "A Different New Title"
story.save
story.versions.size # => 3

Specifying when a new version should occur

You can override the wants_new_version? method to determine exactly when a new version should be created. The method versioned_attribute_changed? is provided for your convenience, and can be used inside wants_new_version?

TODO: enable replacing a current version with an old version.

Defined Under Namespace

Modules: InstanceMethods

Constant Summary collapse

VERSION =
"0.1.0"

Instance Attribute Summary collapse

Instance Method Summary collapse

Instance Attribute Details

#versioned_property_nameObject (readonly)

Returns the value of attribute versioned_property_name.



53
54
55
# File 'lib/dm-is-revisioned/is/revisioned.rb', line 53

def versioned_property_name
  @versioned_property_name
end

Instance Method Details

#is_revisioned(options = {}) ⇒ Object



55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
# File 'lib/dm-is-revisioned/is/revisioned.rb', line 55

def is_revisioned(options = {})
  include DataMapper::Is::Revisioned::InstanceMethods
  
  @versioned_property_name = on = options[:on]

  class << self; self end.class_eval do
    define_method :const_missing do |name|
      storage_name = Extlib::Inflection.tableize(self.name + "Version")
      model = DataMapper::Model.new(storage_name)

      if name == :Version
        properties.each do |property|
          options = property.options
          options[:key] = true if property.name == on || options[:serial] == true
          options[:serial] = false
          model.property property.name, property.type, options
        end

        self.const_set("Version", model)
      else
        super(name)
      end
    end
  end

  after_class_method :auto_migrate! do
    self::Version.auto_migrate!
  end

  after_class_method :auto_upgrade! do
    self::Version.auto_upgrade!
  end
  
  before :create, :check_if_wants_new_version
  after  :create, :save_new_version
  
  before :update, :check_if_wants_new_version
  after  :update, :save_new_version
end