wikify 0.0.1.pre
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.gitignore +19 -0
- data/.travis.yml +13 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.md +91 -0
- data/Rakefile +1 -0
- data/lib/generators/wikify/migration/USAGE +5 -0
- data/lib/generators/wikify/migration/migration_generator.rb +11 -0
- data/lib/wikify.rb +58 -0
- data/lib/wikify/child_methods.rb +38 -0
- data/lib/wikify/controller.rb +23 -0
- data/lib/wikify/methods.rb +39 -0
- data/lib/wikify/model.rb +74 -0
- data/lib/wikify/version.rb +6 -0
- data/lib/wikify/version_concern.rb +62 -0
- data/lib/wikify/version_number.rb +4 -0
- data/spec/children_spec.rb +69 -0
- data/spec/comitter_spec.rb +27 -0
- data/spec/config_spec.rb +25 -0
- data/spec/create_spec.rb +11 -0
- data/spec/destroy_spec.rb +17 -0
- data/spec/included_spec.rb +22 -0
- data/spec/logical_function_spec.rb +77 -0
- data/spec/models/child.rb +5 -0
- data/spec/models/document.rb +5 -0
- data/spec/models/parent.rb +5 -0
- data/spec/models/revision.rb +3 -0
- data/spec/restore_spec.rb +39 -0
- data/spec/spec_helper.rb +27 -0
- data/spec/support/controller.rb +45 -0
- data/spec/support/database.rb +73 -0
- data/spec/update_spec.rb +28 -0
- data/spec/version_spec.rb +37 -0
- data/wikify.gemspec +29 -0
- metadata +194 -0
checksums.yaml
ADDED
@@ -0,0 +1,7 @@
|
|
1
|
+
---
|
2
|
+
SHA1:
|
3
|
+
metadata.gz: bfb7da00d14ef7a813e3fbc64869133635a7958c
|
4
|
+
data.tar.gz: f34e12fbf529cf68005815784fb03299fd6b7aad
|
5
|
+
SHA512:
|
6
|
+
metadata.gz: 1f3096e30c0f7f77e27b2217b59dad0d96942663967250e8d62a598435de1e9c6c51a478c997c093af8b43a63282b4f61c29c7409c6a4253ba1da6dc779becae
|
7
|
+
data.tar.gz: 0462d4122d9179c6648c161211a75109082dc8f86ca1f142ee3fa7f1cc82e99f3770e16ab73d7942139b2d6aaa99c95a4a9424aac98e083f9b6e4e9a348bf50d
|
data/.gitignore
ADDED
data/.travis.yml
ADDED
data/Gemfile
ADDED
data/LICENSE.txt
ADDED
@@ -0,0 +1,22 @@
|
|
1
|
+
Copyright (c) 2013 Adam Laycock
|
2
|
+
|
3
|
+
MIT License
|
4
|
+
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining
|
6
|
+
a copy of this software and associated documentation files (the
|
7
|
+
"Software"), to deal in the Software without restriction, including
|
8
|
+
without limitation the rights to use, copy, modify, merge, publish,
|
9
|
+
distribute, sublicense, and/or sell copies of the Software, and to
|
10
|
+
permit persons to whom the Software is furnished to do so, subject to
|
11
|
+
the following conditions:
|
12
|
+
|
13
|
+
The above copyright notice and this permission notice shall be
|
14
|
+
included in all copies or substantial portions of the Software.
|
15
|
+
|
16
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
|
17
|
+
EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
|
18
|
+
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
|
19
|
+
NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
|
20
|
+
LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
|
21
|
+
OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
|
22
|
+
WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
data/README.md
ADDED
@@ -0,0 +1,91 @@
|
|
1
|
+
# Wikify
|
2
|
+
|
3
|
+
Active Record model versioning.
|
4
|
+
|
5
|
+
[](https://travis-ci.org/Arcath/Wikify) | [](https://codeclimate.com/github/Arcath/Wikify) | [](https://coveralls.io/r/Arcath/Wikify) | [RDoc](http://rubydoc.info/github/Arcath/Wikify/master/frames)
|
6
|
+
|
7
|
+
## Installation
|
8
|
+
|
9
|
+
### Adding the Gem
|
10
|
+
|
11
|
+
Add this line to your application's Gemfile:
|
12
|
+
|
13
|
+
gem 'wikify'
|
14
|
+
|
15
|
+
And then execute:
|
16
|
+
|
17
|
+
$ bundle
|
18
|
+
|
19
|
+
Or install it yourself as:
|
20
|
+
|
21
|
+
$ gem install wikify
|
22
|
+
|
23
|
+
### Migration
|
24
|
+
|
25
|
+
Wikify has a built in generator for creating the migration which can be run using:
|
26
|
+
|
27
|
+
$ rails g wikify:migration
|
28
|
+
$ rake db:migrate
|
29
|
+
|
30
|
+
You will now have a table for your versions, wikify contains a model for the versions which is used by default.
|
31
|
+
|
32
|
+
## Usage
|
33
|
+
|
34
|
+
To enable wikify on your models add `wikify` to your model class:
|
35
|
+
|
36
|
+
``` ruby
|
37
|
+
class Article < ActiveRecord::Base
|
38
|
+
wikify
|
39
|
+
end
|
40
|
+
```
|
41
|
+
|
42
|
+
Your model now has version tracking!
|
43
|
+
|
44
|
+
For an example of how Wikify works see the [Logical Function Spec](https://github.com/Arcath/Wikify/blob/master/spec/logical_function_spec.rb) which is a commented example of all the functionality (that gets tested with every push).
|
45
|
+
|
46
|
+
## Restoring a Version
|
47
|
+
|
48
|
+
Versions have a handy `restore` method that lets you very quickly and easily restore a version over the current/target model. A version stores the model & id when it gets created when you call `restore` Wikify finds the model with the stored id and then overwrites all its attributes with the ones in the versions cache.
|
49
|
+
|
50
|
+
### Restoring a deleted version
|
51
|
+
|
52
|
+
You can restore a deleted versions by using the `Wikify.destroyed_versions` method. You must supply a model and optionally an id e.g.
|
53
|
+
|
54
|
+
``` ruby
|
55
|
+
Wikify.destroyed_versions(Article)
|
56
|
+
#> An list of versions where event is "destroy" and model is "Article"
|
57
|
+
Wikify.destroyed_versions(Article, 2)
|
58
|
+
#> The destory events for the given article only
|
59
|
+
```
|
60
|
+
|
61
|
+
### Associations
|
62
|
+
|
63
|
+
#### Has-Many
|
64
|
+
|
65
|
+
Wikify can track the versions of child objects, for example a comments model attached to that articles model:
|
66
|
+
|
67
|
+
``` ruby
|
68
|
+
class Article < ActiveRecord::Base
|
69
|
+
has_many :comments
|
70
|
+
|
71
|
+
wikify
|
72
|
+
end
|
73
|
+
|
74
|
+
class Comment < ActiveRecord::Base
|
75
|
+
belongs_to :article
|
76
|
+
|
77
|
+
wikify_on_parent(:article)
|
78
|
+
end
|
79
|
+
```
|
80
|
+
|
81
|
+
This then stores versions on the parent model so that they can be tracked with it. The child model also has a `versions` method that works the same but it looks for its versions through the parent.
|
82
|
+
|
83
|
+
Again see the [Logical Function Spec](https://github.com/Arcath/Wikify/blob/master/spec/logical_function_spec.rb) for examples of this code in action.
|
84
|
+
|
85
|
+
## Contributing
|
86
|
+
|
87
|
+
1. Fork it
|
88
|
+
2. Create your feature branch (`git checkout -b my-new-feature`)
|
89
|
+
3. Commit your changes (`git commit -am 'Add some feature'`)
|
90
|
+
4. Push to the branch (`git push origin my-new-feature`)
|
91
|
+
5. Create new Pull Request
|
data/Rakefile
ADDED
@@ -0,0 +1 @@
|
|
1
|
+
require "bundler/gem_tasks"
|
@@ -0,0 +1,11 @@
|
|
1
|
+
module Wikify
|
2
|
+
module Generators
|
3
|
+
class MigrationGenerator < Rails::Generators::Base
|
4
|
+
argument :model_name, :type => :string, :default => "versions"
|
5
|
+
|
6
|
+
def generate_migration
|
7
|
+
generate "migration", "create_wikify_#{model_name}", "resource_id:integer", "resource_type", "data:text", "event", "linked_child_resource_type", "linked_child_resource_id:integer", "linked_child:boolean", "comitter_id:integer", "created_at:datetime", "updated_at:datetime"
|
8
|
+
end
|
9
|
+
end
|
10
|
+
end
|
11
|
+
end
|
data/lib/wikify.rb
ADDED
@@ -0,0 +1,58 @@
|
|
1
|
+
# Version Number
|
2
|
+
require "wikify/version_number"
|
3
|
+
|
4
|
+
# System
|
5
|
+
require 'ostruct' #Required for ruby 1.9.3
|
6
|
+
|
7
|
+
# Gems
|
8
|
+
require 'active_record'
|
9
|
+
require 'active_support'
|
10
|
+
|
11
|
+
# Internal Requires
|
12
|
+
require "wikify/child_methods"
|
13
|
+
require "wikify/controller"
|
14
|
+
require "wikify/methods"
|
15
|
+
require "wikify/model"
|
16
|
+
require "wikify/version_concern"
|
17
|
+
require "wikify/version"
|
18
|
+
|
19
|
+
# Wikify
|
20
|
+
#
|
21
|
+
# Model Versioning for ActiveRecord
|
22
|
+
module Wikify
|
23
|
+
# Searches the version table for destroy events, takes an optional id when you know exactly what you are looking for.
|
24
|
+
#
|
25
|
+
# Wikify.destroyed_versions(Model, 10)
|
26
|
+
def self.destroyed_versions(model, id = nil)
|
27
|
+
hash = {"#{model.wikify_options[:assoc_as]}_type".to_sym => model.to_s, event: "destroy"}
|
28
|
+
hash["#{model.wikify_options[:assoc_as]}_id".to_sym] = id if id
|
29
|
+
model.wikify_options[:assoc_model].constantize.where(hash)
|
30
|
+
end
|
31
|
+
|
32
|
+
# Stores the current users id within the current thread (lets us get it from the controller)
|
33
|
+
def self.set_user_id(id)
|
34
|
+
thread_store.user_id = id
|
35
|
+
end
|
36
|
+
|
37
|
+
# Returns the stored id
|
38
|
+
def self.user_id
|
39
|
+
thread_store.user_id
|
40
|
+
end
|
41
|
+
|
42
|
+
private
|
43
|
+
|
44
|
+
def self.thread_store
|
45
|
+
Thread.current[:wikify_store] ||= OpenStruct.new({user_id: nil})
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
|
50
|
+
ActiveSupport.on_load(:active_record) do
|
51
|
+
include Wikify::Model
|
52
|
+
end
|
53
|
+
|
54
|
+
if defined?(ActionController)
|
55
|
+
ActiveSupport.on_load(:action_controller) do
|
56
|
+
include Wikify::Controller
|
57
|
+
end
|
58
|
+
end
|
@@ -0,0 +1,38 @@
|
|
1
|
+
module Wikify
|
2
|
+
# Methods included by child models
|
3
|
+
module ChildMethods
|
4
|
+
# Records an update operation against the parent
|
5
|
+
def wikify_update
|
6
|
+
new_version = new_version_instance
|
7
|
+
new_version.data = @wikify_cached_object
|
8
|
+
new_version.event = "child" + (@wikify_override[:event] || "update")
|
9
|
+
new_version.save
|
10
|
+
end
|
11
|
+
|
12
|
+
# Records a create operation against the parent
|
13
|
+
def wikify_create
|
14
|
+
new_version = new_version_instance
|
15
|
+
new_version.event = "child create"
|
16
|
+
new_version.save
|
17
|
+
@wikify_cached_object = self.attributes
|
18
|
+
end
|
19
|
+
|
20
|
+
# Records a destroy operation against the parent
|
21
|
+
def wikify_destroy
|
22
|
+
new_version = new_version_instance
|
23
|
+
new_version.data = @wikify_cached_object
|
24
|
+
new_version.event = "child destroy"
|
25
|
+
new_version.save
|
26
|
+
end
|
27
|
+
|
28
|
+
private
|
29
|
+
|
30
|
+
def new_version_instance
|
31
|
+
self.send(wikify_parent).send(wikify_options[:assoc_name]).new({linked_child: true, linked_child_resource_type: self.class.to_s, linked_child_resource_id: self.id})
|
32
|
+
end
|
33
|
+
|
34
|
+
def wikify_search_hash
|
35
|
+
{"linked_child_#{wikify_options[:assoc_as]}_id".to_sym => self.id, "linked_child_#{wikify_options[:assoc_as]}_type".to_sym => self.class.to_s, "linked_child" => true}
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module Wikify
|
2
|
+
|
3
|
+
# Used to extend ActionController with the required methods
|
4
|
+
module Controller
|
5
|
+
|
6
|
+
# Adds the before filter trigger to ActionController (aka your ApplicationController)
|
7
|
+
def self.included(base)
|
8
|
+
if defined?(ActionController) && (base == ActionController::Base || base == ActionController::API)
|
9
|
+
base.before_filter :set_wikify_user
|
10
|
+
end
|
11
|
+
end
|
12
|
+
|
13
|
+
# Default method for finding the current user
|
14
|
+
def current_user_wikify
|
15
|
+
current_user if defined?(current_user)
|
16
|
+
end
|
17
|
+
|
18
|
+
# The before filter method that stores the user id in Wikify
|
19
|
+
def set_wikify_user
|
20
|
+
Wikify.set_user_id(current_user_wikify.id) if current_user_wikify != nil
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
module Wikify
|
2
|
+
# Methods that get included on models using wikify
|
3
|
+
module Methods
|
4
|
+
# The Wikify update operation
|
5
|
+
#
|
6
|
+
# Creates a new version, records the cached object and saves it as an update
|
7
|
+
def wikify_update
|
8
|
+
new_version = self.send(wikify_options[:assoc_name]).new
|
9
|
+
new_version.data = @wikify_cached_object
|
10
|
+
new_version.event = (@wikify_override[:event] || "update")
|
11
|
+
new_version.save
|
12
|
+
end
|
13
|
+
|
14
|
+
# The Wikify create operation
|
15
|
+
#
|
16
|
+
# Creates a new version with no data and sets the event to create
|
17
|
+
def wikify_create
|
18
|
+
new_version = self.send(wikify_options[:assoc_name]).new
|
19
|
+
new_version.event = "create"
|
20
|
+
new_version.save
|
21
|
+
@wikify_cached_object = self.attributes
|
22
|
+
end
|
23
|
+
|
24
|
+
# The Wikify destroy operation
|
25
|
+
#
|
26
|
+
# Creates a new version recods the cached object and saves it as a destroy
|
27
|
+
def wikify_destroy
|
28
|
+
new_version = self.send(wikify_options[:assoc_name]).new
|
29
|
+
new_version.data = @wikify_cached_object
|
30
|
+
new_version.event = "destroy"
|
31
|
+
new_version.save
|
32
|
+
end
|
33
|
+
|
34
|
+
# The hash used to find versions
|
35
|
+
def wikify_search_hash
|
36
|
+
{"#{wikify_options[:assoc_as]}_id".to_sym => self.id, "#{wikify_options[:assoc_as]}_type".to_sym => self.class.to_s}
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
data/lib/wikify/model.rb
ADDED
@@ -0,0 +1,74 @@
|
|
1
|
+
module Wikify
|
2
|
+
module Model
|
3
|
+
def self.included(base)
|
4
|
+
base.extend ClassMethods
|
5
|
+
end
|
6
|
+
|
7
|
+
# Caches the model
|
8
|
+
#
|
9
|
+
# Called using the `after_find` callback in ActiveRecord
|
10
|
+
def wikify_cache
|
11
|
+
@wikify_override = {}
|
12
|
+
@wikify_cached_object = self.attributes
|
13
|
+
end
|
14
|
+
|
15
|
+
# Allows you override the wikify options for this event
|
16
|
+
def wikify_override(options)
|
17
|
+
@wikify_override = options
|
18
|
+
end
|
19
|
+
|
20
|
+
def version_at(time)
|
21
|
+
self.versions.where("created_at < ?", time).limit(1).first.next
|
22
|
+
end
|
23
|
+
|
24
|
+
module ClassMethods
|
25
|
+
# Enables the wikify functionality on the model
|
26
|
+
#
|
27
|
+
# Takes a hash of options:
|
28
|
+
#
|
29
|
+
# :assoc_name => :versions
|
30
|
+
# :assoc_as => :resource
|
31
|
+
# :assoc_model => "Wikify::Version"
|
32
|
+
#
|
33
|
+
def wikify(options = {})
|
34
|
+
# Create a class_attribute to store the wikify options hash in
|
35
|
+
class_attribute :wikify_options
|
36
|
+
|
37
|
+
# Set some Defaults
|
38
|
+
options[:assoc_name] ||= :versions
|
39
|
+
options[:assoc_as] ||= :resource
|
40
|
+
options[:assoc_model] ||= "Wikify::Version"
|
41
|
+
options[:no_include] ||= false
|
42
|
+
|
43
|
+
# Store the Options Hash
|
44
|
+
self.wikify_options = options.dup
|
45
|
+
|
46
|
+
# Register the Callbacks
|
47
|
+
after_find :wikify_cache
|
48
|
+
after_create :wikify_create
|
49
|
+
after_update :wikify_update
|
50
|
+
after_destroy :wikify_destroy
|
51
|
+
|
52
|
+
# Allow reading of the cached object
|
53
|
+
attr_reader :wikify_cached_object
|
54
|
+
|
55
|
+
# Define a method to access the versions
|
56
|
+
define_method(wikify_options[:assoc_name]){
|
57
|
+
wikify_options[:assoc_model].constantize.where(wikify_search_hash)
|
58
|
+
}
|
59
|
+
|
60
|
+
include Wikify::Methods unless options[:no_include]
|
61
|
+
end
|
62
|
+
|
63
|
+
# Takes the same options as wikify
|
64
|
+
def wikify_on_parent(parent, options = {})
|
65
|
+
wikify(options.merge({no_include: true}))
|
66
|
+
|
67
|
+
class_attribute :wikify_parent
|
68
|
+
self.wikify_parent = parent
|
69
|
+
|
70
|
+
include Wikify::ChildMethods
|
71
|
+
end
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
module Wikify
|
2
|
+
module VersionConcern
|
3
|
+
extend ActiveSupport::Concern
|
4
|
+
|
5
|
+
included do
|
6
|
+
serialize :data, Hash
|
7
|
+
|
8
|
+
before_save :record_comitter
|
9
|
+
end
|
10
|
+
|
11
|
+
def object
|
12
|
+
OpenStruct.new(data)
|
13
|
+
end
|
14
|
+
|
15
|
+
def previous
|
16
|
+
self.class.where("created_at < ?", self.created_at).limit(1).first
|
17
|
+
end
|
18
|
+
|
19
|
+
def next
|
20
|
+
results = self.class.where("created_at > ?", self.created_at).limit(1)
|
21
|
+
return results.first if results != []
|
22
|
+
return self.restore_to
|
23
|
+
end
|
24
|
+
|
25
|
+
# Finds the model/instance to restore to and then over writes all its data.
|
26
|
+
#
|
27
|
+
# Also over rides the version event to restore so you can tell the difference between a restore and an update in your history.
|
28
|
+
def restore
|
29
|
+
unless event == "destroy"
|
30
|
+
target = restore_to
|
31
|
+
target.attributes = self.data
|
32
|
+
target.wikify_override({event: "restore"})
|
33
|
+
target.save
|
34
|
+
else
|
35
|
+
target = resource_type.constantize.new
|
36
|
+
target.attributes = self.data
|
37
|
+
target.wikify_override({event: "restore"})
|
38
|
+
target.save
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
# Finds the model to restore type
|
43
|
+
def restore_to
|
44
|
+
restore_type.constantize.find(restore_id)
|
45
|
+
end
|
46
|
+
|
47
|
+
def restore_type
|
48
|
+
return self.send(self.attributes.keys.select {|i| i =~ /_type/ }.first.to_sym) unless self.linked_child == true
|
49
|
+
return self.send(self.attributes.keys.select {|i| i =~ /linked_child_.*?_type/ }.first.to_sym)
|
50
|
+
end
|
51
|
+
|
52
|
+
def restore_id
|
53
|
+
return self.send(self.attributes.keys.select {|i| i =~ /_id/ }.first.to_sym) unless self.linked_child == true
|
54
|
+
return self.send(self.attributes.keys.select {|i| i =~ /linked_child_.*?_id/ }.first.to_sym)
|
55
|
+
end
|
56
|
+
|
57
|
+
# Gets the comitter from the Wikify thread store
|
58
|
+
def record_comitter
|
59
|
+
self.comitter_id = Wikify.user_id if Wikify.user_id != nil
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
@@ -0,0 +1,69 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Child do
|
4
|
+
it "should have the wikify methods" do
|
5
|
+
Child._create_callbacks.length.should eq 1
|
6
|
+
Child._update_callbacks.length.should eq 1
|
7
|
+
Child._destroy_callbacks.length.should eq 1
|
8
|
+
end
|
9
|
+
|
10
|
+
it "should have the callback methods" do
|
11
|
+
child = Parent.last.children.new
|
12
|
+
child.methods.include?(:wikify_cache).should be_true
|
13
|
+
child.methods.include?(:wikify_update).should be_true
|
14
|
+
child.methods.include?(:wikify_create).should be_true
|
15
|
+
child.methods.include?(:wikify_destroy).should be_true
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should write its updates to the parent" do
|
19
|
+
parent = Parent.new({name: "Parent 100"})
|
20
|
+
parent.save
|
21
|
+
|
22
|
+
parent.versions.count.should eq 1
|
23
|
+
|
24
|
+
child = parent.children.new({name: "Child 1"})
|
25
|
+
child.save
|
26
|
+
|
27
|
+
parent.versions.count.should eq 2
|
28
|
+
parent.versions.last.event.should eq "child create"
|
29
|
+
end
|
30
|
+
|
31
|
+
it "should record updates to the parent" do
|
32
|
+
child = Child.find_by_name("Child 1")
|
33
|
+
|
34
|
+
child.parent.versions.count.should eq 2
|
35
|
+
|
36
|
+
child.name = "Child 1 Updated"
|
37
|
+
child.save
|
38
|
+
|
39
|
+
child.parent.versions.count.should eq 3
|
40
|
+
end
|
41
|
+
|
42
|
+
it "Should set the restore to values" do
|
43
|
+
child = Child.find_by_name("Child 1 Updated")
|
44
|
+
|
45
|
+
child.versions.last.restore_type.should eq "Child"
|
46
|
+
child.versions.last.restore_id.should eq child.id
|
47
|
+
end
|
48
|
+
|
49
|
+
it "should restore a version do" do
|
50
|
+
child = Child.find_by_name("Child 1 Updated")
|
51
|
+
child.versions.last.restore
|
52
|
+
|
53
|
+
child = Child.find(child.id)
|
54
|
+
|
55
|
+
child.name.should eq "Child 1"
|
56
|
+
end
|
57
|
+
|
58
|
+
it "should create an event on destroy" do
|
59
|
+
child = Child.find_by_name("Child 1")
|
60
|
+
parent = child.parent
|
61
|
+
|
62
|
+
c = parent.versions.count
|
63
|
+
|
64
|
+
child.destroy
|
65
|
+
|
66
|
+
parent.versions.count.should eq c + 1
|
67
|
+
parent.versions.last.event.should eq "child destroy"
|
68
|
+
end
|
69
|
+
end
|
@@ -0,0 +1,27 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "User id storing" do
|
4
|
+
it "should only be for that thread" do
|
5
|
+
Wikify.user_id.should be_nil
|
6
|
+
Thread.new do
|
7
|
+
Wikify.set_user_id = 1
|
8
|
+
Wikify.user_id.should eq 1
|
9
|
+
end
|
10
|
+
Wikify.user_id.should be_nil
|
11
|
+
end
|
12
|
+
|
13
|
+
it "should get set by the controller" do
|
14
|
+
parent = Parent.new({name: "Committer 1"})
|
15
|
+
parent.save
|
16
|
+
parent
|
17
|
+
controller = Controller.new
|
18
|
+
controller.request # See this method for what it does
|
19
|
+
parent = Parent.find_by_name("Committer 1 Updated")
|
20
|
+
parent.versions.count.should eq 2
|
21
|
+
parent.versions.last.comitter_id.should eq 1
|
22
|
+
end
|
23
|
+
|
24
|
+
it "should handle the current_user return being nil" do
|
25
|
+
lambda { controller = NilController.new }.should_not raise_exception
|
26
|
+
end
|
27
|
+
end
|
data/spec/config_spec.rb
ADDED
@@ -0,0 +1,25 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "With custom config" do
|
4
|
+
it "should set the assosiation name" do
|
5
|
+
doc = Document.new
|
6
|
+
doc.revisions.count.should eq 0
|
7
|
+
end
|
8
|
+
|
9
|
+
it "should record a version for create/update" do
|
10
|
+
Document.create!({title: "Foo"})
|
11
|
+
doc = Document.find_by_title("Foo")
|
12
|
+
doc.title = "Bar"
|
13
|
+
doc.save
|
14
|
+
|
15
|
+
doc.revisions.count.should eq 2
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should let you restore a version" do
|
19
|
+
doc = Document.find_by_title("Bar")
|
20
|
+
doc.revisions.last.restore
|
21
|
+
|
22
|
+
doc = Document.find_by_title("Foo")
|
23
|
+
doc.title.should eq "Foo"
|
24
|
+
end
|
25
|
+
end
|
data/spec/create_spec.rb
ADDED
@@ -0,0 +1,17 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "Model Destroy" do
|
4
|
+
it "should record a destroy" do
|
5
|
+
Wikify.destroyed_versions(Parent).count.should eq 0
|
6
|
+
|
7
|
+
parent = Parent.new({name: "First Destory Test"})
|
8
|
+
parent.save
|
9
|
+
|
10
|
+
parent.destroy
|
11
|
+
|
12
|
+
Wikify.destroyed_versions(Parent).count.should eq 1
|
13
|
+
|
14
|
+
old_version = Wikify.destroyed_versions(Parent).last
|
15
|
+
old_version.data.should eq parent.attributes
|
16
|
+
end
|
17
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Parent do
|
4
|
+
it "Should have the wikify method" do
|
5
|
+
Parent._create_callbacks.length.should eq 2
|
6
|
+
Parent._update_callbacks.length.should eq 2
|
7
|
+
Parent._destroy_callbacks.length.should eq 1
|
8
|
+
end
|
9
|
+
|
10
|
+
it "should have the callback methods" do
|
11
|
+
parent = Parent.new
|
12
|
+
parent.methods.include?(:wikify_cache).should be_true
|
13
|
+
parent.methods.include?(:wikify_update).should be_true
|
14
|
+
parent.methods.include?(:wikify_create).should be_true
|
15
|
+
parent.methods.include?(:wikify_destroy).should be_true
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should have the relationship with versions" do
|
19
|
+
parent = Parent.new
|
20
|
+
parent.versions.count.should eq 0
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,77 @@
|
|
1
|
+
# This is a worked example that appears in the readme except with shoulds to make sure that it works as planned
|
2
|
+
require 'spec_helper'
|
3
|
+
|
4
|
+
describe "Working logically" do
|
5
|
+
it "should behave like we expect" do
|
6
|
+
# First lets create a new object
|
7
|
+
parent = Parent.new
|
8
|
+
parent.name = "david" # Lets set the name
|
9
|
+
parent.save # And save that record
|
10
|
+
|
11
|
+
parent_id = parent.id # We will need this later
|
12
|
+
|
13
|
+
parent.versions.count.should eq 1 # We should now have 1 version
|
14
|
+
parent.versions.first.event.should eq "create" # that was created when we created the record
|
15
|
+
parent.versions.first.data.should eq Hash.new # and has an empty hash for its data
|
16
|
+
|
17
|
+
# Its a new day and we want to change "david" to "David"
|
18
|
+
david = Parent.find(parent_id)
|
19
|
+
david.name = "David"
|
20
|
+
david.save
|
21
|
+
|
22
|
+
david.versions.count.should eq 2 # We should now have a new version
|
23
|
+
david.versions.last.event.should eq "update" # that was an update
|
24
|
+
david.versions.last.data["name"].should eq "david" # and has the old name in the data hash
|
25
|
+
|
26
|
+
# Its another day and we make another change
|
27
|
+
david = Parent.find(parent_id)
|
28
|
+
david.name = "Dav1d"
|
29
|
+
david.save
|
30
|
+
|
31
|
+
david.versions.count.should eq 3 # We should now have a new version
|
32
|
+
david.versions.last.event.should eq "update" # that was an update
|
33
|
+
david.versions.last.data["name"].should eq "David" # and has the old name in the data hash
|
34
|
+
|
35
|
+
# Its another day and we want to restore the version with David
|
36
|
+
david = Parent.find(parent_id)
|
37
|
+
david.versions.last.restore # Restore the last version
|
38
|
+
|
39
|
+
david = Parent.find(parent_id)
|
40
|
+
david.versions.count.should eq 4 # We should now have a new version
|
41
|
+
david.versions.last.event.should eq "restore" # that was an update
|
42
|
+
david.versions.last.data["name"].should eq "Dav1d" # and has the old name in the data hash
|
43
|
+
david.name.should eq "David" # The name should have been restored
|
44
|
+
|
45
|
+
# David has died so its time to delete his record
|
46
|
+
david = Parent.find(parent_id)
|
47
|
+
david.destroy
|
48
|
+
|
49
|
+
# Whoops he wasn't dead just resting his heart time to restore his record
|
50
|
+
david_version = Wikify.destroyed_versions(Parent, parent_id).last
|
51
|
+
david_version.event.should eq "destroy" # The last thing to happen to david should be destroy
|
52
|
+
david_version.restore
|
53
|
+
|
54
|
+
david = Parent.find(parent_id)
|
55
|
+
david.name.should eq "David" # And now hes back! and at the same ID as before!
|
56
|
+
|
57
|
+
# David has now had a child (Like Arnie did in Junior)
|
58
|
+
david = Parent.find(parent_id)
|
59
|
+
|
60
|
+
david.versions.count.should eq 6 # David should have 6 versions at this point
|
61
|
+
|
62
|
+
jeff = david.children.new({name: "Jeff"})
|
63
|
+
jeff.save
|
64
|
+
|
65
|
+
david.versions.count.should eq 7 # Now that Jeff has been saved David should have 7 versions
|
66
|
+
|
67
|
+
# Turns out Jeff is a girl, name change needed
|
68
|
+
jeff = Child.find_by_name("Jeff")
|
69
|
+
jeff.name = "Jasmine"
|
70
|
+
jeff.save
|
71
|
+
|
72
|
+
jeff.parent.versions.count.should eq 8 # That change should be recorded in the parent
|
73
|
+
|
74
|
+
jeff.versions.count.should eq 2 # Children's versions search the parent for versions related to them.
|
75
|
+
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,39 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "Restoring a Model" do
|
4
|
+
it "should have a model to restore to" do
|
5
|
+
parent = Parent.new({name: "First Restore Test"})
|
6
|
+
parent.save
|
7
|
+
|
8
|
+
parent.versions.last.restore_to.should eq parent
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should restore a model" do
|
12
|
+
parent = Parent.find_by_name("First Restore Test")
|
13
|
+
parent.name = "Updated Restore Test"
|
14
|
+
|
15
|
+
parent.versions.last.restore
|
16
|
+
Parent.find(parent.id).name.should eq "First Restore Test"
|
17
|
+
end
|
18
|
+
|
19
|
+
it "after a restore the last versions action should be restored" do
|
20
|
+
parent = Parent.find_by_name("First Restore Test")
|
21
|
+
parent.name = "Updated Restore Test"
|
22
|
+
|
23
|
+
parent.versions.last.restore
|
24
|
+
Parent.find(parent.id).versions.last.event.should eq "restore"
|
25
|
+
end
|
26
|
+
|
27
|
+
it "should restore a deleted version" do
|
28
|
+
parent = Parent.find_by_name("First Restore Test")
|
29
|
+
parent.destroy
|
30
|
+
parent_id = parent.id
|
31
|
+
|
32
|
+
version = Wikify.destroyed_versions(Parent).last
|
33
|
+
version.restore
|
34
|
+
|
35
|
+
parent = Parent.find_by_name("First Restore Test")
|
36
|
+
parent.name.should eq "First Restore Test"
|
37
|
+
parent.id.should eq parent_id
|
38
|
+
end
|
39
|
+
end
|
data/spec/spec_helper.rb
ADDED
@@ -0,0 +1,27 @@
|
|
1
|
+
require 'simplecov'
|
2
|
+
require 'coveralls'
|
3
|
+
SimpleCov.formatter = SimpleCov::Formatter::MultiFormatter[
|
4
|
+
SimpleCov::Formatter::HTMLFormatter,
|
5
|
+
Coveralls::SimpleCov::Formatter
|
6
|
+
]
|
7
|
+
SimpleCov.start do
|
8
|
+
add_filter "spec"
|
9
|
+
end
|
10
|
+
|
11
|
+
# Controller
|
12
|
+
require 'support/controller'
|
13
|
+
|
14
|
+
# Require Gem
|
15
|
+
require 'wikify'
|
16
|
+
|
17
|
+
ActionController::Base.load
|
18
|
+
|
19
|
+
# Require Models
|
20
|
+
require 'models/parent'
|
21
|
+
require 'models/document'
|
22
|
+
require 'models/revision'
|
23
|
+
require 'models/child'
|
24
|
+
|
25
|
+
# Configure Active Record
|
26
|
+
require 'sqlite3'
|
27
|
+
require 'support/database'
|
@@ -0,0 +1,45 @@
|
|
1
|
+
module ActionController
|
2
|
+
API = true
|
3
|
+
|
4
|
+
class Base
|
5
|
+
def self.load
|
6
|
+
ActiveSupport.run_load_hooks(:action_controller, self)
|
7
|
+
end
|
8
|
+
|
9
|
+
def self.before_filter(sym)
|
10
|
+
true
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
class Controller < ActionController::Base
|
16
|
+
def initialize
|
17
|
+
set_wikify_user
|
18
|
+
end
|
19
|
+
|
20
|
+
def current_user
|
21
|
+
OpenStruct.new({id: 1})
|
22
|
+
end
|
23
|
+
|
24
|
+
def request
|
25
|
+
parent = Parent.find_by_name("Committer 1")
|
26
|
+
parent.name = "Committer 1 Updated"
|
27
|
+
parent.save
|
28
|
+
end
|
29
|
+
end
|
30
|
+
|
31
|
+
class NilController < ActionController::Base
|
32
|
+
def initialize
|
33
|
+
set_wikify_user
|
34
|
+
end
|
35
|
+
|
36
|
+
def current_user
|
37
|
+
nil
|
38
|
+
end
|
39
|
+
|
40
|
+
def request
|
41
|
+
parent = Parent.find_by_name("Committer 1")
|
42
|
+
parent.name = "Committer 1 Updated"
|
43
|
+
parent.save
|
44
|
+
end
|
45
|
+
end
|
@@ -0,0 +1,73 @@
|
|
1
|
+
ActiveRecord::Base.establish_connection(
|
2
|
+
:adapter => 'sqlite3',
|
3
|
+
:database => ':memory:'
|
4
|
+
)
|
5
|
+
|
6
|
+
puts "---------------"
|
7
|
+
puts "Database Creation"
|
8
|
+
puts "---------------"
|
9
|
+
|
10
|
+
ActiveRecord::Schema.define do
|
11
|
+
create_table :parents do |table|
|
12
|
+
table.column :name, :string
|
13
|
+
|
14
|
+
table.timestamps
|
15
|
+
end
|
16
|
+
|
17
|
+
create_table :children do |table|
|
18
|
+
table.column :name, :string
|
19
|
+
table.column :parent_id, :integer
|
20
|
+
|
21
|
+
table.timestamps
|
22
|
+
end
|
23
|
+
|
24
|
+
create_table :wikify_versions do |table|
|
25
|
+
table.column :resource_id, :integer
|
26
|
+
table.column :resource_type, :string
|
27
|
+
table.column :data, :text
|
28
|
+
table.column :linked_child_resource_type, :string
|
29
|
+
table.column :linked_child_resource_id, :integer
|
30
|
+
table.column :linked_child, :boolean, default: false
|
31
|
+
table.column :event, :string
|
32
|
+
table.column :comitter_id, :integer
|
33
|
+
|
34
|
+
table.timestamps
|
35
|
+
end
|
36
|
+
|
37
|
+
create_table :revisions do |table|
|
38
|
+
table.column :thing_id, :integer
|
39
|
+
table.column :thing_type, :string
|
40
|
+
table.column :linked_child_thing_id, :integer
|
41
|
+
table.column :linked_child_thing_type, :string
|
42
|
+
table.column :linked_child, :boolean, default: false
|
43
|
+
table.column :data, :text
|
44
|
+
table.column :event, :string
|
45
|
+
table.column :comitter_id, :integer
|
46
|
+
|
47
|
+
table.timestamps
|
48
|
+
end
|
49
|
+
|
50
|
+
create_table :documents do |table|
|
51
|
+
table.column :title, :string
|
52
|
+
|
53
|
+
table.timestamps
|
54
|
+
end
|
55
|
+
end
|
56
|
+
|
57
|
+
puts "---------------"
|
58
|
+
puts "Begin Tests"
|
59
|
+
puts "---------------"
|
60
|
+
|
61
|
+
describe "The Database" do
|
62
|
+
it "should be empty" do
|
63
|
+
Parent.all.count.should eq 0
|
64
|
+
Child.all.count.should eq 0
|
65
|
+
end
|
66
|
+
|
67
|
+
it "should work" do
|
68
|
+
parent = Parent.new
|
69
|
+
parent.name = "Hello World"
|
70
|
+
parent.save
|
71
|
+
Parent.last.name.should eq "Hello World"
|
72
|
+
end
|
73
|
+
end
|
data/spec/update_spec.rb
ADDED
@@ -0,0 +1,28 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe "Model Update" do
|
4
|
+
it "should create a version on update and set the event to :update" do
|
5
|
+
parent = Parent.new({name: "First Update Test"})
|
6
|
+
parent.save
|
7
|
+
|
8
|
+
ffound = Parent.find_by_name("First Update Test")
|
9
|
+
ffound.name = "Updated First Update Test"
|
10
|
+
ffound.save
|
11
|
+
|
12
|
+
sfound = Parent.find_by_name("Updated First Update Test")
|
13
|
+
sfound.versions.count.should eq 2
|
14
|
+
sfound.versions.last.data["name"].should eq "First Update Test"
|
15
|
+
sfound.versions.last.event.should eq "update"
|
16
|
+
end
|
17
|
+
|
18
|
+
it "should create a second version after the first" do
|
19
|
+
ffound = Parent.find_by_name("Updated First Update Test")
|
20
|
+
ffound.name = "Second Update Test"
|
21
|
+
ffound.save
|
22
|
+
|
23
|
+
sfound = Parent.find_by_name("Second Update Test")
|
24
|
+
sfound.versions.count.should eq 3
|
25
|
+
sfound.versions[1].data["name"].should eq "First Update Test"
|
26
|
+
sfound.versions.last.data["name"].should eq "Updated First Update Test"
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe Wikify::Version do
|
4
|
+
it "should create a struct for your data" do
|
5
|
+
version = Wikify::Version.last
|
6
|
+
version.object.should be_a OpenStruct
|
7
|
+
end
|
8
|
+
|
9
|
+
it "should have a link to the previous version" do
|
10
|
+
version = Wikify::Version.last
|
11
|
+
version.previous.should be_a Wikify::Version
|
12
|
+
end
|
13
|
+
|
14
|
+
it "should have a link to the next version" do
|
15
|
+
version = Wikify::Version.last
|
16
|
+
prev = version.previous
|
17
|
+
prev.next.should be_a Wikify::Version
|
18
|
+
end
|
19
|
+
|
20
|
+
it "should return the current model for next if it is the latest version" do
|
21
|
+
version = Wikify::Version.last
|
22
|
+
version.next.should be_a version.restore_type.constantize
|
23
|
+
end
|
24
|
+
|
25
|
+
it "should find the version at a specified time" do
|
26
|
+
parent = Parent.new({name: 'Time Test'})
|
27
|
+
parent.save
|
28
|
+
sleep 3
|
29
|
+
parent = Parent.find(parent.id)
|
30
|
+
parent.name = "Time Test 1"
|
31
|
+
parent.save
|
32
|
+
sleep 1
|
33
|
+
version = parent.version_at(Time.now - 3)
|
34
|
+
version.should be_a Wikify::Version
|
35
|
+
version.object.name.should eq "Time Test"
|
36
|
+
end
|
37
|
+
end
|
data/wikify.gemspec
ADDED
@@ -0,0 +1,29 @@
|
|
1
|
+
# coding: utf-8
|
2
|
+
lib = File.expand_path('../lib', __FILE__)
|
3
|
+
$LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
|
4
|
+
require 'wikify/version_number'
|
5
|
+
|
6
|
+
Gem::Specification.new do |spec|
|
7
|
+
spec.name = "wikify"
|
8
|
+
spec.version = Wikify::VersionNumber
|
9
|
+
spec.authors = ["Adam Laycock"]
|
10
|
+
spec.email = ["adam@arcath.net"]
|
11
|
+
spec.description = %q{Active Record Model history/versioning with restore functionality.}
|
12
|
+
spec.summary = %q{Active Record Model history/versioning with restore functionality.}
|
13
|
+
spec.homepage = ""
|
14
|
+
spec.license = "MIT"
|
15
|
+
|
16
|
+
spec.files = `git ls-files`.split($/)
|
17
|
+
spec.executables = spec.files.grep(%r{^bin/}) { |f| File.basename(f) }
|
18
|
+
spec.test_files = spec.files.grep(%r{^(test|spec|features)/})
|
19
|
+
spec.require_paths = ["lib"]
|
20
|
+
|
21
|
+
spec.add_dependency "activerecord", "~> 4.0"
|
22
|
+
spec.add_dependency "activesupport", "~> 4.0"
|
23
|
+
|
24
|
+
spec.add_development_dependency "bundler", "~> 1.3"
|
25
|
+
spec.add_development_dependency "rake"
|
26
|
+
spec.add_development_dependency 'rspec'
|
27
|
+
spec.add_development_dependency 'sqlite3'
|
28
|
+
spec.add_development_dependency 'coveralls'
|
29
|
+
end
|
metadata
ADDED
@@ -0,0 +1,194 @@
|
|
1
|
+
--- !ruby/object:Gem::Specification
|
2
|
+
name: wikify
|
3
|
+
version: !ruby/object:Gem::Version
|
4
|
+
version: 0.0.1.pre
|
5
|
+
platform: ruby
|
6
|
+
authors:
|
7
|
+
- Adam Laycock
|
8
|
+
autorequire:
|
9
|
+
bindir: bin
|
10
|
+
cert_chain: []
|
11
|
+
date: 2014-01-14 00:00:00.000000000 Z
|
12
|
+
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: activerecord
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - ~>
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: '4.0'
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - ~>
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: '4.0'
|
27
|
+
- !ruby/object:Gem::Dependency
|
28
|
+
name: activesupport
|
29
|
+
requirement: !ruby/object:Gem::Requirement
|
30
|
+
requirements:
|
31
|
+
- - ~>
|
32
|
+
- !ruby/object:Gem::Version
|
33
|
+
version: '4.0'
|
34
|
+
type: :runtime
|
35
|
+
prerelease: false
|
36
|
+
version_requirements: !ruby/object:Gem::Requirement
|
37
|
+
requirements:
|
38
|
+
- - ~>
|
39
|
+
- !ruby/object:Gem::Version
|
40
|
+
version: '4.0'
|
41
|
+
- !ruby/object:Gem::Dependency
|
42
|
+
name: bundler
|
43
|
+
requirement: !ruby/object:Gem::Requirement
|
44
|
+
requirements:
|
45
|
+
- - ~>
|
46
|
+
- !ruby/object:Gem::Version
|
47
|
+
version: '1.3'
|
48
|
+
type: :development
|
49
|
+
prerelease: false
|
50
|
+
version_requirements: !ruby/object:Gem::Requirement
|
51
|
+
requirements:
|
52
|
+
- - ~>
|
53
|
+
- !ruby/object:Gem::Version
|
54
|
+
version: '1.3'
|
55
|
+
- !ruby/object:Gem::Dependency
|
56
|
+
name: rake
|
57
|
+
requirement: !ruby/object:Gem::Requirement
|
58
|
+
requirements:
|
59
|
+
- - '>='
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
62
|
+
type: :development
|
63
|
+
prerelease: false
|
64
|
+
version_requirements: !ruby/object:Gem::Requirement
|
65
|
+
requirements:
|
66
|
+
- - '>='
|
67
|
+
- !ruby/object:Gem::Version
|
68
|
+
version: '0'
|
69
|
+
- !ruby/object:Gem::Dependency
|
70
|
+
name: rspec
|
71
|
+
requirement: !ruby/object:Gem::Requirement
|
72
|
+
requirements:
|
73
|
+
- - '>='
|
74
|
+
- !ruby/object:Gem::Version
|
75
|
+
version: '0'
|
76
|
+
type: :development
|
77
|
+
prerelease: false
|
78
|
+
version_requirements: !ruby/object:Gem::Requirement
|
79
|
+
requirements:
|
80
|
+
- - '>='
|
81
|
+
- !ruby/object:Gem::Version
|
82
|
+
version: '0'
|
83
|
+
- !ruby/object:Gem::Dependency
|
84
|
+
name: sqlite3
|
85
|
+
requirement: !ruby/object:Gem::Requirement
|
86
|
+
requirements:
|
87
|
+
- - '>='
|
88
|
+
- !ruby/object:Gem::Version
|
89
|
+
version: '0'
|
90
|
+
type: :development
|
91
|
+
prerelease: false
|
92
|
+
version_requirements: !ruby/object:Gem::Requirement
|
93
|
+
requirements:
|
94
|
+
- - '>='
|
95
|
+
- !ruby/object:Gem::Version
|
96
|
+
version: '0'
|
97
|
+
- !ruby/object:Gem::Dependency
|
98
|
+
name: coveralls
|
99
|
+
requirement: !ruby/object:Gem::Requirement
|
100
|
+
requirements:
|
101
|
+
- - '>='
|
102
|
+
- !ruby/object:Gem::Version
|
103
|
+
version: '0'
|
104
|
+
type: :development
|
105
|
+
prerelease: false
|
106
|
+
version_requirements: !ruby/object:Gem::Requirement
|
107
|
+
requirements:
|
108
|
+
- - '>='
|
109
|
+
- !ruby/object:Gem::Version
|
110
|
+
version: '0'
|
111
|
+
description: Active Record Model history/versioning with restore functionality.
|
112
|
+
email:
|
113
|
+
- adam@arcath.net
|
114
|
+
executables: []
|
115
|
+
extensions: []
|
116
|
+
extra_rdoc_files: []
|
117
|
+
files:
|
118
|
+
- .gitignore
|
119
|
+
- .travis.yml
|
120
|
+
- Gemfile
|
121
|
+
- LICENSE.txt
|
122
|
+
- README.md
|
123
|
+
- Rakefile
|
124
|
+
- lib/generators/wikify/migration/USAGE
|
125
|
+
- lib/generators/wikify/migration/migration_generator.rb
|
126
|
+
- lib/wikify.rb
|
127
|
+
- lib/wikify/child_methods.rb
|
128
|
+
- lib/wikify/controller.rb
|
129
|
+
- lib/wikify/methods.rb
|
130
|
+
- lib/wikify/model.rb
|
131
|
+
- lib/wikify/version.rb
|
132
|
+
- lib/wikify/version_concern.rb
|
133
|
+
- lib/wikify/version_number.rb
|
134
|
+
- spec/children_spec.rb
|
135
|
+
- spec/comitter_spec.rb
|
136
|
+
- spec/config_spec.rb
|
137
|
+
- spec/create_spec.rb
|
138
|
+
- spec/destroy_spec.rb
|
139
|
+
- spec/included_spec.rb
|
140
|
+
- spec/logical_function_spec.rb
|
141
|
+
- spec/models/child.rb
|
142
|
+
- spec/models/document.rb
|
143
|
+
- spec/models/parent.rb
|
144
|
+
- spec/models/revision.rb
|
145
|
+
- spec/restore_spec.rb
|
146
|
+
- spec/spec_helper.rb
|
147
|
+
- spec/support/controller.rb
|
148
|
+
- spec/support/database.rb
|
149
|
+
- spec/update_spec.rb
|
150
|
+
- spec/version_spec.rb
|
151
|
+
- wikify.gemspec
|
152
|
+
homepage: ''
|
153
|
+
licenses:
|
154
|
+
- MIT
|
155
|
+
metadata: {}
|
156
|
+
post_install_message:
|
157
|
+
rdoc_options: []
|
158
|
+
require_paths:
|
159
|
+
- lib
|
160
|
+
required_ruby_version: !ruby/object:Gem::Requirement
|
161
|
+
requirements:
|
162
|
+
- - '>='
|
163
|
+
- !ruby/object:Gem::Version
|
164
|
+
version: '0'
|
165
|
+
required_rubygems_version: !ruby/object:Gem::Requirement
|
166
|
+
requirements:
|
167
|
+
- - '>'
|
168
|
+
- !ruby/object:Gem::Version
|
169
|
+
version: 1.3.1
|
170
|
+
requirements: []
|
171
|
+
rubyforge_project:
|
172
|
+
rubygems_version: 2.0.0
|
173
|
+
signing_key:
|
174
|
+
specification_version: 4
|
175
|
+
summary: Active Record Model history/versioning with restore functionality.
|
176
|
+
test_files:
|
177
|
+
- spec/children_spec.rb
|
178
|
+
- spec/comitter_spec.rb
|
179
|
+
- spec/config_spec.rb
|
180
|
+
- spec/create_spec.rb
|
181
|
+
- spec/destroy_spec.rb
|
182
|
+
- spec/included_spec.rb
|
183
|
+
- spec/logical_function_spec.rb
|
184
|
+
- spec/models/child.rb
|
185
|
+
- spec/models/document.rb
|
186
|
+
- spec/models/parent.rb
|
187
|
+
- spec/models/revision.rb
|
188
|
+
- spec/restore_spec.rb
|
189
|
+
- spec/spec_helper.rb
|
190
|
+
- spec/support/controller.rb
|
191
|
+
- spec/support/database.rb
|
192
|
+
- spec/update_spec.rb
|
193
|
+
- spec/version_spec.rb
|
194
|
+
has_rdoc:
|