active_versioning 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml ADDED
@@ -0,0 +1,7 @@
1
+ ---
2
+ SHA1:
3
+ metadata.gz: 372e09adffd4d458bf02a8f21790b4c0545c3654
4
+ data.tar.gz: d7d12be88770e3731fcda71a38dc8ccdee72ab50
5
+ SHA512:
6
+ metadata.gz: 7e60a689e0bb675c81617a4c1f585e2a7e9c609603608cb29aa2301af76c2d4586b91104d9cc20d7686e6730442fd472958d79a197cca27373f5a8d9322026b2
7
+ data.tar.gz: e9b46b96aade3689dddcd4de01b089d75316e8c478d129e2e9a71d31abd613b5b177230cd8de9f9e4a3095be2ac48ee3ff09df6e41f564ac2cd27c77912632c3
data/.gitignore ADDED
@@ -0,0 +1,9 @@
1
+ /.bundle/
2
+ /.yardoc
3
+ /Gemfile.lock
4
+ /_yardoc/
5
+ /coverage/
6
+ /doc/
7
+ /pkg/
8
+ /spec/reports/
9
+ /tmp/
data/.rspec ADDED
@@ -0,0 +1,2 @@
1
+ --format documentation
2
+ --color
data/.travis.yml ADDED
@@ -0,0 +1,4 @@
1
+ language: ruby
2
+ rvm:
3
+ - 2.2.2
4
+ before_install: gem install bundler -v 1.10.3
data/Gemfile ADDED
@@ -0,0 +1,4 @@
1
+ source 'https://rubygems.org'
2
+
3
+ # Specify your gem's dependencies in active_versioning.gemspec
4
+ gemspec
data/README.md ADDED
@@ -0,0 +1,140 @@
1
+ # ActiveVersioning
2
+
3
+ [![Gem Version](https://badge.fury.io/rb/active_versioning.svg)](http://badge.fury.io/rb/active_versioning) [![Code Climate](https://codeclimate.com/github/vigetlabs/active_versioning/badges/gpa.svg)](https://codeclimate.com/github/vigetlabs/active_versioning) [![Test Coverage](https://codeclimate.com/github/vigetlabs/active_versioning/badges/coverage.svg)](https://codeclimate.com/github/vigetlabs/active_versioning/coverage) [![Circle CI](https://circleci.com/gh/vigetlabs/active_versioning.svg?style=svg)](https://circleci.com/gh/vigetlabs/active_versioning)
4
+
5
+ ActiveVersioning provides out-of-the-box versioning functionality in Rails. ActiveVersioning serializes attributes when records are saved and allows for version and draft management.
6
+
7
+ ## Installation
8
+
9
+ Add this line to your application's Gemfile:
10
+
11
+ ```ruby
12
+ gem 'active_versioning'
13
+ ```
14
+
15
+ And then execute:
16
+
17
+ $ bundle
18
+
19
+ Or install it yourself as:
20
+
21
+ $ gem install active_versioning
22
+
23
+ Once installed, generate the necessary files and run migrations:
24
+
25
+ $ rails generate active_versioning
26
+ $ bundle exec rake db:migrate
27
+
28
+ ## Setup
29
+
30
+ To set up versioning in your Rails app, include the following module in each model you'd like to version:
31
+ ```ruby
32
+ class Post < ActiveRecord::Base
33
+ include ActiveVersioning::Model::Versioned
34
+ end
35
+ ```
36
+
37
+ ## Working with Drafts
38
+
39
+ `ActiveVersioning::Model::Versioned` provides a number of methods for accessing and working with versions.
40
+
41
+ To access the current draft of a record, use...
42
+ ```ruby
43
+ draft = post.current_draft
44
+ ```
45
+ This returns a proxy object to a draft version of the record, so you can treat it like the `post` itself -- making changes and either saving or updating.
46
+ ```ruby
47
+ draft.title = 'New Title'
48
+ draft.save
49
+
50
+ # or..
51
+
52
+ draft.update(title: 'New Title')
53
+ ```
54
+ Both `save` and `update` will make changes to the draft version of the post.
55
+
56
+ When you are ready to overwrite the record with its draft, use...
57
+ ```ruby
58
+ draft.commit(committer: 'Bob', commit_message: 'Update post title.')
59
+ ```
60
+ This changes our post's attributes to match those of the draft and then marks the draft as a committed version.
61
+
62
+ If you want to throw away a draft:
63
+ ```ruby
64
+ post.destroy_draft
65
+ ```
66
+
67
+ ## Working with Versions
68
+
69
+ A draft is just a version with a particular state. To access all the versions for a particular record, use...
70
+ ```ruby
71
+ post.versions # => All versions, whether the version state is 'create', 'draft', or 'commit'
72
+ post.versions.draft # => All draft versions
73
+ post.versions.committed # => All non-draft versions
74
+ post.versions.newest_first # => All versions starting with the most recently created
75
+ ```
76
+
77
+ You can use any existing version to create a new draft:
78
+ ```ruby
79
+ old_version = post.versions.committed.first
80
+
81
+ post.create_draft_from_version(old_version.id)
82
+ ```
83
+ This will set `post.current_draft`'s attributes to the attributes stored in the given version's record. Returns boolean based on the save's success.
84
+
85
+ ## Capturing Version Metadata
86
+
87
+ In addition to manually committing a version with a committer and commit message...
88
+ ```ruby
89
+ post.current_draft.commit(committer: 'Bob', commit_message: 'Update post title.')
90
+ ```
91
+ ActiveVersioning provides a `version_author` accessor on any versioned model, so you can capture the author for a record's initial create:
92
+ ```ruby
93
+ post = Post.create(title: 'Title', body: 'Body text.', version_author: 'Bob')
94
+
95
+ post.versions.first.version_author # => 'Bob'
96
+ ```
97
+
98
+ ## Viewing and Modifying Versioned Attributes
99
+
100
+ If you want to see the attributes the are versioned, use...
101
+ ```ruby
102
+ post.versioned_attributes # => { 'id' => 1, 'title' => 'Default Title' }
103
+ ```
104
+
105
+ If you require additional versioned attributes, overwrite the `versioned_attribute_names` method in your model:
106
+ ```ruby
107
+ class Post < ActiveRecord::Base
108
+ private
109
+
110
+ def versioned_attribute_names
111
+ super + %w(photo_id)
112
+ end
113
+ end
114
+ ```
115
+
116
+ ## Handling Incompatible Versions
117
+
118
+ In the case of a versioned model that undergoes a schema change, all previous versions may reference attributes that no longer exist.
119
+
120
+ In ActiveVersioning, we consider these incompatible versions. An attempt to create a draft from an incompatible version will raise an error:
121
+ ```
122
+ incompatible_version = post.versions.committed.last
123
+
124
+ incompatible_version.object
125
+ # => { 'deleted_attribute' => value }
126
+
127
+ post.create_draft_from_version(incompatible_version.id)
128
+ # => ActiveVersioning::Errors::IncompatibleVersion:
129
+ # The given version contains attributes that are no longer compatible with the current schema: deleted_attribute.
130
+ ```
131
+
132
+ When rescued, the error object contains a reference to the record and the incompatible version:
133
+ ```
134
+ begin
135
+ post.create_draft_from_version(incompatible_version.id)
136
+ rescue ActiveVersioning::Errors::IncompatibleVersion => error
137
+ error.record # => our `post` record
138
+ error.version # => our `incompatible_version`
139
+ end
140
+ ```
data/Rakefile ADDED
@@ -0,0 +1,6 @@
1
+ require "bundler/gem_tasks"
2
+ require "rspec/core/rake_task"
3
+
4
+ RSpec::Core::RakeTask.new(:spec)
5
+
6
+ task :default => :spec
@@ -0,0 +1,34 @@
1
+ # coding: utf-8
2
+ lib = File.expand_path('../lib', __FILE__)
3
+ $LOAD_PATH.unshift(lib) unless $LOAD_PATH.include?(lib)
4
+
5
+ require 'active_versioning/version'
6
+
7
+ Gem::Specification.new do |spec|
8
+ spec.name = "active_versioning"
9
+ spec.version = ActiveVersioning::VERSION
10
+ spec.authors = ["Ryan Stenberg"]
11
+ spec.email = ["ryan.stenberg@viget.com"]
12
+
13
+ spec.summary = "Plug-and-Play Versioning for Rails"
14
+ spec.description = "ActiveVersioning serializes attributes when records are saved and allows for version and draft management."
15
+ spec.homepage = "https://github.com/vigetlabs/active_versioning"
16
+ spec.license = "BSD"
17
+
18
+ spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
19
+ spec.bindir = "exe"
20
+ spec.executables = spec.files.grep(%r{^exe/}) { |f| File.basename(f) }
21
+ spec.require_paths = ["lib"]
22
+
23
+ spec.add_dependency "rails", ">= 4.2.1"
24
+
25
+ spec.add_development_dependency "bundler", ">= 1.10"
26
+ spec.add_development_dependency "rake", ">= 10.0"
27
+ spec.add_development_dependency "rspec"
28
+ spec.add_development_dependency "shoulda-matchers"
29
+ spec.add_development_dependency "database_cleaner"
30
+ spec.add_development_dependency "generator_spec"
31
+ spec.add_development_dependency "pry"
32
+ spec.add_development_dependency "sqlite3"
33
+ spec.add_development_dependency "codeclimate-test-reporter"
34
+ end
data/bin/console ADDED
@@ -0,0 +1,14 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require "bundler/setup"
4
+ require "active_versioning"
5
+
6
+ # You can add fixtures and/or initialization code here to make experimenting
7
+ # with your gem easier. You can also use a different console, if you like.
8
+
9
+ # (If you use this, don't forget to add pry to your Gemfile!)
10
+ # require "pry"
11
+ # Pry.start
12
+
13
+ require "irb"
14
+ IRB.start
data/bin/setup ADDED
@@ -0,0 +1,7 @@
1
+ #!/bin/bash
2
+ set -euo pipefail
3
+ IFS=$'\n\t'
4
+
5
+ bundle install
6
+
7
+ # Do any other automated setup that you need to do here
data/circle.yml ADDED
@@ -0,0 +1,6 @@
1
+ database:
2
+ override:
3
+ - echo "No database setup necessary."
4
+ dependencies:
5
+ pre:
6
+ - gem install bundler --pre
@@ -0,0 +1,12 @@
1
+ module ActiveVersioning
2
+ module Errors
3
+ class IncompatibleVersion < StandardError
4
+ attr_reader :record, :version
5
+
6
+ def initialize(record, version)
7
+ @record = record
8
+ @version = version
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,8 @@
1
+ module ActiveVersioning
2
+ module Errors
3
+ autoload :IncompatibleVersion, 'active_versioning/errors/incompatible_version'
4
+
5
+ RecordNotPersisted = Class.new(StandardError)
6
+ InvalidVersion = Class.new(StandardError)
7
+ end
8
+ end
@@ -0,0 +1,13 @@
1
+ module ActiveVersioning
2
+ module Events
3
+ CREATE = 'create'
4
+ DRAFT = 'draft'
5
+ COMMIT = 'commit'
6
+
7
+ ALL = [
8
+ CREATE,
9
+ DRAFT,
10
+ COMMIT
11
+ ]
12
+ end
13
+ end
@@ -0,0 +1,119 @@
1
+ module ActiveVersioning
2
+ module Model
3
+ class VersionProxy < Delegator
4
+ #
5
+ # VersionProxy class
6
+ #
7
+ # Uses Ruby's Delegator class to delegate methods to the versioned
8
+ # resource. The bulk of this class overrides the Rails save, update, and
9
+ # reload methods to modify the record in the versions table as opposed
10
+ # to the versioned resource.
11
+ #
12
+ # A `commit` instance method writes to the versioned resource's record.
13
+
14
+ VersionInvalid = Class.new(StandardError)
15
+
16
+ attr_reader :version
17
+
18
+ def initialize(version)
19
+ @version = version
20
+ __setobj__(version.reify)
21
+ end
22
+
23
+ def __getobj__
24
+ @record
25
+ end
26
+
27
+ def __setobj__(record)
28
+ @record = record
29
+ end
30
+
31
+ # `class` should delegate to versioned resource, not return
32
+ # ActiveVersioning::Model::VersionProxy
33
+ undef class
34
+
35
+ def reload
36
+ __setobj__(version.reify)
37
+ end
38
+
39
+ def to_param
40
+ version.versionable.to_param
41
+ end
42
+
43
+ def save(*)
44
+ if valid?
45
+ version.update(version_attributes)
46
+ else
47
+ false
48
+ end
49
+ end
50
+
51
+ def save!(*)
52
+ if valid?
53
+ version.update!(version_attributes)
54
+ else
55
+ raise ::ActiveRecord::RecordInvalid.new(__getobj__)
56
+ end
57
+ end
58
+
59
+ def update(attributes)
60
+ raise draft_exception unless version.draft?
61
+
62
+ with_transaction_returning_status do
63
+ assign_attributes(attributes)
64
+ save
65
+ end
66
+ end
67
+ alias update_attributes update
68
+
69
+ def update!(attributes)
70
+ raise draft_exception unless version.draft?
71
+
72
+ with_transaction_returning_status do
73
+ assign_attributes(attributes)
74
+ save!
75
+ end
76
+ end
77
+ alias update_attributes! update!
78
+
79
+ def live?
80
+ false
81
+ end
82
+
83
+ def version?
84
+ true
85
+ end
86
+
87
+ def commit(params = {})
88
+ raise draft_exception unless version.draft?
89
+
90
+ attrs = version_attributes.tap do |attrs|
91
+ attrs.merge!(
92
+ draft: false,
93
+ event: ActiveVersioning::Events::COMMIT,
94
+ committed_at: Time.current
95
+ )
96
+
97
+ attrs.merge!(params)
98
+ end
99
+
100
+ version.update(attrs)
101
+
102
+ __getobj__.update(versioned_attributes)
103
+ end
104
+
105
+ private
106
+
107
+ def draft_exception
108
+ ActiveVersioning::Errors::InvalidVersion.new("Version #{version.id} must be a draft")
109
+ end
110
+
111
+ def version_attributes
112
+ {
113
+ committer: version_author,
114
+ object: versioned_attributes
115
+ }
116
+ end
117
+ end
118
+ end
119
+ end
@@ -0,0 +1,73 @@
1
+ module ActiveVersioning
2
+ module Model
3
+ module Versioned
4
+ def self.included(base)
5
+ base.class_eval do
6
+ has_many :versions, -> { newest_first }, as: :versionable, dependent: :destroy
7
+
8
+ after_create :create_version!
9
+
10
+ attr_accessor :version_author
11
+ end
12
+ end
13
+
14
+ def live?
15
+ true
16
+ end
17
+
18
+ def version?
19
+ false
20
+ end
21
+
22
+ def current_draft(force_reload = false)
23
+ unless persisted?
24
+ raise ActiveVersioning::Errors::RecordNotPersisted.new("#{self} must be persisted to create a draft version")
25
+ end
26
+
27
+ @current_draft = nil if force_reload
28
+
29
+ @current_draft ||= VersionProxy.new(versions.draft.first_or_create(
30
+ object: versioned_attributes,
31
+ event: 'draft'
32
+ ))
33
+ end
34
+
35
+ def current_draft?
36
+ versions.draft.present?
37
+ end
38
+
39
+ def destroy_draft
40
+ versions.draft.destroy_all
41
+ end
42
+
43
+ def version_manager
44
+ @version_manager ||= VersionManager.new(self)
45
+ end
46
+
47
+ def create_draft_from_version(version_id)
48
+ version_manager.create_draft_from_version(version_id) and current_draft(true)
49
+ end
50
+
51
+ def versioned_attributes
52
+ versioned_attribute_names.reduce(Hash.new) do |attrs, name|
53
+ attrs.merge(name => send(name))
54
+ end
55
+ end
56
+
57
+ def versioned_attribute_names
58
+ attribute_names - VersionManager::BLACKLISTED_ATTRIBUTES
59
+ end
60
+
61
+ private
62
+
63
+ def create_version!
64
+ versions.create!(
65
+ event: ActiveVersioning::Events::CREATE,
66
+ committer: version_author,
67
+ committed_at: Time.current,
68
+ object: versioned_attributes
69
+ )
70
+ end
71
+ end
72
+ end
73
+ end
@@ -0,0 +1,37 @@
1
+ module ActiveVersioning
2
+ module Model
3
+ extend ActiveSupport::Concern
4
+
5
+ autoload :Versioned, 'active_versioning/model/versioned'
6
+ autoload :VersionProxy, 'active_versioning/model/version_proxy'
7
+
8
+ included do
9
+ belongs_to :versionable, polymorphic: true
10
+
11
+ serialize :object, Hash
12
+
13
+ validates :event, presence: true, inclusion: { in: ActiveVersioning::Events::ALL }
14
+
15
+ scope :newest_first, -> { order created_at: :desc }
16
+ scope :draft, -> { where draft: true }
17
+ scope :committed, -> { where draft: false }
18
+
19
+ def to_s
20
+ [
21
+ versionable.to_s,
22
+ committed_at.try(:utc).try(:strftime, '#%Y%m%d%H%M%S')
23
+ ].compact.join(' ')
24
+ end
25
+
26
+ def reify
27
+ resource = versionable(true)
28
+
29
+ # Necessary to ensure resource and versionable are two distinct objects in memory
30
+ versionable(true)
31
+
32
+ resource.assign_attributes(object.slice(*resource.versioned_attribute_names))
33
+ resource
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,3 @@
1
+ module ActiveVersioning
2
+ VERSION = "0.1.0"
3
+ end
@@ -0,0 +1,31 @@
1
+ module ActiveVersioning
2
+ class VersionManager < Struct.new(:record)
3
+ BLACKLISTED_ATTRIBUTES = %w(
4
+ created_at
5
+ updated_at
6
+ published
7
+ )
8
+
9
+ def create_draft_from_version(id)
10
+ version = record.versions.find(id)
11
+
12
+ ensure_compatibility_with(version)
13
+
14
+ new_version = record.versions.draft.first_or_create(event: 'draft')
15
+ new_version.object = version.object
16
+ new_version.save
17
+ end
18
+
19
+ def ensure_compatibility_with(version)
20
+ incompatible_attributes(version).tap do |incompatible_attrs|
21
+ if incompatible_attrs.any?
22
+ raise Errors::IncompatibleVersion.new(record, version), "The given version contains attributes that are no longer compatible with the current schema: #{incompatible_attrs.to_sentence}."
23
+ end
24
+ end
25
+ end
26
+
27
+ def incompatible_attributes(version)
28
+ version.object.keys - record.attributes.keys
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,9 @@
1
+ require 'active_versioning/version'
2
+ require 'generators/active_versioning_generator'
3
+
4
+ module ActiveVersioning
5
+ autoload :Errors, 'active_versioning/errors'
6
+ autoload :Events, 'active_versioning/events'
7
+ autoload :Model, 'active_versioning/model'
8
+ autoload :VersionManager, 'active_versioning/version_manager'
9
+ end
@@ -0,0 +1,15 @@
1
+ require 'rails/generators/active_record/migration'
2
+
3
+ class ActiveVersioningGenerator < Rails::Generators::Base
4
+ include ActiveRecord::Generators::Migration
5
+
6
+ source_root File.expand_path('../templates', __FILE__)
7
+
8
+ def install_models
9
+ copy_file 'models/version.rb', 'app/models/version.rb'
10
+ end
11
+
12
+ def install_migrations
13
+ migration_template 'migrations/create_versions.rb', 'db/migrate/create_versions.rb'
14
+ end
15
+ end
@@ -0,0 +1,18 @@
1
+ class CreateVersions < ActiveRecord::Migration
2
+ def change
3
+ create_table :versions do |t|
4
+ t.string :versionable_type, null: false
5
+ t.integer :versionable_id, null: false
6
+ t.string :event, null: false
7
+ t.string :committer
8
+ t.text :object
9
+ t.boolean :draft, default: false
10
+ t.text :commit_message
11
+ t.datetime :committed_at
12
+
13
+ t.timestamps null: false
14
+ end
15
+
16
+ add_index :versions, [:versionable_type, :versionable_id]
17
+ end
18
+ end
@@ -0,0 +1,3 @@
1
+ class Version < ActiveRecord::Base
2
+ include ActiveVersioning::Model
3
+ end
metadata ADDED
@@ -0,0 +1,207 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: active_versioning
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.0
5
+ platform: ruby
6
+ authors:
7
+ - Ryan Stenberg
8
+ autorequire:
9
+ bindir: exe
10
+ cert_chain: []
11
+ date: 2015-09-16 00:00:00.000000000 Z
12
+ dependencies:
13
+ - !ruby/object:Gem::Dependency
14
+ name: rails
15
+ requirement: !ruby/object:Gem::Requirement
16
+ requirements:
17
+ - - ">="
18
+ - !ruby/object:Gem::Version
19
+ version: 4.2.1
20
+ type: :runtime
21
+ prerelease: false
22
+ version_requirements: !ruby/object:Gem::Requirement
23
+ requirements:
24
+ - - ">="
25
+ - !ruby/object:Gem::Version
26
+ version: 4.2.1
27
+ - !ruby/object:Gem::Dependency
28
+ name: bundler
29
+ requirement: !ruby/object:Gem::Requirement
30
+ requirements:
31
+ - - ">="
32
+ - !ruby/object:Gem::Version
33
+ version: '1.10'
34
+ type: :development
35
+ prerelease: false
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: '1.10'
41
+ - !ruby/object:Gem::Dependency
42
+ name: rake
43
+ requirement: !ruby/object:Gem::Requirement
44
+ requirements:
45
+ - - ">="
46
+ - !ruby/object:Gem::Version
47
+ version: '10.0'
48
+ type: :development
49
+ prerelease: false
50
+ version_requirements: !ruby/object:Gem::Requirement
51
+ requirements:
52
+ - - ">="
53
+ - !ruby/object:Gem::Version
54
+ version: '10.0'
55
+ - !ruby/object:Gem::Dependency
56
+ name: rspec
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: shoulda-matchers
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: database_cleaner
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: generator_spec
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
+ - !ruby/object:Gem::Dependency
112
+ name: pry
113
+ requirement: !ruby/object:Gem::Requirement
114
+ requirements:
115
+ - - ">="
116
+ - !ruby/object:Gem::Version
117
+ version: '0'
118
+ type: :development
119
+ prerelease: false
120
+ version_requirements: !ruby/object:Gem::Requirement
121
+ requirements:
122
+ - - ">="
123
+ - !ruby/object:Gem::Version
124
+ version: '0'
125
+ - !ruby/object:Gem::Dependency
126
+ name: sqlite3
127
+ requirement: !ruby/object:Gem::Requirement
128
+ requirements:
129
+ - - ">="
130
+ - !ruby/object:Gem::Version
131
+ version: '0'
132
+ type: :development
133
+ prerelease: false
134
+ version_requirements: !ruby/object:Gem::Requirement
135
+ requirements:
136
+ - - ">="
137
+ - !ruby/object:Gem::Version
138
+ version: '0'
139
+ - !ruby/object:Gem::Dependency
140
+ name: codeclimate-test-reporter
141
+ requirement: !ruby/object:Gem::Requirement
142
+ requirements:
143
+ - - ">="
144
+ - !ruby/object:Gem::Version
145
+ version: '0'
146
+ type: :development
147
+ prerelease: false
148
+ version_requirements: !ruby/object:Gem::Requirement
149
+ requirements:
150
+ - - ">="
151
+ - !ruby/object:Gem::Version
152
+ version: '0'
153
+ description: ActiveVersioning serializes attributes when records are saved and allows
154
+ for version and draft management.
155
+ email:
156
+ - ryan.stenberg@viget.com
157
+ executables: []
158
+ extensions: []
159
+ extra_rdoc_files: []
160
+ files:
161
+ - ".gitignore"
162
+ - ".rspec"
163
+ - ".travis.yml"
164
+ - Gemfile
165
+ - README.md
166
+ - Rakefile
167
+ - active_versioning.gemspec
168
+ - bin/console
169
+ - bin/setup
170
+ - circle.yml
171
+ - lib/active_versioning.rb
172
+ - lib/active_versioning/errors.rb
173
+ - lib/active_versioning/errors/incompatible_version.rb
174
+ - lib/active_versioning/events.rb
175
+ - lib/active_versioning/model.rb
176
+ - lib/active_versioning/model/version_proxy.rb
177
+ - lib/active_versioning/model/versioned.rb
178
+ - lib/active_versioning/version.rb
179
+ - lib/active_versioning/version_manager.rb
180
+ - lib/generators/active_versioning_generator.rb
181
+ - lib/generators/templates/migrations/create_versions.rb
182
+ - lib/generators/templates/models/version.rb
183
+ homepage: https://github.com/vigetlabs/active_versioning
184
+ licenses:
185
+ - BSD
186
+ metadata: {}
187
+ post_install_message:
188
+ rdoc_options: []
189
+ require_paths:
190
+ - lib
191
+ required_ruby_version: !ruby/object:Gem::Requirement
192
+ requirements:
193
+ - - ">="
194
+ - !ruby/object:Gem::Version
195
+ version: '0'
196
+ required_rubygems_version: !ruby/object:Gem::Requirement
197
+ requirements:
198
+ - - ">="
199
+ - !ruby/object:Gem::Version
200
+ version: '0'
201
+ requirements: []
202
+ rubyforge_project:
203
+ rubygems_version: 2.4.5
204
+ signing_key:
205
+ specification_version: 4
206
+ summary: Plug-and-Play Versioning for Rails
207
+ test_files: []