stuff_arc 0.0.3

Sign up to get free protection for your applications and to get access to all the features.
data/Gemfile ADDED
@@ -0,0 +1,5 @@
1
+ gem 'rake'
2
+ gem 'i18n'
3
+ gem 'rails', "~> 3.1.0"
4
+
5
+ gem 'pry'
data/LICENSE ADDED
@@ -0,0 +1 @@
1
+ include LGPL 3
data/README.md ADDED
@@ -0,0 +1,77 @@
1
+ # stuff_arc - supports Rails portable data dump and restore
2
+
3
+ ## Version 0.0.2
4
+
5
+ stuff_arc adds class level archiving and unarchiving of an ActiveRecord object
6
+ a Rails app.
7
+
8
+ Archives are JSON data, one line per model instance with the 'id' value omitted so that
9
+ the data can be restored w/o worrying about primary key clashes.
10
+
11
+ Restoration is performed by instantiating the model and then calling save!. **save!** exceptions
12
+ are trapped and generate simple error messages, thus Rails validations can be used to avoid
13
+ data duplication and data clobbering.
14
+
15
+ These methods are designed to be used in a Rails Console, not programatically.
16
+
17
+ ## Install
18
+
19
+ gem install stuff_arc
20
+
21
+ ## Usage
22
+
23
+ Include into models in which you want to create archives.
24
+
25
+ app/models/foo.rb:
26
+
27
+ require 'stuff_arc'
28
+
29
+ class Foo < ActiveRecord::Base
30
+ include StuffArc
31
+
32
+ . . .
33
+ end
34
+
35
+ This will add two class methods to Foo:
36
+
37
+ * Foo.archive(options = {}) - which will create the file 'foos.json' containing JSON serializations
38
+ of every record retrieved by Foo.all with the 'id' entry is excluded.
39
+ * Foo.unarchive(options = {}) - which reads the file 'foos.json', decodes each record and attempts
40
+ to save! them to the database.
41
+
42
+ The options are:
43
+
44
+ * :fname - name of archive file. Defaults to the _underscored_, _pluralized_ version of the
45
+ class name with the '.json' suffix.
46
+ * :lib\_dir - path to directory archives are placed/looked for in. **NOTE:** :lib\_dir is ignored if
47
+ :fname is an absolute path. Defaults to:
48
+
49
+ &lt;app root&gt;/lib/stuff\_arc - if Rails.public\_path is defined
50
+
51
+ '.' - if Rails.public\_path is not defined
52
+
53
+
54
+ This creates a portable dump and restore facility for each model in which StuffArc is
55
+ included.
56
+
57
+ ## Creating an Archive
58
+
59
+ Fire up the rails console [rails c] and . . .
60
+
61
+ Create an archive in the default directory with default name:
62
+
63
+ Foo.archive
64
+
65
+ Create an archive in the default directory with a different name
66
+
67
+ Foo.archive :fname => 'foobar'
68
+
69
+ Create an archive in a specified directory with the default name
70
+
71
+ Foo.archive :lib_dir => '/tmp'
72
+
73
+ ## Restoring an Archive
74
+
75
+ Fire up the rails console [rails c] and . . .
76
+
77
+ repeat one of the commands above using **Foo.unarchive** instead of *Foo.archive*
data/Rakefile ADDED
@@ -0,0 +1,42 @@
1
+ require 'rake'
2
+
3
+ gem_name = 'stuff_arc'
4
+
5
+ # snarf gemspec and set version
6
+ gem_spec = eval File.new("#{gem_name}.gemspec").read
7
+ gem_version = gem_spec.version.to_s
8
+
9
+ gem_zip = "#{gem_name}_#{gem_version}.zip"
10
+ gem_tgz = "#{gem_name}_#{gem_version}.tgz"
11
+
12
+ task :default => :test
13
+
14
+ desc "Run unit tests"
15
+ task :test do
16
+ system 'ruby tests/*'
17
+ # require "./test/#{gem_name}_base_test"
18
+ end
19
+
20
+ desc "run rdoc to create doc"
21
+ task :doc do
22
+ system 'rdoc'
23
+ end
24
+
25
+ desc "build gem"
26
+ task :gem do
27
+ system "gem build #{gem_name}.gemspec"
28
+ if 'mike.local' == IO.popen('hostname').read.chomp
29
+ system "cp #{gem_name}-#{gem_version}.gem ~/Rails/GemCache/gems/"
30
+ system "(cd ~/Rails/GemCache ; gem generate_index -d . )"
31
+ end
32
+ end
33
+
34
+ desc "push to github"
35
+ task :git_push do
36
+ system 'git push'
37
+ end
38
+
39
+ desc "push to rubygems"
40
+ task :gem_push => :gem do
41
+ system "gem push #{gem_name}-#{gem_version}.gem"
42
+ end
data/lib/stuff_arc.rb ADDED
@@ -0,0 +1,89 @@
1
+ # StuffArc - supports portable Rails databases dump and restore
2
+ #
3
+ # defines two class level methods for archiving and unarchiving ActiveRecord::Base
4
+ # objects.
5
+ #
6
+ # archive - creates an archive named <class.underscore>.json containing JSON representations
7
+ # of each instance of the model
8
+ #
9
+ # unarchive - which reads a file created by **archive** (named <class.underscore>.json) and
10
+ # saves each record in the datbase.
11
+ #
12
+ # Both methods are designed to be run from a Rails Console - not programatically.
13
+
14
+ require 'rails'
15
+ # require 'pry'
16
+ # require 'active_support'
17
+ # require 'active_support/inflector'
18
+ # require 'active_support/json'
19
+
20
+ module StuffArc
21
+ VERSION = "0.0.3"
22
+
23
+ def self.included(mod)
24
+ mod_lowercase = mod.to_s.underscore.pluralize
25
+ tmp =<<-EOF
26
+ def self.archive options = {}
27
+ unless (lib_dir = options.delete(:lib_dir))
28
+ if Rails.public_path
29
+ lib_dir = File.join( File.dirname(::Rails.public_path), 'lib', 'stuff_arc' )
30
+ Dir.mkdir(lib_dir) unless File.exists? lib_dir
31
+ else
32
+ lib_dir = '.'
33
+ end
34
+ end
35
+ fname = options.delete(:fname) || '#{mod_lowercase}.json'
36
+ fname = File.join(lib_dir, fname) unless fname[0] == File::SEPARATOR
37
+
38
+ if File.exists? fname
39
+ back_name = fname + '~'
40
+ File.unlink back_name if File.exists? back_name
41
+ File.rename fname, back_name
42
+ end
43
+ f = File.open(fname, 'w')
44
+ list = self.all
45
+ list.each do |#{mod_lowercase}|
46
+ json_str = ActiveSupport::JSON.encode #{mod_lowercase}, :include_root_in_json => false, :except => :id
47
+ f.write json_str + "\n"
48
+ end
49
+ f.close
50
+ list.length
51
+ end
52
+ EOF
53
+
54
+ mod.instance_eval tmp, __FILE__, __LINE__
55
+
56
+ tmp =<<-EOF
57
+ def self.unarchive options = {}
58
+ unless (lib_dir = options.delete(:lib_dir))
59
+ if Rails.public_path
60
+ lib_dir = File.join( File.dirname(::Rails.public_path), 'lib', 'stuff_arc' )
61
+ Dir.mkdir(lib_dir) unless File.exists? lib_dir
62
+ else
63
+ lib_dir = '.'
64
+ end
65
+ end
66
+ fname = options.delete(:fname) || '#{mod_lowercase}.json'
67
+ fname = File.join(lib_dir, fname) unless fname[0] == File::SEPARATOR
68
+
69
+ return nil unless File.exists? fname
70
+
71
+ f = File.new fname
72
+
73
+ f.lines do |line|
74
+ #{mod_lowercase} = self.new Hash[ActiveSupport::JSON.decode(line).map { |k,v| [k.to_sym, v] }]
75
+ begin
76
+ #{mod_lowercase}.save!
77
+ rescue Exception => e
78
+ puts "exception unarchiving #{mod_lowercase}: \#{e}\n"
79
+ end
80
+ end
81
+
82
+ f.close
83
+ end
84
+ EOF
85
+
86
+ mod.instance_eval tmp, __FILE__, __LINE__
87
+
88
+ end
89
+ end
@@ -0,0 +1,86 @@
1
+ $LOAD_PATH << File.expand_path("../../lib", __FILE__)
2
+ require 'test/unit'
3
+ require 'stuff_arc'
4
+ # require 'active_model'
5
+
6
+ class StuffArcHelper
7
+ include StuffArc
8
+
9
+ class <<self
10
+ attr_accessor :db
11
+
12
+ def init_db
13
+ self.db = []
14
+ end
15
+ end
16
+
17
+ attr_accessor :foo, :bar
18
+
19
+ def initialize args = nil
20
+ unless args.nil?
21
+ self.foo = args[:foo] if args[:foo]
22
+ self.bar = args[:bar] if args[:bar]
23
+ end
24
+ end
25
+
26
+ def ==(other)
27
+ self.foo == other.foo && self.bar == other.bar
28
+ end
29
+
30
+ def self.all
31
+ [self.new({foo: 'foo', bar: 'bar'}), self.new({foo: 'foo2', bar: 'bar2'})]
32
+ end
33
+
34
+ def save!
35
+ StuffArcHelper.db << self
36
+ end
37
+ end
38
+
39
+ class StuffArcTest < Test::Unit::TestCase
40
+ # def setup
41
+ # puts "StuffArcHelper.public_methods: #{StuffArcHelper.public_methods.grep /arc/}"
42
+ # end
43
+
44
+ def teardown
45
+ fname = StuffArcHelper.to_s.underscore.pluralize + '.json'
46
+ [fname, fname + '~'].each do |fn|
47
+ File.unlink(fn) if File.exists? fn
48
+ end
49
+ end
50
+
51
+ def test_methods_exist
52
+ assert StuffArcHelper.respond_to?(:archive), "StuffArcHelper has class method :archive"
53
+ assert StuffArcHelper.respond_to?(:unarchive), "StuffArcHelper has class method :unarchive"
54
+ end
55
+
56
+ def test_creates_archive
57
+ StuffArcHelper.archive
58
+ fname = StuffArcHelper.to_s.underscore
59
+ assert_equal 'stuff_arc_helper', fname, "underscore should transform class name correctly"
60
+ assert File.exists?('stuff_arc_helpers.json'), "archive creates a file"
61
+ end
62
+
63
+ def test_reads_archive
64
+ StuffArcHelper.archive
65
+ StuffArcHelper.init_db
66
+ assert_equal [], StuffArcHelper.db, "StuffArcHelper.init_db should empty db"
67
+ StuffArcHelper.unarchive
68
+ assert_equal StuffArcHelper.all, StuffArcHelper.db, "Unarchiving should fill db"
69
+ end
70
+
71
+ def test_full_path_to_archive
72
+ path = File.join(Dir.pwd, 'path-to-archive')
73
+ Dir.mkdir(path) unless File.exists? path
74
+ StuffArcHelper.archive :lib_dir => path
75
+ assert File.exists?(File.join(path, 'stuff_arc_helpers.json')), "archive should be in #{path}"
76
+ File.unlink File.join(path, 'stuff_arc_helpers.json') if File.exists? File.join(path, 'stuff_arc_helpers.json')
77
+ Dir.rmdir path if File.exists? path
78
+ end
79
+
80
+ def test_fname_override
81
+ fname = 'foo-stuff'
82
+ StuffArcHelper.archive :fname => fname
83
+ assert File.exists?(fname), "file #{fname} should exist"
84
+ File.unlink(fname) if File.exists? fname
85
+ end
86
+ end
metadata ADDED
@@ -0,0 +1,63 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: stuff_arc
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.0.3
5
+ prerelease:
6
+ platform: ruby
7
+ authors:
8
+ - Mike Howard
9
+ autorequire:
10
+ bindir: bin
11
+ cert_chain: []
12
+ date: 2011-09-07 00:00:00.000000000Z
13
+ dependencies:
14
+ - !ruby/object:Gem::Dependency
15
+ name: activesupport
16
+ requirement: &2166654720 !ruby/object:Gem::Requirement
17
+ none: false
18
+ requirements:
19
+ - - ! '>='
20
+ - !ruby/object:Gem::Version
21
+ version: '0'
22
+ type: :runtime
23
+ prerelease: false
24
+ version_requirements: *2166654720
25
+ description: stuff_arc - adds class level archiving/unarchiving to ActiveRecord::Base
26
+ children
27
+ email: mike@clove.com
28
+ executables: []
29
+ extensions: []
30
+ extra_rdoc_files: []
31
+ files:
32
+ - lib/stuff_arc.rb
33
+ - tests/stuff_arc_test.rb
34
+ - LICENSE
35
+ - Rakefile
36
+ - README.md
37
+ - Gemfile
38
+ homepage: http://github.com/mikehoward/stuff_arc
39
+ licenses: []
40
+ post_install_message:
41
+ rdoc_options: []
42
+ require_paths:
43
+ - lib
44
+ required_ruby_version: !ruby/object:Gem::Requirement
45
+ none: false
46
+ requirements:
47
+ - - ! '>='
48
+ - !ruby/object:Gem::Version
49
+ version: '0'
50
+ required_rubygems_version: !ruby/object:Gem::Requirement
51
+ none: false
52
+ requirements:
53
+ - - ! '>='
54
+ - !ruby/object:Gem::Version
55
+ version: '0'
56
+ requirements: []
57
+ rubyforge_project:
58
+ rubygems_version: 1.8.6
59
+ signing_key:
60
+ specification_version: 3
61
+ summary: stuff_arc - adds class level archiving/unarchiving to ActiveRecord::Base
62
+ children
63
+ test_files: []