harvixture 0.8.0

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.
data/License.txt ADDED
@@ -0,0 +1,20 @@
1
+ Copyright (c) 2008 Jeremy Friesen
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,50 @@
1
+ = harvixture
2
+
3
+ * FIX (url)
4
+
5
+ == DESCRIPTION:
6
+
7
+ Harvixture is a tool that can be used to extract data, in the form of fixtures,
8
+ from a Rails project. It is done by pointing the harvixture at a request_path
9
+ and dumping fixtures for all "found" ActiveRecord objects.
10
+
11
+ == SYNOPSIS:
12
+
13
+ $ cd path/to/rails/project
14
+ $ . harvixture run --request_path=/calendars/1 --output_dir=./bug_100 --rails_env=production
15
+ ./bug_100/users.yml
16
+ ./bug_100/calendars.yml
17
+
18
+ == REQUIREMENTS:
19
+
20
+ gem main, activerecord, mocha (for tests)
21
+ a Rails project
22
+
23
+ == INSTALL:
24
+
25
+ sudo gem install harvixture
26
+
27
+ == LICENSE:
28
+
29
+ (The MIT License)
30
+
31
+ Copyright (c) 2008 FIX
32
+
33
+ Permission is hereby granted, free of charge, to any person obtaining
34
+ a copy of this software and associated documentation files (the
35
+ 'Software'), to deal in the Software without restriction, including
36
+ without limitation the rights to use, copy, modify, merge, publish,
37
+ distribute, sublicense, and/or sell copies of the Software, and to
38
+ permit persons to whom the Software is furnished to do so, subject to
39
+ the following conditions:
40
+
41
+ The above copyright notice and this permission notice shall be
42
+ included in all copies or substantial portions of the Software.
43
+
44
+ THE SOFTWARE IS PROVIDED 'AS IS', WITHOUT WARRANTY OF ANY KIND,
45
+ EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
46
+ MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
47
+ IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY
48
+ CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
49
+ TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
50
+ SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
data/bin/harvixture ADDED
@@ -0,0 +1,83 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'date'
4
+ require 'rubygems'
5
+ require 'harvixture'
6
+ gem 'harvixture'
7
+ require 'harvixture/command'
8
+ gem 'main'
9
+ require 'main'
10
+
11
+ Main {
12
+ description <<-txt
13
+ Harvixture is a tool to help you capture fixtures from a system
14
+ txt
15
+
16
+ mode(:run) {
17
+ description <<-txt
18
+ Point harvixture to a URI and gather the fixtures.
19
+ txt
20
+ example <<-txt
21
+ ./harvixture --request_path=/calendars/1 --output_dir=./bug_100 --rails_env=production
22
+ txt
23
+ mixin :option_output_dir, :option_rails_env, :option_request_path, :option_user_id, :option_rails_root
24
+ run {
25
+ Harvixture::Command.process!(
26
+ :rails_root => rails_root,
27
+ :output_dir => output_dir,
28
+ :request_path => request_path,
29
+ :rails_env => rails_env,
30
+ :user_id => user_id
31
+ )
32
+ }
33
+ }
34
+
35
+ mixin :option_rails_root do
36
+ option(:r, :rails_root){
37
+ required
38
+ defaults './'
39
+ argument :required
40
+ desc 'path to rails root'
41
+ attr
42
+ }
43
+ end
44
+ mixin :option_output_dir do
45
+ option(:o,:output_dir){
46
+ required
47
+ defaults "./test/fixtures/scenario_for_#{Date.today.strftime('%Y_%m_%d')}"
48
+ argument :required
49
+ desc 'directory name where fixtures will be written'
50
+ attr
51
+ }
52
+ end
53
+
54
+ mixin :option_rails_env do
55
+ option(:e,:rails_env){
56
+ required
57
+ defaults 'production'
58
+ argument :required
59
+ desc 'script/server environment to use'
60
+ attr
61
+ }
62
+ end
63
+
64
+ mixin :option_request_path do
65
+ option(:p,:request_path){
66
+ required
67
+ argument :required
68
+ desc 'path to request from the script/server'
69
+ attr
70
+ }
71
+ end
72
+
73
+ mixin :option_user_id do
74
+ option(:u,:user_id){
75
+ argument :optional
76
+ desc 'authenticate with user_id'
77
+ attr
78
+ }
79
+ end
80
+
81
+ run{ help! }
82
+ }
83
+
data/lib/harvixture.rb ADDED
@@ -0,0 +1,13 @@
1
+ $:.unshift(File.dirname(__FILE__)) unless
2
+ $:.include?(File.dirname(__FILE__)) || $:.include?(File.expand_path(File.dirname(__FILE__)))
3
+
4
+ module Harvixture
5
+
6
+ end
7
+ require 'rubygems'
8
+ require 'activerecord'
9
+ require 'harvixture/config'
10
+ require 'harvixture/active_record_extension'
11
+ require 'harvixture/command'
12
+ require 'harvixture/model'
13
+ require 'harvixture/preparer'
@@ -0,0 +1,37 @@
1
+ module Harvixture
2
+ module ActiveRecordExtension
3
+ def after_find
4
+ harvixture_model.write_fixture
5
+ end
6
+ def to_harvixture
7
+ lines = attributes.to_yaml.split("\n")
8
+ lines.shift
9
+ "\n#{self.class.table_name}_#{self.id}:\n " + lines.join("\n ")
10
+ end
11
+
12
+ protected
13
+ def harvixture_model
14
+ @harvixture_model ||= Harvixture::Model.new(self)
15
+ end
16
+
17
+ end
18
+ end
19
+
20
+ ActiveRecord::Base.send(:include, Harvixture::ActiveRecordExtension) unless ActiveRecord::Base.included_modules.include?(Harvixture::ActiveRecordExtension)
21
+
22
+ class << ActiveRecord::Base
23
+ # Oh the trickery!
24
+ def method_added(method_name)
25
+ return true if @__adjusting_after_find
26
+ super
27
+ if method_name == :after_find
28
+ @__adjusting_after_find = true
29
+ after_find_method = self.instance_method(:after_find)
30
+ define_method(:after_find) do
31
+ super
32
+ after_find_method.bind(self).call
33
+ end
34
+ @__adjusting_after_find = false
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,37 @@
1
+ require 'open-uri'
2
+ module Harvixture
3
+ module Command
4
+ class << self
5
+ # :rails_root
6
+ # :output_dir
7
+ # :request_path
8
+ # :rails_env
9
+ # :user_id
10
+ def process!(options={})
11
+ process = nil
12
+ Preparer.do_it!(options[:rails_root])
13
+ Config.update(options)
14
+ process = Process.fork do
15
+ Signal.trap('HUP') { exit }
16
+ stdin = open '/dev/null', 'r'
17
+ stdout = open '/dev/null', 'w'
18
+ stderr = open '/dev/null', 'w'
19
+ STDIN.reopen stdin
20
+ STDOUT.reopen stdout
21
+ STDERR.reopen stderr
22
+ exec %(ruby script/server -e harvixture -p 8675)
23
+ end
24
+ # Wait for the script server to reload
25
+ sleep(5)
26
+ open(File.join('http://localhost:8675', Config.request_path))
27
+ rescue Exception => e
28
+ puts e
29
+ puts e.backtrace
30
+ ensure
31
+ Process.kill('HUP', process) if process
32
+ Process.wait
33
+ Process.exit!
34
+ end
35
+ end
36
+ end
37
+ end
@@ -0,0 +1,59 @@
1
+ module Harvixture
2
+ class Config
3
+ class << self
4
+ def rails_env
5
+ values['rails_env']
6
+ end
7
+ def request_path
8
+ values['request_path']
9
+ end
10
+ def output_dir
11
+ values['output_dir']
12
+ end
13
+ def user_id
14
+ values['user_id']
15
+ end
16
+
17
+ def update(attributes = {})
18
+ new_values = {
19
+ 'output_dir' => attributes[:output_dir] || attributes['output_dir'] || output_dir,
20
+ 'rails_env' => attributes[:rails_env] || attributes['rails_env'] || rails_env,
21
+ 'request_path' => attributes[:request_path] || attributes['request_path'] || request_path,
22
+ 'user_id' => attributes[:user_id] || attributes['user_id'] || user_id,
23
+ }
24
+ File.open(filename, 'w+') {|f| f.puts YAML.dump(new_values)}
25
+ Dir.glob(File.join(output_dir, '*.yml')).each {|f| File.delete(f) if File.exist?(f)}
26
+ @values = nil
27
+ values
28
+ end
29
+
30
+ def filename
31
+ File.join(home, '.harvixture_config.yml')
32
+ end
33
+
34
+ protected
35
+ def home
36
+ ENV['HOME'] || ENV['USERPROFILE'] || ENV['HOMEPATH']
37
+ end
38
+ def values
39
+ return @values if @values
40
+ begin
41
+ @values = YAML::load(open(filename)) || write_template
42
+ rescue
43
+ @values = write_template
44
+ end
45
+
46
+ @values
47
+ end
48
+
49
+ def write_template
50
+ open(filename,'w').write(template)
51
+ YAML::load open(filename)
52
+ end
53
+
54
+ def template
55
+ %(---\n output_dir: ./test/fixtures/harvixture_scenario\n user_id: \n rails_env: production\n request_path: )
56
+ end
57
+ end
58
+ end
59
+ end
@@ -0,0 +1,21 @@
1
+ require 'fileutils'
2
+ module Harvixture
3
+ class Model
4
+ attr_reader :object
5
+ def initialize(object)
6
+ @object = object
7
+ end
8
+
9
+ def write_fixture
10
+ FileUtils.mkdir_p(File.dirname(filename))
11
+ File.open(filename, 'w+') { |file| file.print '---' } unless File.exist?(filename)
12
+ File.open(filename, 'a+') do |file|
13
+ file.puts object.to_harvixture
14
+ end
15
+ end
16
+
17
+ def filename
18
+ File.join(RAILS_ROOT, Config.output_dir, "#{object.class.table_name}.yml")
19
+ end
20
+ end
21
+ end
@@ -0,0 +1,39 @@
1
+ module Harvixture
2
+ class Preparer
3
+ class << self
4
+
5
+ # Install the necessary files on the rails project
6
+ def do_it!(rails_root)
7
+ self.new(rails_root)
8
+ end
9
+ end
10
+ attr_reader :rails_root
11
+ def initialize(rails_root)
12
+ @rails_root = rails_root
13
+ create_environment_harvixture
14
+ update_database_yml
15
+ end
16
+
17
+ protected
18
+
19
+ def create_environment_harvixture
20
+ filename = File.join(rails_root, 'config', 'environments', 'harvixture.rb')
21
+ return if File.exist?(filename)
22
+ File.open(filename, 'w+') do |file|
23
+ file.puts '#START DO NOT MODIFY'
24
+ file.puts 'require "harvixture"'
25
+ file.puts '"#{File.read(File.join(File.dirname(__FILE__), "#{Harvixture::Config.rails_env}.rb"))}"'
26
+ file.puts '#END DO NOT MODIFY'
27
+ end
28
+ end
29
+ def update_database_yml
30
+ config = File.read(File.join(rails_root, 'config', 'database.yml'))
31
+ return if config.match(/^harvixture:/)
32
+ puts 'updating database.yml'
33
+ config.gsub!(/^(\w*): *$/, '\1: &\1')
34
+ File.open(File.join(rails_root, 'config', 'database.yml'), 'w+') do |file|
35
+ file.puts "#{config}\n\nharvixture:\n <<: *<%= Harvixture::Config.rails_env rescue 'production' %>"
36
+ end
37
+ end
38
+ end
39
+ end
@@ -0,0 +1,43 @@
1
+ require File.dirname(__FILE__) + '/test_helper'
2
+ class Harvixture::ActiveRecordExtensionTest < Test::Unit::TestCase
3
+ class AbstractUnit < ActiveRecord::Base
4
+ def self.columns; []; end
5
+ def attributes
6
+ {'name' => 'my name', 'id' => id }
7
+ end
8
+ def id; 8675309; end
9
+ end
10
+
11
+ class AbstractUnitWithAfterFind < AbstractUnit
12
+ def after_find
13
+ @after_find_called = true
14
+ end
15
+ def after_find_called?
16
+ @after_find_called
17
+ end
18
+ end
19
+
20
+ def test_after_find_with_inheritance
21
+ abstract_unit = AbstractUnitWithAfterFind.new
22
+ abstract_unit.send(:harvixture_model).expects(:write_fixture)
23
+ abstract_unit.after_find
24
+ end
25
+
26
+ def test_after_find_with_inheritance_calls_defined_inheritance_model
27
+ abstract_unit = AbstractUnitWithAfterFind.new
28
+ abstract_unit.send(:harvixture_model).stubs(:write_fixture)
29
+ abstract_unit.after_find
30
+ assert abstract_unit.after_find_called?
31
+ end
32
+
33
+ def test_after_find_should_write_to_the_harvixture_model
34
+ abstract_unit = AbstractUnit.new
35
+ abstract_unit.send(:harvixture_model).expects(:write_fixture).returns(:expected_value)
36
+ abstract_unit.after_find
37
+ end
38
+
39
+ def test_to_harvixture
40
+ abstract_unit = AbstractUnit.new
41
+ assert_equal abstract_unit.to_harvixture, "\nabstract_units_8675309:\n name: my name\n id: 8675309"
42
+ end
43
+ end
@@ -0,0 +1,30 @@
1
+ require File.dirname(__FILE__) + '/test_helper'
2
+
3
+ class Harvixture::ModelTest < Test::Unit::TestCase
4
+ class AbstractModel
5
+ class << self
6
+ def table_name
7
+ 'abstract_models'
8
+ end
9
+ end
10
+ def to_harvixture
11
+ %(
12
+ abstract_model_1:
13
+ name: hello)
14
+ end
15
+ end
16
+ def test_fixtures
17
+ @harvixture_model = Harvixture::Model.new(mock_model)
18
+ def @harvixture_model.filename
19
+ File.join(File.dirname(__FILE__), 'tmp.yml')
20
+ end
21
+ @harvixture_model.write_fixture
22
+ assert YAML.load(File.read(@harvixture_model.filename))['abstract_model_1']
23
+ ensure
24
+ FIle.delete(File.dirname(__FILE__), 'tmp.yml') rescue true
25
+ end
26
+
27
+ def mock_model
28
+ @abstract_model ||= AbstractModel.new
29
+ end
30
+ end
@@ -0,0 +1,3 @@
1
+ require 'test/unit'
2
+ require File.dirname(__FILE__) + '/../lib/harvixture'
3
+ require 'mocha'
metadata ADDED
@@ -0,0 +1,93 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: harvixture
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.8.0
5
+ platform: ruby
6
+ authors:
7
+ - Jeremy Friesen
8
+ autorequire:
9
+ bindir: bin
10
+ cert_chain: []
11
+
12
+ date: 2008-04-28 00:00:00 -04:00
13
+ default_executable:
14
+ dependencies:
15
+ - !ruby/object:Gem::Dependency
16
+ name: main
17
+ version_requirement:
18
+ version_requirements: !ruby/object:Gem::Requirement
19
+ requirements:
20
+ - - ">="
21
+ - !ruby/object:Gem::Version
22
+ version: 2.8.0
23
+ version:
24
+ - !ruby/object:Gem::Dependency
25
+ name: activerecord
26
+ version_requirement:
27
+ version_requirements: !ruby/object:Gem::Requirement
28
+ requirements:
29
+ - - ">="
30
+ - !ruby/object:Gem::Version
31
+ version: 2.0.0
32
+ version:
33
+ - !ruby/object:Gem::Dependency
34
+ name: mocha
35
+ version_requirement:
36
+ version_requirements: !ruby/object:Gem::Requirement
37
+ requirements:
38
+ - - ">="
39
+ - !ruby/object:Gem::Version
40
+ version: 0.5.6
41
+ version:
42
+ description: Harvixture is a tool that can be used to extract data, in the form of fixtures, from a Rails project. It is done by pointing the harvixture at a request_path and dumping fixtures for all "found" ActiveRecord objects.
43
+ email: jeremyf@lightsky.com
44
+ executables:
45
+ - harvixture
46
+ extensions: []
47
+
48
+ extra_rdoc_files:
49
+ - README
50
+ files:
51
+ - lib/harvixture/active_record_extension.rb
52
+ - lib/harvixture/command.rb
53
+ - lib/harvixture/config.rb
54
+ - lib/harvixture/model.rb
55
+ - lib/harvixture/preparer.rb
56
+ - lib/harvixture.rb
57
+ - bin/harvixture
58
+ - test/test_harvixture_active_record_extension.rb
59
+ - test/test_harvixture_model.rb
60
+ - test/test_helper.rb
61
+ - README
62
+ - License.txt
63
+ has_rdoc: true
64
+ homepage: http://github.com/jeremyf/harvixture
65
+ post_install_message:
66
+ rdoc_options:
67
+ - --main
68
+ - README
69
+ require_paths:
70
+ - lib
71
+ required_ruby_version: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: "0"
76
+ version:
77
+ required_rubygems_version: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - ">="
80
+ - !ruby/object:Gem::Version
81
+ version: "0"
82
+ version:
83
+ requirements: []
84
+
85
+ rubyforge_project:
86
+ rubygems_version: 1.0.1
87
+ signing_key:
88
+ specification_version: 2
89
+ summary: A tool for harvesting fixtures from production data
90
+ test_files:
91
+ - test/test_harvixture_active_record_extension.rb
92
+ - test/test_harvixture_model.rb
93
+ - test/test_helper.rb