simply_versioned 0.9.3.2
Sign up to get free protection for your applications and to get access to all the features.
- data/CHANGES +51 -0
- data/MIT-LICENSE +20 -0
- data/README +140 -0
- data/Rakefile +31 -0
- data/generators/simply_versioned_migration/simply_versioned_migration_generator.rb +11 -0
- data/generators/simply_versioned_migration/templates/migration.rb +18 -0
- data/init.rb +1 -0
- data/install.rb +1 -0
- data/lib/simply_versioned.rb +229 -0
- data/lib/version.rb +47 -0
- data/rdoc/classes/SoftwareHeretics.html +122 -0
- data/rdoc/classes/SoftwareHeretics/ActiveRecord.html +111 -0
- data/rdoc/classes/SoftwareHeretics/ActiveRecord/SimplyVersioned.html +149 -0
- data/rdoc/classes/SoftwareHeretics/ActiveRecord/SimplyVersioned/ClassMethods.html +159 -0
- data/rdoc/classes/SoftwareHeretics/ActiveRecord/SimplyVersioned/InstanceMethods.html +178 -0
- data/rdoc/classes/SoftwareHeretics/ActiveRecord/SimplyVersioned/VersionsProxyMethods.html +286 -0
- data/rdoc/created.rid +1 -0
- data/rdoc/files/README.html +216 -0
- data/rdoc/files/lib/simply_versioned_rb.html +112 -0
- data/rdoc/files/lib/version_rb.html +112 -0
- data/rdoc/fr_class_index.html +32 -0
- data/rdoc/fr_file_index.html +29 -0
- data/rdoc/fr_method_index.html +36 -0
- data/rdoc/index.html +24 -0
- data/rdoc/rdoc-style.css +208 -0
- data/simply_versioned.gemspec +18 -0
- data/tasks/simply_versioned_tasks.rake +4 -0
- data/test/simply_versioned_test.rb +326 -0
- data/test/test_helper.rb +56 -0
- data/uninstall.rb +1 -0
- metadata +117 -0
data/CHANGES
ADDED
@@ -0,0 +1,51 @@
|
|
1
|
+
0.9.3.1 - 20-05-2008 Jérôme Lipowicz
|
2
|
+
|
3
|
+
Pragmatic branch (using dirty parameters, rails 2.1 only)
|
4
|
+
New records are not versioned: two versions are created at once upon first record update.
|
5
|
+
Unchanged records are not versioned too.
|
6
|
+
|
7
|
+
0.9.3 - 28-01-2008
|
8
|
+
|
9
|
+
Fixed #version_number to versioned instances as a shortcut
|
10
|
+
|
11
|
+
0.9.2 - 28-01-2008
|
12
|
+
|
13
|
+
Fixed :exclude => :column now equivalent to :exclude => [:column]
|
14
|
+
|
15
|
+
0.9.1 - 24-01-2008
|
16
|
+
|
17
|
+
Improved implementation of revert_to_version with further tests.
|
18
|
+
Provided clean aliases for methods in VersionProxy.
|
19
|
+
|
20
|
+
0.9 - 24-01-2008
|
21
|
+
|
22
|
+
Added an :exclude option (default: [])
|
23
|
+
|
24
|
+
0.8 - 08-01-2008
|
25
|
+
|
26
|
+
Added an :automatic option (default: true)
|
27
|
+
|
28
|
+
0.7 - 04-01-2008
|
29
|
+
|
30
|
+
The without_versioning method becomes with_versioning( exp )
|
31
|
+
|
32
|
+
0.6 - 01-01-2008
|
33
|
+
|
34
|
+
The default is now to keep all versions, specify :keep if you want to set a limit.
|
35
|
+
Dropped the updated_at column from revisions as unnecessary.
|
36
|
+
|
37
|
+
0.5 - 30-12-2007
|
38
|
+
|
39
|
+
The revert_to_version call now takes an :except => [:name,:and,:so,:on] list of attributes whose value will not be reverted. The defautl is [:created_at,:updated_at].
|
40
|
+
|
41
|
+
0.4 - 30-12-2007
|
42
|
+
|
43
|
+
Changed some method names to reduce possibility of conflicts. Added more tests. Changed some method implementations w.r.t. empty versions to try and tease out a bug in production.
|
44
|
+
|
45
|
+
0.3 - 30-12-2007
|
46
|
+
|
47
|
+
Added versioning_enabled? and without_versioning( &block ) to allow save without a version being generated.
|
48
|
+
|
49
|
+
0.2 - 30-12-2007
|
50
|
+
|
51
|
+
Added a test & some documentation, shaved a yak or two
|
data/MIT-LICENSE
ADDED
@@ -0,0 +1,20 @@
|
|
1
|
+
Copyright (c) 2007 Matt Mower
|
2
|
+
|
3
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
4
|
+
a copy of this software and associated documentation files (the
|
5
|
+
"Software"), to deal in the Software without restriction, including
|
6
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
7
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
8
|
+
permit persons to whom the Software is furnished to do so, subject to
|
9
|
+
the following conditions:
|
10
|
+
|
11
|
+
The above copyright notice and this permission notice shall be
|
12
|
+
included in all copies or substantial portions of the Software.
|
13
|
+
|
14
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
15
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
16
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
17
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
18
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
19
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
20
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README
ADDED
@@ -0,0 +1,140 @@
|
|
1
|
+
SimplyVersioned
|
2
|
+
===============
|
3
|
+
|
4
|
+
Release: 0.9.3.2
|
5
|
+
Date: 05-04-2010
|
6
|
+
Author: Matt Mower <self@mattmower.com>
|
7
|
+
Fork: Jerôme Lipowicz <yayel.com>
|
8
|
+
|
9
|
+
SimplyVersioned is a simple, non-invasive, approach to versioning ActiveRecord models.
|
10
|
+
|
11
|
+
SimplyVersioned does not require any structural change to the models to be versioned and requires only one versions table to be created (a migration generator is supplied with the plugin) regardless of the number of models being versioned.
|
12
|
+
|
13
|
+
The plugin introduces a 'Version' ActiveRecord model (that reflects changes to model attributes) to which versioned models are polymorphically associated. Version records store the model information as a YAML hash.
|
14
|
+
|
15
|
+
SimplyVersioned meets a simple need for model versioning. If your needs are more complex maybe try Rick Olsen's acts_as_versioned (http://svn.techno-weenie.net/projects/plugins/acts_as_versioned/).
|
16
|
+
|
17
|
+
SimplyVersioned is only compatible with Rails 2.1. This pragmatic branch only versions altered records.
|
18
|
+
|
19
|
+
Usage
|
20
|
+
=====
|
21
|
+
|
22
|
+
1. Install the lib
|
23
|
+
|
24
|
+
1.1 as a plugin:
|
25
|
+
|
26
|
+
./script/plugin install git://github.com/jerome/simply_versioned.git
|
27
|
+
|
28
|
+
1.2 or as a gem:
|
29
|
+
|
30
|
+
gem install simply_versioned
|
31
|
+
|
32
|
+
# environment.rb
|
33
|
+
config.gem "simply_versioned"
|
34
|
+
|
35
|
+
2. Generate the migration
|
36
|
+
|
37
|
+
./script/generate simply_versioned_migration
|
38
|
+
|
39
|
+
Note that the migration defaults to storing the version info in a TEXT field. On MySQL this will default to a
|
40
|
+
limit of 64K. If you are versioning particularly large models you will want to modify the migration to include
|
41
|
+
a :limit => n condition to promote the yaml column to a MEDIUMTEXT or (god forbid) a LONGTEXT.
|
42
|
+
|
43
|
+
3. Create the versions table
|
44
|
+
|
45
|
+
rake db:migrate
|
46
|
+
|
47
|
+
4. Annotate the models you want to version specifying how many versions to keep
|
48
|
+
|
49
|
+
class Thing < ActiveRecord::Base
|
50
|
+
simply_versioned :keep => 10
|
51
|
+
end
|
52
|
+
|
53
|
+
If you do not specify a limit then old versions are never automatically deleted. You can
|
54
|
+
manually delete them like this:
|
55
|
+
|
56
|
+
thing.versions.purge( 10 )
|
57
|
+
|
58
|
+
which would delete all the but the last ten versions.
|
59
|
+
|
60
|
+
If you want fine-grained control over when versions are created you can use:
|
61
|
+
|
62
|
+
class Thing < ActiveRecord::Base
|
63
|
+
simply_versioned :automatic => false
|
64
|
+
end
|
65
|
+
|
66
|
+
and new versions will no longer be created by default. You will then need to use
|
67
|
+
the with_versioning method to create a version.
|
68
|
+
|
69
|
+
Lastly you can control which columns will be versioned by specifying an exclude parameter.
|
70
|
+
|
71
|
+
class Thing < ActiveRecord::Base
|
72
|
+
simply_versioned :exclude => :awkward_column
|
73
|
+
end
|
74
|
+
|
75
|
+
or
|
76
|
+
|
77
|
+
class Thing < ActiveRecord::Base
|
78
|
+
simply_versioned :exclude => [:first_awkward_column,:second_awkward_column,...]
|
79
|
+
end
|
80
|
+
|
81
|
+
This may be helpful if you run into conflicts with other plugins which try to manage columns.
|
82
|
+
|
83
|
+
5. Create versions
|
84
|
+
|
85
|
+
thing = Thing.create!( :foo => bar ) # creates v1
|
86
|
+
thing.foo = baz
|
87
|
+
thing.save! # creates v2
|
88
|
+
|
89
|
+
If you need to control whether a version is created or not, use #with_versioning. For example:
|
90
|
+
|
91
|
+
thing.with_versioning( false ) do |t|
|
92
|
+
t.save!
|
93
|
+
end
|
94
|
+
|
95
|
+
or, using the "magic pen" (http://dablog.rubypal.com/2007/2/18/the-magic-pens-of-ruby thanks hmj):
|
96
|
+
|
97
|
+
thing.with_versioning( false, &:save! )
|
98
|
+
|
99
|
+
6. Find versions
|
100
|
+
|
101
|
+
thing.versions.each do |version| ... end
|
102
|
+
render :partial => 'thing_version', :collection => thing.versions
|
103
|
+
thing.versions.current
|
104
|
+
thing.versions.first
|
105
|
+
thing.versions.get( 3 )
|
106
|
+
|
107
|
+
To find a version number:
|
108
|
+
|
109
|
+
thing.version_number
|
110
|
+
|
111
|
+
7. Revert to a previous version
|
112
|
+
|
113
|
+
thing.revert_to_version( 5 )
|
114
|
+
|
115
|
+
If a specific reversion needs to avoid overwriting some column values pass
|
116
|
+
an :except option, e.g.
|
117
|
+
|
118
|
+
thing.revert_to_version( 1, :except => [:name,:age] )
|
119
|
+
|
120
|
+
The revert_to_version method also takes an existing Version instance, e.g.
|
121
|
+
|
122
|
+
version = thing.versions.find( ... )
|
123
|
+
thing.revert_to_version( version )
|
124
|
+
|
125
|
+
8. Traverse versions
|
126
|
+
|
127
|
+
thing.versions.current.previous
|
128
|
+
thing.versions.first.next
|
129
|
+
|
130
|
+
9. Obtain a copy of a previous versioned model
|
131
|
+
|
132
|
+
thing.versions.first.model # => Instantiated Thing with versioned values
|
133
|
+
|
134
|
+
Thanks to:
|
135
|
+
|
136
|
+
Josh Susser (http://blog.hasmanythrough.com/) for useful suggestions and feedback
|
137
|
+
Rick Olson (http://techno-weenie.net/) for all the many plugins whose code i've read
|
138
|
+
|
139
|
+
Copyright (c) 2007 Matt Mower <self@mattmower.com> and released under the MIT license
|
140
|
+
Copyright (c) 2008 Jérôme Lipowicz <yayel.com> and released under the MIT license
|
data/Rakefile
ADDED
@@ -0,0 +1,31 @@
|
|
1
|
+
require 'rake'
|
2
|
+
require 'rake/testtask'
|
3
|
+
require 'rake/rdoctask'
|
4
|
+
|
5
|
+
desc 'Default: run unit tests.'
|
6
|
+
task :default => :test
|
7
|
+
|
8
|
+
desc 'Test the simply_versioned plugin.'
|
9
|
+
Rake::TestTask.new(:test) do |t|
|
10
|
+
t.libs << 'lib'
|
11
|
+
t.pattern = 'test/**/*_test.rb'
|
12
|
+
t.verbose = true
|
13
|
+
end
|
14
|
+
|
15
|
+
desc 'Generate documentation for the simply_versioned plugin.'
|
16
|
+
Rake::RDocTask.new(:rdoc) do |rdoc|
|
17
|
+
rdoc.rdoc_dir = 'rdoc'
|
18
|
+
rdoc.title = 'SimplyVersioned'
|
19
|
+
rdoc.options << '--line-numbers' << '--inline-source'
|
20
|
+
rdoc.rdoc_files.include('README')
|
21
|
+
rdoc.rdoc_files.include('lib/**/*.rb')
|
22
|
+
end
|
23
|
+
|
24
|
+
desc 'Measures test coverage using rcov'
|
25
|
+
task :rcov do
|
26
|
+
rm_f "coverage"
|
27
|
+
rm_f "coverage.data"
|
28
|
+
rcov = "rcov --rails --aggregate coverage.data --text-summary -Ilib"
|
29
|
+
system("#{rcov} --html #{Dir.glob('test/**/*_test.rb').join(' ')}")
|
30
|
+
system("open coverage/index.html") if PLATFORM['darwin']
|
31
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
class SimplyVersionedMigration < ActiveRecord::Migration
|
2
|
+
|
3
|
+
def self.up
|
4
|
+
create_table :versions do |t|
|
5
|
+
t.integer :versionable_id
|
6
|
+
t.string :versionable_type
|
7
|
+
t.integer :number
|
8
|
+
t.text :yaml
|
9
|
+
t.datetime :created_at
|
10
|
+
end
|
11
|
+
|
12
|
+
add_index :versions, [:versionable_id, :versionable_type]
|
13
|
+
end
|
14
|
+
|
15
|
+
def self.down
|
16
|
+
drop_table :versions
|
17
|
+
end
|
18
|
+
end
|
data/init.rb
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
require 'simply_versioned'
|
data/install.rb
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
# Install hook code here
|
@@ -0,0 +1,229 @@
|
|
1
|
+
# SimplyVersioned 0.9.3
|
2
|
+
#
|
3
|
+
# Simple ActiveRecord versioning
|
4
|
+
# Copyright (c) 2007,2008 Matt Mower <self@mattmower.com>
|
5
|
+
# Released under the MIT license (see accompany MIT-LICENSE file)
|
6
|
+
#
|
7
|
+
|
8
|
+
module SoftwareHeretics
|
9
|
+
|
10
|
+
module ActiveRecord
|
11
|
+
|
12
|
+
module SimplyVersioned
|
13
|
+
|
14
|
+
class BadOptions < StandardError
|
15
|
+
def initialize( keys )
|
16
|
+
super( "Keys: #{keys.join( "," )} are not known by SimplyVersioned" )
|
17
|
+
end
|
18
|
+
end
|
19
|
+
|
20
|
+
module ClassMethods
|
21
|
+
|
22
|
+
# Marks this ActiveRecord model as being versioned. Calls to +create+ or +save+ will,
|
23
|
+
# in future, create a series of associated Version instances that can be accessed via
|
24
|
+
# the +versions+ association.
|
25
|
+
#
|
26
|
+
# Options:
|
27
|
+
# +limit+ - specifies the number of old versions to keep (default = nil, never delete old versions)
|
28
|
+
# +automatic+ - controls whether versions are created automatically (default = true, save versions)
|
29
|
+
# +exclude+ - specify columns that will not be saved (default = [], save all columns)
|
30
|
+
#
|
31
|
+
# To save the record without creating a version either set +versioning_enabled+ to false
|
32
|
+
# on the model before calling save or, alternatively, use +without_versioning+ and save
|
33
|
+
# the model from its block.
|
34
|
+
#
|
35
|
+
|
36
|
+
def simply_versioned( options = {} )
|
37
|
+
bad_keys = options.keys - [:keep,:automatic,:exclude]
|
38
|
+
raise SimplyVersioned::BadOptions.new( bad_keys ) unless bad_keys.empty?
|
39
|
+
|
40
|
+
options.reverse_merge!( {
|
41
|
+
:keep => nil,
|
42
|
+
:automatic => true,
|
43
|
+
:exclude => [:updated_at, :position]
|
44
|
+
})
|
45
|
+
|
46
|
+
has_many :versions, :order => 'number DESC', :as => :versionable, :dependent => :destroy, :extend => VersionsProxyMethods
|
47
|
+
|
48
|
+
before_save :save_new_record_status
|
49
|
+
before_save :simply_versioned_keep_dirty_version
|
50
|
+
after_save :simply_versioned_create_versions
|
51
|
+
after_save :unset_new_record_status
|
52
|
+
|
53
|
+
cattr_accessor :simply_versioned_keep_limit
|
54
|
+
self.simply_versioned_keep_limit = options[:keep]
|
55
|
+
|
56
|
+
cattr_accessor :simply_versioned_save_by_default
|
57
|
+
self.simply_versioned_save_by_default = options[:automatic]
|
58
|
+
|
59
|
+
cattr_accessor :simply_versioned_excluded_columns
|
60
|
+
self.simply_versioned_excluded_columns = Array( options[ :exclude ] ).map( &:to_s )
|
61
|
+
|
62
|
+
class_eval do
|
63
|
+
def versioning_enabled=( enabled )
|
64
|
+
self.instance_variable_set( :@simply_versioned_enabled, enabled )
|
65
|
+
end
|
66
|
+
|
67
|
+
def versioning_enabled?
|
68
|
+
enabled = self.instance_variable_get( :@simply_versioned_enabled )
|
69
|
+
if enabled.nil?
|
70
|
+
enabled = self.instance_variable_set( :@simply_versioned_enabled, self.simply_versioned_save_by_default )
|
71
|
+
end
|
72
|
+
enabled
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
|
77
|
+
end
|
78
|
+
|
79
|
+
# Methods that will be defined on the ActiveRecord model being versioned
|
80
|
+
module InstanceMethods
|
81
|
+
|
82
|
+
# Revert the attributes of this model to their values as of an earlier version.
|
83
|
+
#
|
84
|
+
# Pass either a Version instance or a version number.
|
85
|
+
#
|
86
|
+
# options:
|
87
|
+
# +except+ specify a list of attributes that are not restored (default: created_at, updated_at)
|
88
|
+
#
|
89
|
+
def revert_to_version( version, options = {} )
|
90
|
+
options.reverse_merge!({
|
91
|
+
:except => [:created_at,:updated_at]
|
92
|
+
})
|
93
|
+
|
94
|
+
version = if version.kind_of?( Version )
|
95
|
+
version
|
96
|
+
elsif version.kind_of?( Fixnum )
|
97
|
+
self.versions.find_by_number( version )
|
98
|
+
end
|
99
|
+
|
100
|
+
raise "Invalid version (#{version.inspect}) specified!" unless version
|
101
|
+
|
102
|
+
options[:except] = options[:except].map( &:to_s )
|
103
|
+
|
104
|
+
self.update_attributes( YAML::load( version.yaml ).except( *options[:except] ) )
|
105
|
+
end
|
106
|
+
|
107
|
+
# Invoke the supplied block passing the receiver as the sole block argument with
|
108
|
+
# versioning enabled or disabled depending upon the value of the +enabled+ parameter
|
109
|
+
# for the duration of the block.
|
110
|
+
def with_versioning( enabled, &block )
|
111
|
+
versioning_was_enabled = self.versioning_enabled?
|
112
|
+
self.versioning_enabled = enabled
|
113
|
+
begin
|
114
|
+
block.call( self )
|
115
|
+
ensure
|
116
|
+
self.versioning_enabled = versioning_was_enabled
|
117
|
+
end
|
118
|
+
end
|
119
|
+
|
120
|
+
def unversioned?
|
121
|
+
self.versions.nil? || self.versions.size == 0
|
122
|
+
end
|
123
|
+
|
124
|
+
def versioned?
|
125
|
+
!unversioned?
|
126
|
+
end
|
127
|
+
|
128
|
+
def version_number
|
129
|
+
if self.versions.empty?
|
130
|
+
0
|
131
|
+
else
|
132
|
+
self.versions.current.number
|
133
|
+
end
|
134
|
+
end
|
135
|
+
|
136
|
+
protected
|
137
|
+
|
138
|
+
def save_new_record_status
|
139
|
+
@was_new_record = self.new_record?
|
140
|
+
true
|
141
|
+
end
|
142
|
+
|
143
|
+
def unset_new_record_status
|
144
|
+
@was_new_record = false
|
145
|
+
true
|
146
|
+
end
|
147
|
+
|
148
|
+
def simply_versioned_keep_dirty_version
|
149
|
+
changed_attr = self.changes.except(*simply_versioned_excluded_columns)
|
150
|
+
@dirty_attributes = if self.versioning_enabled? && !self.new_record? && !changed_attr.empty?
|
151
|
+
changed_attr.each {|k,v| changed_attr[k] = v.first }
|
152
|
+
else
|
153
|
+
{ }
|
154
|
+
end
|
155
|
+
true
|
156
|
+
end
|
157
|
+
|
158
|
+
def simply_versioned_create_versions
|
159
|
+
# new or unchanged records are not versioned while first time
|
160
|
+
# versioning will create two versions in the same time
|
161
|
+
unless @was_new_record
|
162
|
+
if self.versioning_enabled? && !@dirty_attributes.empty?
|
163
|
+
if self.unversioned?
|
164
|
+
self.versions.create( :yaml => self.attributes.except( *simply_versioned_excluded_columns).merge(@dirty_attributes).to_yaml )
|
165
|
+
end
|
166
|
+
|
167
|
+
if self.versions.create( :yaml => self.attributes.except( *simply_versioned_excluded_columns ).to_yaml )
|
168
|
+
self.versions.clean_old_versions( simply_versioned_keep_limit.to_i ) if simply_versioned_keep_limit
|
169
|
+
end
|
170
|
+
end
|
171
|
+
end
|
172
|
+
true
|
173
|
+
end
|
174
|
+
|
175
|
+
end
|
176
|
+
|
177
|
+
module VersionsProxyMethods
|
178
|
+
|
179
|
+
# Get the Version instance corresponding to this models for the specified version number.
|
180
|
+
def get_version( number )
|
181
|
+
find_by_number( number )
|
182
|
+
end
|
183
|
+
alias_method :get, :get_version
|
184
|
+
|
185
|
+
# Get the first Version corresponding to this model.
|
186
|
+
def first_version
|
187
|
+
find( :first, :order => 'number ASC' )
|
188
|
+
end
|
189
|
+
alias_method :first, :first_version
|
190
|
+
|
191
|
+
# Get the current Version corresponding to this model.
|
192
|
+
def current_version
|
193
|
+
find( :first, :order => 'number DESC' )
|
194
|
+
end
|
195
|
+
alias_method :current, :current_version
|
196
|
+
|
197
|
+
# If the model instance has more versions than the limit specified, delete all excess older versions.
|
198
|
+
def clean_old_versions( versions_to_keep )
|
199
|
+
find( :all, :conditions => [ 'number <= ?', self.maximum( :number ) - versions_to_keep ] ).each do |version|
|
200
|
+
version.destroy
|
201
|
+
end
|
202
|
+
end
|
203
|
+
alias_method :purge, :clean_old_versions
|
204
|
+
|
205
|
+
# Return the Version for this model with the next higher version
|
206
|
+
def next_version( number )
|
207
|
+
find( :first, :order => 'number ASC', :conditions => [ "number > ?", number ] )
|
208
|
+
end
|
209
|
+
alias_method :next, :next_version
|
210
|
+
|
211
|
+
# Return the Version for this model with the next lower version
|
212
|
+
def previous_version( number )
|
213
|
+
find( :first, :order => 'number DESC', :conditions => [ "number < ?", number ] )
|
214
|
+
end
|
215
|
+
alias_method :previous, :previous_version
|
216
|
+
end
|
217
|
+
|
218
|
+
def self.included( receiver )
|
219
|
+
receiver.extend ClassMethods
|
220
|
+
receiver.send :include, InstanceMethods
|
221
|
+
end
|
222
|
+
|
223
|
+
end
|
224
|
+
|
225
|
+
end
|
226
|
+
|
227
|
+
end
|
228
|
+
|
229
|
+
ActiveRecord::Base.send( :include, SoftwareHeretics::ActiveRecord::SimplyVersioned )
|