reflection 0.0.2 → 0.3.1

Sign up to get free protection for your applications and to get access to all the features.
data/Reflection.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{reflection}
8
- s.version = "0.0.2"
8
+ s.version = "0.3.1"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["Andreas Wolff"]
12
- s.date = %q{2009-11-15}
12
+ s.date = %q{2009-11-17}
13
13
  s.default_executable = %q{reflection}
14
14
  s.description = %q{
15
15
  Reflection is designed to keep your production assets (database comming soon) in sync with your development system.
@@ -38,6 +38,7 @@ Gem::Specification.new do |s|
38
38
  "lib/reflection/command/apply.rb",
39
39
  "lib/reflection/command/base.rb",
40
40
  "lib/reflection/command/stash.rb",
41
+ "lib/reflection/config.rb",
41
42
  "lib/reflection/directory.rb",
42
43
  "lib/reflection/directory/base.rb",
43
44
  "lib/reflection/directory/stash.rb",
@@ -48,6 +49,7 @@ Gem::Specification.new do |s|
48
49
  "lib/reflection/validations.rb",
49
50
  "spec/reflection/cli_spec.rb",
50
51
  "spec/reflection/command/stash_spec.rb",
52
+ "spec/reflection/config_spec.rb",
51
53
  "spec/reflection/directory/base_spec.rb",
52
54
  "spec/reflection/directory/stash_spec.rb",
53
55
  "spec/reflection/repository_spec.rb",
@@ -65,6 +67,7 @@ Gem::Specification.new do |s|
65
67
  s.test_files = [
66
68
  "spec/reflection/cli_spec.rb",
67
69
  "spec/reflection/command/stash_spec.rb",
70
+ "spec/reflection/config_spec.rb",
68
71
  "spec/reflection/directory/base_spec.rb",
69
72
  "spec/reflection/directory/stash_spec.rb",
70
73
  "spec/reflection/repository_spec.rb",
data/TODO CHANGED
@@ -1,7 +1,9 @@
1
+ + Add config files ('$ reflection path/to/config')
1
2
  + Add DB Dumper (include in cli-opt-parser)
2
3
  + Remove stash directory if its empty (on reinit)
3
4
  + Add Logger (Reflection::Support.log)
4
5
  + After command callbacks: Twitter, Campfire on Serverside
5
6
  + List existing reflections in client side
6
7
  + Allow to apply any (git) version, not just the latest
7
- + Allow collection of assets from Akamai and/or CloudFront
8
+ + Add cli option use tmp-apply (removes ~/.reflection/apply-dir after command)
9
+ + Allow collection of assets from Akamai and/or CloudFront (hm.. does that make sense?)
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.0.2
1
+ 0.3.1
data/lib/reflection.rb CHANGED
@@ -2,6 +2,7 @@ require 'rubygems'
2
2
 
3
3
  module Reflection
4
4
  autoload :CLI, 'reflection/cli'
5
+ autoload :Config, 'reflection/config'
5
6
  autoload :Command, 'reflection/command'
6
7
  autoload :Directory, 'reflection/directory'
7
8
  autoload :Repository, 'reflection/repository'
@@ -1,64 +1,29 @@
1
- require 'optparse'
2
- require 'ostruct'
3
-
4
1
  module Reflection
5
2
  module CLI
6
3
  class << self
7
4
 
8
5
  def run!(args = nil)
9
- options = parse_options(args)
10
- if options == false
6
+ config = Reflection::Config.parse(args)
7
+
8
+ if verify_config(config) == false
11
9
  Reflection::Support.exit_with_error("Ahh ja, missing arguments. Please read 'reflection --help' to get a feeling of how it works.")
12
10
  else
13
- case options.command
14
- when :apply
15
- Reflection::Command::Apply.run!(options)
16
- when :stash
17
- Reflection::Command::Stash.run!(options)
18
- else
19
- Reflection::Support.exit_with_error("Couldn't identify command. Please run 'reflection --help'.")
20
- end
21
- end
22
- end
23
-
24
- def parse_options(args)
25
- options = OpenStruct.new
26
-
27
- opt_parser = OptionParser.new do |opts|
28
- opts.banner = "Usage: reflection --COMMAND --repository=GIT_REPO --directory=PATH"
29
-
30
- opts.separator " "
31
- opts.separator "On the server side:"
32
-
33
- opts.on("-s", "--stash", "Store your assets and/or a database dump in a git-repository.") do |stash|
34
- options.command = :stash
35
- end
36
-
37
- opts.separator "On the client side:"
38
- opts.on("-a", "--apply", "Apply assets and/or a database dump loaded from a git-repository.") do |apply|
39
- options.command = :apply
40
- end
41
-
42
- opts.separator " "
43
- opts.separator "Required options for both:"
44
- opts.on("-r", "--repository GIT_URL", "A Git repository(url) to be used as storage") do |repository|
45
- options.repository = repository
46
- end
47
-
48
- opts.on("-d", "--directory PATH", "Path to your asset directory") do |directory|
49
- options.directory = directory
11
+ case config.command
12
+ when :apply
13
+ Reflection::Command::Apply.run!(config)
14
+ when :stash
15
+ Reflection::Command::Stash.run!(config)
16
+ else
17
+ Reflection::Support.exit_with_error("Couldn't identify command. Please run 'reflection --help'.")
50
18
  end
51
19
  end
52
-
53
- opt_parser.parse!(args)
54
- verify_options(options)
55
20
  end
56
21
 
57
22
 
58
23
  private
59
24
 
60
- def verify_options(options)
61
- return ([:stash, :apply].include?(options.command) && !options.repository.nil? && !options.directory.nil?) ? options : false
25
+ def verify_config(config)
26
+ return ([:stash, :apply].include?(config.command) && !config.repository.nil? && !config.directory.nil?) ? config : false
62
27
  end
63
28
  end
64
29
  end
@@ -0,0 +1,99 @@
1
+ require 'optparse'
2
+ require 'ostruct'
3
+ require 'yaml'
4
+
5
+ module Reflection
6
+
7
+ class ConfigArgumentError < StandardError; end
8
+
9
+ class Config
10
+
11
+ attr_accessor :command
12
+ attr_accessor :directory
13
+ attr_accessor :repository
14
+ attr_accessor :store_configuration_path
15
+
16
+ def self.parse(args = [])
17
+ config = Config.new
18
+ case
19
+ when !args.empty? && File.exists?(args.first)
20
+ config.read!(args.first)
21
+ when !args.empty?
22
+ config.parse_command_line_options(args)
23
+ config.write(config.store_configuration_path) if config.store_configuration_path
24
+ else
25
+ config.read!(File.join(Dir.pwd, 'reflection.yml'))
26
+ end
27
+ config
28
+ end
29
+
30
+ def to_hash
31
+ { :command => self.command, :repository => self.repository, :directory => self.directory }
32
+ end
33
+
34
+ def from_hash(hash)
35
+ self.command = hash[:command]
36
+ self.directory = hash[:directory]
37
+ self.repository = hash[:repository]
38
+ end
39
+
40
+ def write(path)
41
+ begin
42
+ io = File.open(path, 'w')
43
+ YAML.dump(self.to_hash, io)
44
+ io.close
45
+ rescue => e
46
+ Reflection::Support.exit_with_error("Writing of config file to '#{path}' failed: #{e.message}")
47
+ end
48
+ end
49
+
50
+ def read!(path)
51
+ begin
52
+ if File.exist?(path)
53
+ options = YAML.load_file(path)
54
+ raise(Reflection::ConfigArgumentError, "Config file is invalid.") unless options.is_a?(Hash)
55
+ self.from_hash(options)
56
+ end
57
+ rescue => e
58
+ Reflection::Support.exit_with_error("Parsing of config file '#{path}' failed: #{e.message}")
59
+ end
60
+ end
61
+
62
+ def parse_command_line_options(args)
63
+ opt_parser = OptionParser.new do |opts|
64
+ opts.banner = "Usage: reflection --COMMAND --repository=GIT_REPO --directory=PATH"
65
+
66
+ opts.separator " "
67
+ opts.separator "On the server side:"
68
+
69
+ opts.on("-s", "--stash", "Store your assets and/or a database dump in a git-repository.") do |stash|
70
+ self.command = :stash
71
+ end
72
+
73
+ opts.separator "On the client side:"
74
+ opts.on("-a", "--apply", "Apply assets and/or a database dump loaded from a git-repository.") do |apply|
75
+ self.command = :apply
76
+ end
77
+
78
+ opts.separator " "
79
+ opts.separator "Required options for both:"
80
+ opts.on("-r", "--repository GIT_URL", "A Git repository(url) to be used as storage") do |repository|
81
+ self.repository = repository
82
+ end
83
+
84
+ opts.on("-d", "--directory PATH", "Path to your asset directory") do |directory|
85
+ self.directory = directory
86
+ end
87
+
88
+ opts.separator " "
89
+ opts.separator "Additional options for both:"
90
+ opts.on("--write [FILE]", "Create a configuration FILE from the current commandline options") do |config_file_path|
91
+ self.store_configuration_path = config_file_path if config_file_path
92
+ end
93
+ end
94
+
95
+ opt_parser.parse!(args)
96
+ end
97
+
98
+ end
99
+ end
@@ -6,33 +6,34 @@ describe Reflection::CLI do
6
6
  end
7
7
 
8
8
  describe '#run!' do
9
- it 'should parse commandline options' do
9
+ before(:each) do
10
+ @config = mock('Reflection::Config', :command => :stash)
11
+ Reflection::Config.stub!(:parse).and_return(@config)
12
+ @subject.stub!(:verify_config).and_return(true)
13
+ end
14
+
15
+ it 'should create a config object, holding the parsed commandline options' do
16
+ Reflection::Config.should_receive(:parse).with("args").and_return(@config)
10
17
  Reflection::Command::Stash.stub!(:run!)
11
- @subject.should_receive(:parse_options).and_return(OpenStruct.new(:command => :stash))
12
- @subject.run!
18
+ @subject.run!("args")
13
19
  end
14
20
 
15
- it 'should fail gracefully displaying a message if parse_options returns false' do
21
+ it 'should verify the config and fail gracefully displaying a message if verification fails' do
16
22
  Reflection::Support.should_receive(:exit_with_error).with(/reflection --help/)
17
- @subject.stub!(:parse_options).and_return(false)
18
- @subject.run!
23
+ @subject.stub!(:verify_config).and_return(false)
24
+ @subject.run!("args")
19
25
  end
20
26
 
21
- context 'successful parsed options' do
22
- before(:each) do
23
- @parse_options = OpenStruct.new(:options => "more")
24
- @subject.stub!(:parse_options).and_return(@parse_options)
25
- end
26
-
27
+ context 'successfully parsed options' do
27
28
  it 'should call the Stash command if parse_options returned succesfull with command :stash' do
28
- @parse_options.command = :stash
29
- Reflection::Command::Stash.should_receive(:run!).with(@parse_options)
29
+ Reflection::Command::Stash.should_receive(:run!).with(@config)
30
+ @config.stub!(:command).and_return(:stash)
30
31
  @subject.run!
31
32
  end
32
33
 
33
34
  it 'should call the Apply command if parse_options returned succesfull with command :apply' do
34
- @parse_options.command = :apply
35
- Reflection::Command::Apply.should_receive(:run!).with(@parse_options)
35
+ Reflection::Command::Apply.should_receive(:run!).with(@config)
36
+ @config.stub!(:command).and_return(:apply)
36
37
  @subject.run!
37
38
  end
38
39
  end
@@ -0,0 +1,110 @@
1
+ require File.dirname(__FILE__) + '/../spec_helper'
2
+
3
+ describe Reflection::Config do
4
+ before(:each) do
5
+ @valid_options = { :command => :stash, :repository => 'repo', :directory => 'dir' }
6
+ end
7
+
8
+ describe 'parse' do
9
+ before(:each) do
10
+ @mock_config = mock('Reflection::Config', :store_configuration_path => nil)
11
+ Reflection::Config.stub!(:new).and_return(@mock_config)
12
+ end
13
+
14
+ it 'should parse a yaml file if the first arg is an existing file' do
15
+ @mock_config.should_receive(:read!).with('/tmp')
16
+ Reflection::Config.parse(['/tmp'])
17
+ end
18
+
19
+ it 'should parse args as options' do
20
+ @mock_config.should_receive(:parse_command_line_options).with(['-s', '-d'])
21
+ Reflection::Config.parse(['-s', '-d'])
22
+ end
23
+
24
+ it 'should write options to configuration file if --write params is set' do
25
+ @mock_config.should_receive(:write).with('/test/path')
26
+ @mock_config.stub!(:parse_command_line_options)
27
+ @mock_config.stub!(:store_configuration_path).and_return('/test/path')
28
+ Reflection::Config.parse(['-s','-d', '--write /test/path'])
29
+ end
30
+
31
+ it 'should expect a reflection.yml config file in path if args are empty' do
32
+ Dir.stub!(:pwd).and_return('/current_dir')
33
+ @mock_config.should_receive(:read!).with('/current_dir/reflection.yml')
34
+ Reflection::Config.parse
35
+ end
36
+ end
37
+
38
+ describe '#to_hash' do
39
+ it 'should turn its attributes into a hash' do
40
+ @config = Reflection::Config.new
41
+ @config.command = :stash
42
+ @config.repository = 'repo'
43
+ @config.directory = 'dir'
44
+ @config.to_hash.should == @valid_options
45
+ end
46
+ end
47
+
48
+ describe '#from_hash' do
49
+ it 'should assign attributes from a hash' do
50
+ @config = Reflection::Config.new
51
+ @config.from_hash( @valid_options )
52
+ @config.command.should eql(:stash)
53
+ @config.repository.should eql('repo')
54
+ @config.directory.should eql('dir')
55
+ end
56
+ end
57
+
58
+ describe '#write' do
59
+ before(:each) do
60
+ @config = Reflection::Config.new
61
+ @mock_file = mock('File')
62
+ @mock_file.stub!(:close)
63
+ end
64
+
65
+ it 'should dump the config values to a file at the given path' do
66
+ @config.stub!(:to_hash).and_return( @valid_options )
67
+ YAML.should_receive(:dump).with( @valid_options, @mock_file )
68
+ File.should_receive(:open).with('/test/path', 'w').and_return(@mock_file)
69
+ @config.write('/test/path')
70
+ end
71
+
72
+ it 'should gracefully fail if it cannot dump the yaml file' do
73
+ Reflection::Support.should_receive(:exit_with_error)
74
+ File.should_receive(:open).with('/test/path', 'w').and_raise(StandardError)
75
+ @config.write('/test/path')
76
+ end
77
+ end
78
+
79
+ describe '#read!' do
80
+ before(:each) do
81
+ File.stub!(:exist?).and_return(true)
82
+ @config = Reflection::Config.new
83
+ end
84
+
85
+ it 'should get the config attributes from a yaml file' do
86
+ YAML.should_receive(:load_file).with('/tmp/test').and_return( @valid_options )
87
+ @config.should_receive(:from_hash).with(@valid_options)
88
+ @config.read!('/tmp/test')
89
+ end
90
+
91
+ it "should not try to load a yaml file if it doesn't exist" do
92
+ YAML.should_not_receive(:load_file)
93
+ File.stub!(:exist?).and_return(false)
94
+ @config.read!('/tmp/test')
95
+ end
96
+
97
+ it "should gracefully fail if yaml file loading crashed" do
98
+ Reflection::Support.should_receive(:exit_with_error)
99
+ YAML.stub!(:load_file).and_raise(StandardError)
100
+ @config.read!('/tmp/test')
101
+ end
102
+
103
+ it "should gracefully fail if parsing result is not a hash" do
104
+ Reflection::Support.should_receive(:exit_with_error)
105
+ YAML.stub!(:load_file).and_return("String Instead Of Hash")
106
+ @config.read!('/tmp/test')
107
+ end
108
+ end
109
+
110
+ end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: reflection
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.0.2
4
+ version: 0.3.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andreas Wolff
@@ -9,7 +9,7 @@ autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
11
 
12
- date: 2009-11-15 00:00:00 +01:00
12
+ date: 2009-11-17 00:00:00 +01:00
13
13
  default_executable: reflection
14
14
  dependencies:
15
15
  - !ruby/object:Gem::Dependency
@@ -57,6 +57,7 @@ files:
57
57
  - lib/reflection/command/apply.rb
58
58
  - lib/reflection/command/base.rb
59
59
  - lib/reflection/command/stash.rb
60
+ - lib/reflection/config.rb
60
61
  - lib/reflection/directory.rb
61
62
  - lib/reflection/directory/base.rb
62
63
  - lib/reflection/directory/stash.rb
@@ -67,6 +68,7 @@ files:
67
68
  - lib/reflection/validations.rb
68
69
  - spec/reflection/cli_spec.rb
69
70
  - spec/reflection/command/stash_spec.rb
71
+ - spec/reflection/config_spec.rb
70
72
  - spec/reflection/directory/base_spec.rb
71
73
  - spec/reflection/directory/stash_spec.rb
72
74
  - spec/reflection/repository_spec.rb
@@ -106,6 +108,7 @@ summary: Helps you keeping your development machine in sync with production.
106
108
  test_files:
107
109
  - spec/reflection/cli_spec.rb
108
110
  - spec/reflection/command/stash_spec.rb
111
+ - spec/reflection/config_spec.rb
109
112
  - spec/reflection/directory/base_spec.rb
110
113
  - spec/reflection/directory/stash_spec.rb
111
114
  - spec/reflection/repository_spec.rb