-
Notifications
You must be signed in to change notification settings - Fork 0
plugin which adds version control system to models AND associations, and also allows to pack many changes into one changelist
License
kkurach/has_versioning
Folders and files
Name | Name | Last commit message | Last commit date | |
---|---|---|---|---|
Repository files navigation
# Copyright 2009 Google Inc. # Original author: Karol Kurach <kkurach (at) gmail (dot) com> # # Licensed under the Apache License, Version 2.0 (the "License"); # you may not use this file except in compliance with the License. # You may obtain a copy of the License at # # http://www.apache.org/licenses/LICENSE-2.0 # # Unless required by applicable law or agreed to in writing, software # distributed under the License is distributed on an "AS IS" BASIS, # WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. # See the License for the specific language governing permissions and # limitations under the License. HasVersioning ============= This plugin adds version control to your's app models. It allows to: - keep track of all changes to selected models - collect many changes in a one changelist - keep track of object associations Install ======= 1.copy this plugin to yourapp/vendor/plugins. 2.add new migration, with those 2 lines: Changelist.create_versioning_table Change.create_versioning_table 3.for each model, which you want to version, add 'has_versioning' to class definition, and and call to 'add_versioning_columns' in migration. so, if you have: class User end you need to change it to class User has_versioning end and add "User.add_versioning_columns" into your migrations. 4. add argument :versioned => true, for each association you want to version. both sides of association MUST have versioning. Requirements ============ requires RAILS >= 2.3.3 to install rails 2.3.3, you may run following command in your app directory: rake rails:freeze:edge RELEASE=2.3.3 Example ======= let say we have following objects in our app: --- class User has_many :cars has_many :dogs end class Car has_one :engine belong_to :user end class Engine belongs_to :car end --- To make those models use versioning, we need to add 'has_versioning' in class definition. this will allow to query about attributes of this object in the past. if we also need to remember history of has_many :cars assocition, we need to pass :versioned => true argument --- class User has_versioning has_many :cars, :versioned => true has_many :dogs end class Car belong_to :user, :versioned => true has_one :engine, :versioned => true end class Engine has_versioning belong_to :car, :versioned => true end --- now, following magic works: user = User.new new_cl = Changelist.record!('added new user') do user.name = 'kkurach' user.save! end user.version # => 1 user.name = 'nickesk' user.save! # changelist autocreated user.version # => 2 user.at_changelist(new_cl.id).name # => 'kkurach' user.at_version(1).name # => 'kkurach' c1 = Car.create(:color => 'red') c2 = Car.create(:color => 'blue') cl_add1 = Changelist.record! { user.cars << c1 } cl_add2 = Changelist.record! { user.cars << c2 } user.cars # => [c1, c2] user.cars.count # => 2 user.at_changelist(cl_add1.id).cars # => [c1] user.at_changelist(cl_add1.id).cars.count # => 1 user.at_changelist(cl_add2.id).cars.find(:all, :conditions => { :color => 'blue} ) # => [c2] cl_engine = Changelist.record!('engine added') do c1.engine = Engine.create(:power => 123) end c1.engine.power = 444 user.cars.first.engine.power # => 444 user.at_changelist(cl_engine.id+1).cars. first.engine.power # => 444 user.at_changelist(cl_engine.id+1).cars. first.at_changelist(cl_engine.id).engine.power # => 123 ################ END OF EXAMPLE ########################## Limitations ======= 1. plugin wasn't tested with non-standard naming ( different than rails default table names, foreign keys, etc...) so most probably it won't work in this case. 2. it doesn't work with has_many :through and has_one :through (yet ) 3. queries which includes id field in conditions are forbidden after at_changelist(cl). so, for example this query will give wrong output: User.find_by_name('karol').at_changelist(5).cars.find(:all, :conditions => { :id => 4..10 } ) but this is ok: User.find_by_name('karol').at_changelist(5).cars.find(:all, :conditions => { :color => 'red' }) only conditions with primary key after at_changelist are BAD 4. it will never work with has_and_belongs_to_many (or it will be hard and dirty), because it's impossible to set a callback on table in database. we need a model... Special thanks to: ======= Nick Eskelinen - for an idea of writing this plugin, help with starting it, solving tons of my problems & much more Joel Votaw - for being my mentor while Nick was away, and several REALLY great design advises, without which I wouldn't be able to finish writing the plugin. Shane Liebling & Daniel Van Derveer - for everyday's help in Ruby/Rails/Git problems ;) also, [Nick,Joel,Dan,Shane].each { |x| Karol.thanks_for_code_reviews_and_your_patience_when_I_was_asking_stupid_questions(x) }
About
plugin which adds version control system to models AND associations, and also allows to pack many changes into one changelist
Resources
License
Stars
Watchers
Forks
Releases
No releases published
Packages 0
No packages published