boson 0.2.3 → 0.2.4

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,118 +1,122 @@
1
1
  require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
- module Boson
4
- class RepoIndexTest < Test::Unit::TestCase
5
- # since we're defining our own @commands, @libraries, @lib_hashes
6
- before(:all) { @index = RepoIndex.new(Boson.repo); @index.instance_variable_set "@read", true }
7
-
8
- context "read_and_transfer" do
9
- before(:each) { reset_boson; @index.instance_eval "@libraries = @commands = nil" }
10
-
11
- def transfers(options={})
12
- @index.instance_variable_set "@libraries", [Library.new(:name=>'blah', :commands=>['blurb']),
13
- Library.new(:name=>'bling')]
14
- @index.instance_variable_set "@commands", [Command.new(:name=>'blurb', :lib=>'blah')]
15
- @index.read_and_transfer options[:ignored] || []
16
- Boson.libraries.map {|e| e.name}.should == options[:libraries]
17
- Boson.commands.map {|e| e.name}.should == options[:commands]
18
- end
19
-
20
- test "transfers libraries with no libraries to ignore" do
21
- transfers :libraries=>%w{blah bling}, :commands=>%w{blurb}, :ignored=>[]
22
- end
23
-
24
- test "transfers libraries and commands except for ignored libraries and its commands" do
25
- transfers :libraries=>%w{bling}, :commands=>[], :ignored=>%w{blah}
26
- end
27
-
28
- test "doesn't replace existing libraries" do
29
- lib = Library.new(:name=>'blah')
30
- cmd = Command.new(:name=>'blurb', :lib=>'blah')
31
- Boson.libraries << lib
32
- Boson.commands << cmd
33
- transfers :libraries=>%w{blah bling}, :commands=>%w{blurb}
34
- Boson.libraries.include?(lib).should == true
35
- Boson.commands.include?(cmd).should == true
36
- end
37
- end
38
-
39
- context "find_library" do
40
- before(:all) {
41
- reset_boson
42
- commands = [Command.new(:name=>'blurb', :lib=>'blah', :alias=>'bb'),
43
- Command.new(:name=>'sub', :lib=>'bling', :alias=>'s')
44
- ]
45
- @index.instance_variable_set "@commands", commands
46
- @index.instance_variable_set "@libraries", [Library.new(:name=>'blah'), Library.new(:name=>'bling', :namespace=>'bling')]
47
- }
48
-
49
- test "finds command aliased or not" do
50
- @index.find_library('blurb').should == 'blah'
51
- @index.find_library('bb').should == 'blah'
52
- end
53
-
54
- test "doesn't find command" do
55
- @index.find_library('blah').should == nil
56
- end
57
-
58
- test "finds a subcommand aliased or not" do
59
- @index.find_library('bling.sub').should == 'bling'
60
- # @index.find_library('bl.s').should == 'bling'
61
- end
62
-
63
- test "finds namespace command aliased or not without a subcommand" do
64
- @index.find_library('bling').should == 'bling'
65
- # @index.find_library('bl').should == 'bling'
66
- end
67
-
68
- test "doesn't find a subcommand" do
69
- @index.find_library('d.d').should == nil
70
- end
71
- end
72
-
73
- context "changed_libraries" do
74
- before(:all) { @index.instance_eval "@lib_hashes = nil" }
75
-
76
- def changed(string, all_libs=['file1'])
77
- @index.repo.expects(:all_libraries).returns(all_libs)
78
- @index.instance_variable_set "@lib_hashes", {"file1"=>Digest::MD5.hexdigest("state1")}
79
- File.stubs(:exists?).returns(true)
80
- File.expects(:read).returns(string)
81
- @index.changed_libraries
82
- end
83
-
84
- test "detects changed libraries" do
85
- changed("state2").should == %w{file1}
86
- end
87
-
88
- test "detects new libraries" do
89
- changed("state1", ['file2']).should == %w{file2}
90
- end
91
-
92
- test "detects no changed libraries" do
93
- changed("state1").should == []
94
- end
95
- end
96
-
97
- context "write" do
98
- before(:all) {
99
- reset_boson
100
- Boson.commands << Command.new(:name=>'blah', :lib=>'blah', :args=>[['arg1', {}], ['arg2', self.class]])
101
- Boson.libraries << Library.new(:name=>'blah', :module=>self.class)
102
- @index.expects(:latest_hashes)
103
- libraries = commands = []
104
- @index.expects(:save_marshal_index).with {|str| libraries, commands, hashes = Marshal.load(str) ; true}
105
- @index.write
106
- @index_hash = {:libraries=>libraries, :commands=>commands}
107
- }
108
-
109
- test "saves library module constants as strings" do
110
- @index_hash[:libraries][0].module.class.should == String
111
- end
112
-
113
- test "save commands with arg values as strings" do
114
- @index_hash[:commands][0].args.each {|e| e[1].class.should == String}
115
- end
3
+ describe "RepoIndex" do
4
+ # since we're defining our own @commands, @libraries, @lib_hashes
5
+ def index
6
+ @index ||= begin
7
+ ind = RepoIndex.new(Boson.repo)
8
+ ind.instance_variable_set "@read", true
9
+ ind
10
+ end
11
+ end
12
+
13
+ describe "read_and_transfer" do
14
+ before { reset_boson; index.instance_eval "@libraries = @commands = nil" }
15
+
16
+ def transfers(options={})
17
+ index.instance_variable_set "@libraries", [Library.new(:name=>'blah', :commands=>['blurb']),
18
+ Library.new(:name=>'bling')]
19
+ index.instance_variable_set "@commands", [Command.new(:name=>'blurb', :lib=>'blah')]
20
+ index.read_and_transfer options[:ignored] || []
21
+ Boson.libraries.map {|e| e.name}.should == options[:libraries]
22
+ Boson.commands.map {|e| e.name}.should == options[:commands]
23
+ end
24
+
25
+ it "transfers libraries with no libraries to ignore" do
26
+ transfers :libraries=>%w{blah bling}, :commands=>%w{blurb}, :ignored=>[]
27
+ end
28
+
29
+ it "transfers libraries and commands except for ignored libraries and its commands" do
30
+ transfers :libraries=>%w{bling}, :commands=>[], :ignored=>%w{blah}
31
+ end
32
+
33
+ it "doesn't replace existing libraries" do
34
+ lib = Library.new(:name=>'blah')
35
+ cmd = Command.new(:name=>'blurb', :lib=>'blah')
36
+ Boson.libraries << lib
37
+ Boson.commands << cmd
38
+ transfers :libraries=>%w{blah bling}, :commands=>%w{blurb}
39
+ Boson.libraries.include?(lib).should == true
40
+ Boson.commands.include?(cmd).should == true
41
+ end
42
+ end
43
+
44
+ describe "find_library" do
45
+ before_all {
46
+ reset_boson
47
+ commands = [Command.new(:name=>'blurb', :lib=>'blah', :alias=>'bb'),
48
+ Command.new(:name=>'sub', :lib=>'bling', :alias=>'s')
49
+ ]
50
+ index.instance_variable_set "@commands", commands
51
+ index.instance_variable_set "@libraries", [Library.new(:name=>'blah'), Library.new(:name=>'bling', :namespace=>'bling')]
52
+ }
53
+
54
+ it "finds command aliased or not" do
55
+ index.find_library('blurb').should == 'blah'
56
+ index.find_library('bb').should == 'blah'
57
+ end
58
+
59
+ it "doesn't find command" do
60
+ index.find_library('blah').should == nil
61
+ end
62
+
63
+ it "finds a subcommand aliased or not" do
64
+ index.find_library('bling.sub').should == 'bling'
65
+ # @index.find_library('bl.s').should == 'bling'
66
+ end
67
+
68
+ it "finds namespace command aliased or not without a subcommand" do
69
+ index.find_library('bling').should == 'bling'
70
+ # @index.find_library('bl').should == 'bling'
71
+ end
72
+
73
+ it "doesn't find a subcommand" do
74
+ index.find_library('d.d').should == nil
75
+ end
76
+ end
77
+
78
+ describe "changed_libraries" do
79
+ before_all { index.instance_eval "@lib_hashes = nil" }
80
+
81
+ def changed(string, all_libs=['file1'])
82
+ index.repo.expects(:all_libraries).returns(all_libs)
83
+ index.instance_variable_set "@lib_hashes", {"file1"=>Digest::MD5.hexdigest("state1")}
84
+ File.stubs(:exists?).returns(true)
85
+ File.expects(:read).returns(string)
86
+ index.changed_libraries
87
+ end
88
+
89
+ it "detects changed libraries" do
90
+ changed("state2").should == %w{file1}
91
+ end
92
+
93
+ it "detects new libraries" do
94
+ changed("state1", ['file2']).should == %w{file2}
95
+ end
96
+
97
+ it "detects no changed libraries" do
98
+ changed("state1").should == []
99
+ end
100
+ end
101
+
102
+ describe "write" do
103
+ before_all {
104
+ reset_boson
105
+ Boson.commands << Command.new(:name=>'blah', :lib=>'blah', :args=>[['arg1', {}], ['arg2', self.class]])
106
+ Boson.libraries << Library.new(:name=>'blah', :module=>self.class)
107
+ index.expects(:latest_hashes)
108
+ libraries = commands = []
109
+ index.expects(:save_marshal_index).with {|str| libraries, commands, hashes = Marshal.load(str) ; true}
110
+ index.write
111
+ @index_hash = {:libraries=>libraries, :commands=>commands}
112
+ }
113
+
114
+ it "saves library module constants as strings" do
115
+ @index_hash[:libraries][0].module.class.should == String
116
+ end
117
+
118
+ it "save commands with arg values as strings" do
119
+ @index_hash[:commands][0].args.each {|e| e[1].class.should == String}
116
120
  end
117
121
  end
118
122
  end
data/test/repo_test.rb CHANGED
@@ -1,23 +1,23 @@
1
1
  require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
- class Boson::RepoTest < Test::Unit::TestCase
4
- context "config" do
5
- before(:all) { reset }
6
- before(:each) { @repo = Boson::Repo.new(File.dirname(__FILE__)) }
3
+ describe "config" do
4
+ before_all { reset }
5
+ before { @repo = Repo.new(File.dirname(__FILE__)) }
7
6
 
8
- test "reloads config when passed true" do
9
- @repo.config.object_id.should_not == @repo.config(true).object_id
10
- end
7
+ it "reloads config when passed true" do
8
+ @repo.config.object_id.should.not == @repo.config(true).object_id
9
+ end
11
10
 
12
- test "reads existing config correctly" do
13
- expected_hash = {:commands=>{'c1'=>{}}, :libraries=>{}}
14
- File.expects(:exists?).returns(true)
15
- YAML.expects(:load_file).returns(expected_hash)
16
- @repo.config[:commands]['c1'].should == {}
17
- end
11
+ it "reads existing config correctly" do
12
+ expected_hash = {:commands=>{'c1'=>{}}, :libraries=>{}}
13
+ File.expects(:exists?).returns(true)
14
+ YAML.expects(:load_file).returns(expected_hash)
15
+ @repo.config[:commands]['c1'].should == {}
16
+ end
18
17
 
19
- test "ignores nonexistent file and sets config defaults" do
20
- assert @repo.config[:command_aliases].is_a?(Hash) && @repo.config[:libraries].is_a?(Hash)
21
- end
18
+ it "ignores nonexistent file and sets config defaults" do
19
+ @repo.config[:command_aliases].class.should == Hash
20
+ @repo.config[:libraries].class.should == Hash
22
21
  end
23
- end
22
+ after_all { FileUtils.rm_r File.dirname(__FILE__)+'/config', :force=>true }
23
+ end
data/test/runner_test.rb CHANGED
@@ -1,43 +1,40 @@
1
1
  require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
- module Boson
4
- class RunnerTest < Test::Unit::TestCase
5
- context "repl_runner" do
6
- def start(hash={})
7
- Hirb.stubs(:enable)
8
- Boson.start(hash.merge(:verbose=>false))
9
- end
3
+ describe "repl_runner" do
4
+ def start(hash={})
5
+ Hirb.stubs(:enable)
6
+ Boson.start(hash.merge(:verbose=>false))
7
+ end
10
8
 
11
- before(:all) { reset }
12
- before(:each) { Boson::ConsoleRunner.instance_eval("@initialized = false") }
9
+ before_all { reset }
10
+ before { ConsoleRunner.instance_eval("@initialized = false") }
13
11
 
14
- test "loads default libraries and libraries in :console_defaults config" do
15
- defaults = Boson::Runner.default_libraries + ['yo']
16
- with_config(:console_defaults=>['yo']) do
17
- Manager.expects(:load).with {|*args| args[0] == defaults }
18
- start
19
- end
20
- end
12
+ it "loads default libraries and libraries in :console_defaults config" do
13
+ defaults = Runner.default_libraries + ['yo']
14
+ with_config(:console_defaults=>['yo']) do
15
+ Manager.expects(:load).with {|*args| args[0] == defaults }
16
+ start
17
+ end
18
+ end
21
19
 
22
- test "doesn't call init twice" do
23
- start
24
- ConsoleRunner.expects(:init).never
25
- start
26
- end
20
+ it "doesn't call init twice" do
21
+ capture_stderr { start }
22
+ ConsoleRunner.expects(:init).never
23
+ start
24
+ end
27
25
 
28
- test "loads multiple libraries with :libraries option" do
29
- ConsoleRunner.expects(:init)
30
- Manager.expects(:load).with([:lib1,:lib2], anything)
31
- start(:libraries=>[:lib1, :lib2])
32
- end
26
+ it "loads multiple libraries with :libraries option" do
27
+ ConsoleRunner.expects(:init)
28
+ Manager.expects(:load).with([:lib1,:lib2], anything)
29
+ start(:libraries=>[:lib1, :lib2])
30
+ end
33
31
 
34
- test "autoloader autoloads libraries" do
35
- start(:autoload_libraries=>true)
36
- Index.expects(:read)
37
- Index.expects(:find_library).with('blah').returns('blah')
38
- Manager.expects(:load).with('blah', :verbose=>nil)
39
- Boson.main_object.blah
40
- end
41
- end
32
+ it "autoloader autoloads libraries" do
33
+ start(:autoload_libraries=>true)
34
+ Index.expects(:read)
35
+ Index.expects(:find_library).with('blah').returns('blah')
36
+ Manager.expects(:load).with('blah', anything)
37
+ Boson.main_object.blah
42
38
  end
39
+ after_all { FileUtils.rm_r File.dirname(__FILE__)+'/config', :force=>true }
43
40
  end
@@ -1,337 +1,341 @@
1
1
  require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
- module Boson
4
- class ScientistTest < Test::Unit::TestCase
5
- before(:all) {
6
- unless ScientistTest.const_defined?(:Blah)
7
- Boson.send :remove_const, :BinRunner if Boson.const_defined?(:BinRunner)
8
- eval <<-EOF
9
- module Blah
10
- def blah(arg1, options={})
11
- [arg1, options]
12
- end
13
- def splat_blah(*args)
14
- args
15
- end
16
- def default_blah(arg1, arg2=default, options={})
17
- [arg1, arg2, options]
18
- end
19
- def default; 'some default'; end
20
- def default_option(options={})
21
- options
22
- end
3
+ describe "Scientist" do
4
+ before_all {
5
+ Runner.in_shell = nil
6
+ eval <<-EOF
7
+ module Blah
8
+ def blah(arg1, options={})
9
+ [arg1, options]
23
10
  end
24
- EOF
11
+ def splat_blah(*args)
12
+ args
25
13
  end
26
- @opt_cmd = Object.new.extend Blah
27
- }
28
- after(:all) { Runner.in_shell = false }
14
+ def default_blah(arg1, arg2=default, options={})
15
+ [arg1, arg2, options]
16
+ end
17
+ def default; 'some default'; end
18
+ def default_option(options={})
19
+ options
20
+ end
21
+ end
22
+ EOF
23
+ @opt_cmd = Object.new.extend Blah
24
+ }
25
+
26
+ def command(hash, args)
27
+ hash = {:name=>'blah', :lib=>'bling', :options=>{:force=>:boolean, :level=>2}}.merge(hash)
28
+ @cmd = Command.new hash
29
+ @cmd.instance_variable_set("@file_parsed_args", true) if hash[:file_parsed_args]
30
+ Scientist.redefine_command(@opt_cmd, @cmd)
31
+ @opt_cmd.send(hash[:name], *args)
32
+ end
33
+
34
+ def command_with_arg_size(*args)
35
+ command({:args=>2}, args)
36
+ end
37
+
38
+ def command_with_args(*args)
39
+ command({:args=>[['arg1'],['options', {}]]}, args)
40
+ end
41
+
42
+ def basic_command(hash, args)
43
+ command({:name=>'splat_blah', :args=>'*'}.merge(hash), args)
44
+ end
45
+
46
+ def command_with_splat_args(*args)
47
+ command({:name=>'splat_blah', :args=>'*'}, args)
48
+ end
49
+
50
+ def command_with_arg_defaults(*args)
51
+ arg_defaults = [%w{arg1}, %w{arg2 default}, %w{options {}}]
52
+ command({:name=>'default_blah', :file_parsed_args=>true, :args=>arg_defaults}, args)
53
+ end
54
+
55
+ def args_are_equal(args, array)
56
+ command_with_args(*args).should == array
57
+ command_with_arg_size(*args).should == array
58
+ command_with_splat_args(*args).should == array
59
+ end
60
+
61
+ def all_commands
62
+ [:command_with_args, :command_with_arg_size, :command_with_splat_args]
63
+ end
29
64
 
30
- def command(hash, args)
31
- hash = {:name=>'blah', :lib=>'bling', :options=>{:force=>:boolean, :level=>2}}.merge(hash)
32
- @cmd = Command.new hash
33
- @cmd.instance_variable_set("@file_parsed_args", true) if hash[:file_parsed_args]
34
- Scientist.redefine_command(@opt_cmd, @cmd)
35
- @opt_cmd.send(hash[:name], *args)
65
+ describe "all commands" do
66
+ it "translate arg and options as one string" do
67
+ args_are_equal ['a1 -f'], ['a1', {:force=>true, :level=>2}]
36
68
  end
37
69
 
38
- def command_with_arg_size(*args)
39
- command({:args=>2}, args)
70
+ it "translate arg and stringified options" do
71
+ args_are_equal [:cool, '-l3'], [:cool, {:level=>3}]
40
72
  end
41
73
 
42
- def command_with_args(*args)
43
- command({:args=>[['arg1'],['options', {}]]}, args)
74
+ it "translate arg and normal hash options" do
75
+ args_are_equal [:cool, {:ok=>true}], [:cool, {:ok=>true, :level=>2}]
44
76
  end
45
77
 
46
- def basic_command(hash, args)
47
- command({:name=>'splat_blah', :args=>'*'}.merge(hash), args)
78
+ it "translate stringified arg without options sets default options" do
79
+ args_are_equal ['cool'], ['cool', {:level=>2}]
48
80
  end
49
81
 
50
- def command_with_splat_args(*args)
51
- command({:name=>'splat_blah', :args=>'*'}, args)
82
+ it "translate arg without options sets default options" do
83
+ args_are_equal [:cool], [:cool, {:level=>2}]
52
84
  end
53
85
 
54
- def command_with_arg_defaults(*args)
55
- arg_defaults = [%w{arg1}, %w{arg2 default}, %w{options {}}]
56
- command({:name=>'default_blah', :file_parsed_args=>true, :args=>arg_defaults}, args)
86
+ it "with invalid options print errors and delete them" do
87
+ all_commands.each do |cmd|
88
+ capture_stderr {
89
+ send(cmd, 'cool -f -z').should == ['cool', {:force=>true, :level=>2}]
90
+ }.should =~/invalid.*z/
91
+ end
57
92
  end
58
93
 
59
- def args_are_equal(args, array)
60
- command_with_args(*args).should == array
61
- command_with_arg_size(*args).should == array
62
- command_with_splat_args(*args).should == array
94
+ it "print help with help option" do
95
+ all_commands.each do |cmd|
96
+ Boson.expects(:invoke).with(:usage, anything, anything)
97
+ send(cmd, '-h')
98
+ end
63
99
  end
100
+ end
64
101
 
65
- ALL_COMMANDS = [:command_with_args, :command_with_arg_size, :command_with_splat_args]
102
+ describe "command" do
103
+ describe "with arg defaults" do
104
+ it "sets defaults with stringified args" do
105
+ command_with_arg_defaults('1').should == ["1", "some default", {:level=>2}]
106
+ end
66
107
 
67
- context "all commands" do
68
- test "translate arg and options as one string" do
69
- args_are_equal ['a1 -f'], ['a1', {:force=>true, :level=>2}]
108
+ it "sets defaults with normal args" do
109
+ command_with_arg_defaults(1).should == [1, "some default", {:level=>2}]
70
110
  end
71
111
 
72
- test "translate arg and stringified options" do
73
- args_are_equal [:cool, '-l3'], [:cool, {:level=>3}]
112
+ it "sets default if optional arg is a valid option" do
113
+ command_with_arg_defaults("cool -f").should == ["cool", "some default", {:level=>2, :force=>true}]
74
114
  end
75
115
 
76
- test "translate arg and normal hash options" do
77
- args_are_equal [:cool, {:ok=>true}], [:cool, {:ok=>true, :level=>2}]
116
+ it "doesn't set defaults if not needed" do
117
+ command_with_arg_defaults(1, 'nada').should == [1, "nada", {:level=>2}]
78
118
  end
79
119
 
80
- test "translate stringified arg without options sets default options" do
81
- args_are_equal ['cool'], ['cool', {:level=>2}]
120
+ it "prints error for invalid defaults" do
121
+ arg_defaults = [%w{arg1}, %w{arg2 invalidzzz}, %w{options {}}]
122
+ capture_stderr {
123
+ command({:name=>'default_blah', :file_parsed_args=>true, :args=>arg_defaults}, [1])
124
+ }.should =~ /Error.*position 2/
82
125
  end
126
+ end
83
127
 
84
- test "translate arg without options sets default options" do
85
- args_are_equal [:cool], [:cool, {:level=>2}]
128
+ describe "prints error" do
129
+ it "with option error" do
130
+ capture_stderr { command_with_args('a1 -l') }.should =~ /Error.*level/
86
131
  end
87
132
 
88
- test "with invalid options print errors and delete them" do
89
- ALL_COMMANDS.each do |cmd|
90
- capture_stderr {
91
- send(cmd, 'cool -f -z').should == ['cool', {:force=>true, :level=>2}]
92
- }.should =~/invalid.*z/
93
- end
133
+ it "with unexpected error in render" do
134
+ Scientist.expects(:can_render?).raises("unexpected")
135
+ capture_stderr { command_with_args('a1') }.should =~ /Error.*unexpected/
94
136
  end
95
137
 
96
- test "print help with help option" do
97
- ALL_COMMANDS.each do |cmd|
98
- Boson.expects(:invoke).with(:usage, anything, anything)
99
- send(cmd, '-h')
100
- end
138
+ it "with no argument defined for options" do
139
+ assert_error(OptionCommand::CommandArgumentError, '2 for 1') { command({:args=>1}, 'ok') }
101
140
  end
102
141
  end
103
142
 
104
- context "command" do
105
- context "with arg defaults" do
106
- test "sets defaults with stringified args" do
107
- command_with_arg_defaults('1').should == ["1", "some default", {:level=>2}]
108
- end
109
-
110
- test "sets defaults with normal args" do
111
- command_with_arg_defaults(1).should == [1, "some default", {:level=>2}]
112
- end
113
-
114
- test "sets default if optional arg is a valid option" do
115
- command_with_arg_defaults("cool -f").should == ["cool", "some default", {:level=>2, :force=>true}]
116
- end
143
+ it "translates stringfied args + options starting at second arg" do
144
+ command_with_arg_defaults(1, 'nada -l3').should == [1, "nada", {:level=>3}]
145
+ end
117
146
 
118
- test "doesn't set defaults if not needed" do
119
- command_with_arg_defaults(1, 'nada').should == [1, "nada", {:level=>2}]
120
- end
147
+ it "with leading option-like args are translated as arguments" do
148
+ command_with_args('-z -f').should == ["-z", {:force=>true, :level=>2}]
149
+ command_with_args('--blah -f').should == ['--blah', {:force=>true, :level=>2}]
150
+ end
121
151
 
122
- test "prints error for invalid defaults" do
123
- arg_defaults = [%w{arg1}, %w{arg2 invalidzzz}, %w{options {}}]
124
- capture_stderr {
125
- command({:name=>'default_blah', :file_parsed_args=>true, :args=>arg_defaults}, [1])
126
- }.should =~ /Error.*position 2/
127
- end
152
+ it "with splat args does not raise error for too few or many args" do
153
+ [[], [''], [1,2,3], ['1 2 3']].each do |args|
154
+ should.not.raise { command_with_splat_args *args }
128
155
  end
156
+ end
129
157
 
130
- context "prints error" do
131
- test "with option error" do
132
- capture_stderr { command_with_args('a1 -l') }.should =~ /Error.*level/
133
- end
158
+ it "with debug option prints debug" do
159
+ capture_stdout { command_with_args("-v ok") }.should =~ /Arguments.*ok/
160
+ end
134
161
 
135
- test "with unexpected error in render" do
136
- Scientist.expects(:render?).raises("unexpected")
137
- capture_stderr { command_with_args('a1') }.should =~ /Error.*unexpected/
138
- end
162
+ it "with pretend option prints arguments and returns early" do
163
+ Scientist.expects(:render_or_raw).never
164
+ capture_stdout { command_with_args("-p ok") }.should =~ /Arguments.*ok/
165
+ end
139
166
 
140
- test "with no argument defined for options" do
141
- assert_error(OptionCommand::CommandArgumentError, '2 for 1') { command({:args=>1}, 'ok') }
142
- end
143
- end
167
+ it "with not enough args raises CommandArgumentError" do
168
+ args = [OptionCommand::CommandArgumentError, '0 for 1']
169
+ assert_error(*args) { command_with_args }
170
+ assert_error(*args) { command_with_args '' }
171
+ assert_error(*args) { command_with_arg_size }
172
+ assert_error(*args) { command_with_arg_size '' }
173
+ end
144
174
 
145
- test "translates stringfied args + options starting at second arg" do
146
- command_with_arg_defaults(1, 'nada -l3').should == [1, "nada", {:level=>3}]
147
- end
175
+ it "with too many args raises CommandArgumentError" do
176
+ args3 = [ArgumentError, '3 for 2']
177
+ args4 = [OptionCommand::CommandArgumentError, '4 for 2']
178
+ assert_error(*args3) { command_with_args 1,2,3 }
179
+ assert_error(*args4) { command_with_args '1 2 3' }
180
+ assert_error(*args3) { command_with_arg_size 1,2,3 }
181
+ assert_error(*args4) { command_with_arg_size '1 2 3' }
182
+ end
183
+ end
148
184
 
149
- test "with leading option-like args are translated as arguments" do
150
- command_with_args('-z -f').should == ["-z", {:force=>true, :level=>2}]
151
- command_with_args('--blah -f').should == ['--blah', {:force=>true, :level=>2}]
152
- end
185
+ def command_with_render(*args)
186
+ basic_command({:render_options=>{:fields=>{:values=>['f1', 'f2']}} }, args)
187
+ end
153
188
 
154
- test "with splat args does not raise error for too few or many args" do
155
- [[], [''], [1,2,3], ['1 2 3']].each do |args|
156
- assert_nothing_raised { command_with_splat_args *args }
157
- end
158
- end
189
+ def render_expected(options=nil)
190
+ View.expects(:render).with(anything, options || anything, false)
191
+ end
159
192
 
160
- test "with debug option prints debug" do
161
- capture_stdout { command_with_args("-v ok") } =~ /Arguments.*ok/
162
- end
193
+ describe "render" do
194
+ it "called for command with render_options" do
195
+ render_expected
196
+ command_with_render('1')
197
+ end
163
198
 
164
- test "with pretend option prints arguments and returns early" do
165
- Scientist.expects(:render_or_raw).never
166
- capture_stdout { command_with_args("-p ok") } =~ /Arguments.*ok/
167
- end
199
+ it "called for command without render_options and --render" do
200
+ render_expected
201
+ command_with_args('--render 1')
202
+ end
168
203
 
169
- test "with not enough args raises CommandArgumentError" do
170
- args = [OptionCommand::CommandArgumentError, '0 for 1']
171
- assert_error(*args) { command_with_args }
172
- assert_error(*args) { command_with_args '' }
173
- assert_error(*args) { command_with_arg_size }
174
- assert_error(*args) { command_with_arg_size '' }
175
- end
204
+ it "not called for command with render_options and --render" do
205
+ Boson.expects(:invoke).never
206
+ command_with_render('--render 1')
207
+ end
176
208
 
177
- test "with too many args raises CommandArgumentError" do
178
- args3 = [ArgumentError, '3 for 2']
179
- args4 = [OptionCommand::CommandArgumentError, '4 for 2']
180
- assert_error(*args3) { command_with_args 1,2,3 }
181
- assert_error(*args4) { command_with_args '1 2 3' }
182
- assert_error(*args3) { command_with_arg_size 1,2,3 }
183
- assert_error(*args4) { command_with_arg_size '1 2 3' }
184
- end
209
+ it "not called for command without render_options" do
210
+ Boson.expects(:invoke).never
211
+ command_with_args('1')
185
212
  end
213
+ end
186
214
 
187
- def command_with_render(*args)
188
- basic_command({:render_options=>{:fields=>{:values=>['f1', 'f2']}} }, args)
215
+ describe "command renders" do
216
+ it "with basic render options" do
217
+ render_expected :fields => ['f1', 'f2']
218
+ command_with_render("--fields f1,f2 ab")
189
219
  end
190
220
 
191
- def render_expected(options=nil)
192
- View.expects(:render).with(anything, options || anything, false)
221
+ it "without non-render options" do
222
+ render_expected :fields=>['f1']
223
+ Scientist.expects(:can_render?).returns(true)
224
+ args = ["--render --fields f1 ab"]
225
+ basic_command({:render_options=>{:fields=>{:values=>['f1', 'f2']}} }, args)
193
226
  end
194
227
 
195
- context "render" do
196
- test "called for command with render_options" do
197
- render_expected
198
- command_with_render('1')
199
- end
228
+ it "with user-defined render options" do
229
+ render_expected :fields=>['f1'], :foo=>true
230
+ args = ["--foo --fields f1 ab"]
231
+ basic_command({:render_options=>{:foo=>:boolean, :fields=>{:values=>['f1', 'f2']}} }, args)
232
+ end
200
233
 
201
- test "called for command without render_options and --render" do
202
- render_expected
203
- command_with_args('--render 1')
204
- end
234
+ it "with non-hash user-defined render options" do
235
+ render_expected :fields=>['f1'], :foo=>true
236
+ args = ["--foo --fields f1 ab"]
237
+ basic_command({:render_options=>{:foo=>:boolean, :fields=>%w{f1 f2 f3}} }, args)
238
+ end
239
+ end
205
240
 
206
- test "not called for command with render_options and --render" do
207
- Boson.expects(:invoke).never
208
- command_with_render('--render 1')
209
- end
241
+ describe "command with default option" do
242
+ before_all { @cmd_attributes = {:name=>'default_option', :default_option=>'level', :args=>1} }
210
243
 
211
- test "not called for command without render_options" do
212
- Boson.expects(:invoke).never
213
- command_with_args('1')
214
- end
244
+ it "parses normally from irb" do
245
+ command(@cmd_attributes, '-f --level=3').should == {:level=>3, :force=>true}
215
246
  end
216
247
 
217
- context "command renders" do
218
- test "with basic render options" do
219
- render_expected :fields => ['f1', 'f2']
220
- command_with_render("--fields f1,f2 ab")
221
- end
248
+ it "parses normally from cmdline" do
249
+ Runner.expects(:in_shell?).times(2).returns true
250
+ command(@cmd_attributes, ['--force', '--level=3']).should == {:level=>3, :force=>true}
251
+ end
222
252
 
223
- test "without non-render options" do
224
- render_expected :fields=>['f1']
225
- Scientist.expects(:render?).returns(true)
226
- args = ["--render --fields f1 ab"]
227
- basic_command({:render_options=>{:fields=>{:values=>['f1', 'f2']}} }, args)
228
- end
253
+ it "parses no arguments normally" do
254
+ command(@cmd_attributes, '').should == {:level=>2}
255
+ end
229
256
 
230
- test "with user-defined render options" do
231
- render_expected :fields=>['f1'], :foo=>true
232
- args = ["--foo --fields f1 ab"]
233
- basic_command({:render_options=>{:foo=>:boolean, :fields=>{:values=>['f1', 'f2']}} }, args)
234
- end
257
+ it "parses ruby arguments normally" do
258
+ command(@cmd_attributes, [{:force=>true, :level=>10}]).should == {:level=>10, :force=>true}
259
+ end
235
260
 
236
- test "with non-hash user-defined render options" do
237
- render_expected :fields=>['f1'], :foo=>true
238
- args = ["--foo --fields f1 ab"]
239
- basic_command({:render_options=>{:foo=>:boolean, :fields=>%w{f1 f2 f3}} }, args)
240
- end
261
+ it "prepends correctly from irb" do
262
+ command(@cmd_attributes, '3 -f').should == {:level=>3, :force=>true}
241
263
  end
242
264
 
243
- context "command with default option" do
244
- before(:all) { @cmd_attributes = {:name=>'default_option', :default_option=>'level', :args=>1} }
265
+ it "prepends correctly from cmdline" do
266
+ Runner.expects(:in_shell?).times(2).returns true
267
+ command(@cmd_attributes, ['3','-f']).should == {:level=>3, :force=>true}
268
+ end
269
+ end
245
270
 
246
- test "parses normally from irb" do
247
- command(@cmd_attributes, '-f --level=3').should == {:level=>3, :force=>true}
248
- end
271
+ it "optionless command renders" do
272
+ render_expected :fields=>['f1']
273
+ command({:args=>2, :options=>nil, :render_options=>{:fields=>:array}}, ["--fields f1 ab ok"])
274
+ end
249
275
 
250
- test "parses normally from cmdline" do
251
- Runner.expects(:in_shell?).times(2).returns true
252
- command(@cmd_attributes, ['--force', '--level=3']).should == {:level=>3, :force=>true}
253
- end
276
+ it "redefine_command prints error for command with nonexistant method" do
277
+ capture_stderr {
278
+ Scientist.redefine_command Object.new, Command.new(:name=>'blah', :lib=>'blah')
279
+ }.should =~ /Error: No method.*'blah'/
280
+ end
254
281
 
255
- test "parses no arguments normally" do
256
- command(@cmd_attributes, '').should == {:level=>2}
257
- end
282
+ describe "global options:" do
283
+ def local_and_global(*args)
284
+ Scientist.stubs(:can_render?).returns(false) # turn off rendering caused by :render_options
285
+ @non_opts = basic_command(@command_options, args)
286
+ @non_opts.slice!(-1,1) << Scientist.global_options
287
+ end
258
288
 
259
- test "parses ruby arguments normally" do
260
- command(@cmd_attributes, [{:force=>true, :level=>10}]).should == {:level=>10, :force=>true}
261
- end
289
+ before_all {
290
+ @command_options = {:options=>{:do=>:boolean, :foo=>:boolean},
291
+ :render_options=>{:dude=>:boolean}}
292
+ @expected_non_opts = [[], ['doh'], ['doh'], [:doh]]
293
+ }
262
294
 
263
- test "prepends correctly from irb" do
264
- command(@cmd_attributes, '3 -f').should == {:level=>3, :force=>true}
295
+ it "local option overrides global one" do
296
+ ['-d', 'doh -d','-d doh', [:doh, '-d']].each_with_index do |args, i|
297
+ local_and_global(*args).should == [{:do=>true}, {}]
298
+ @non_opts.should == @expected_non_opts[i]
265
299
  end
300
+ end
266
301
 
267
- test "prepends correctly from cmdline" do
268
- Runner.expects(:in_shell?).times(2).returns true
269
- command(@cmd_attributes, ['3','-f']).should == {:level=>3, :force=>true}
302
+ it "global option before local one is valid" do
303
+ args_arr = ['--dude -f', '--dude doh -f', '--dude -f doh', [:doh, '--dude -f']]
304
+ args_arr.each_with_index do |args, i|
305
+ local_and_global(*args).should == [{:foo=>true}, {:dude=>true}]
306
+ @non_opts.should == @expected_non_opts[i]
270
307
  end
271
308
  end
272
309
 
273
- test "optionless command renders" do
274
- render_expected :fields=>['f1']
275
- command({:args=>2, :options=>nil, :render_options=>{:fields=>:array}}, ["--fields f1 ab ok"])
310
+ it "delete_options deletes global options" do
311
+ local_and_global('--delete_options=r,p -rp -f').should ==
312
+ [{:foo=>true}, {:delete_options=>["r", "p"]}]
276
313
  end
277
314
 
278
- context "global options:" do
279
- def local_and_global(*args)
280
- Scientist.stubs(:render?).returns(false) # turn off rendering caused by :render_options
281
- @non_opts = basic_command(@command_options, args)
282
- @non_opts.slice!(-1,1) << Scientist.global_options
283
- end
284
-
285
- before(:all) {
286
- @command_options = {:options=>{:do=>:boolean, :foo=>:boolean},
287
- :render_options=>{:dude=>:boolean}}
288
- @expected_non_opts = [[], ['doh'], ['doh'], [:doh]]
289
- }
290
-
291
- test "local option overrides global one" do
292
- ['-d', 'doh -d','-d doh', [:doh, '-d']].each_with_index do |args, i|
293
- local_and_global(*args).should == [{:do=>true}, {}]
315
+ it "global option after local one is invalid" do
316
+ args_arr = ['-f --dude', '-f doh --dude', '-f --dude doh', [:doh, '-f --dude'] ]
317
+ args_arr.each_with_index do |args, i|
318
+ capture_stderr {
319
+ local_and_global(*args).should == [{:foo=>true}, {}]
294
320
  @non_opts.should == @expected_non_opts[i]
295
- end
296
- end
297
-
298
- test "global option before local one is valid" do
299
- args_arr = ['--dude -f', '--dude doh -f', '--dude -f doh', [:doh, '--dude -f']]
300
- args_arr.each_with_index do |args, i|
301
- local_and_global(*args).should == [{:foo=>true}, {:dude=>true}]
302
- @non_opts.should == @expected_non_opts[i]
303
- end
304
- end
305
-
306
- test "delete_options deletes global options" do
307
- local_and_global('--delete_options=r,p -rp -f').should ==
308
- [{:foo=>true}, {:delete_options=>["r", "p"]}]
309
- end
310
-
311
- test "global option after local one is invalid" do
312
- args_arr = ['-f --dude', '-f doh --dude', '-f --dude doh', [:doh, '-f --dude'] ]
313
- args_arr.each_with_index do |args, i|
314
- capture_stderr {
315
- local_and_global(*args).should == [{:foo=>true}, {}]
316
- @non_opts.should == @expected_non_opts[i]
317
- }.should =~ /invalid.*dude/
318
- end
321
+ }.should =~ /invalid.*dude/
319
322
  end
323
+ end
320
324
 
321
- test "global option after local one and -" do
322
- local_and_global("doh -r -f - --dude").should == [{:foo=>true}, {:dude=>true, :render=>true}]
323
- end
325
+ it "global option after local one and -" do
326
+ local_and_global("doh -r -f - --dude").should == [{:foo=>true}, {:dude=>true, :render=>true}]
327
+ end
324
328
 
325
- test "conflicting global option after -" do
326
- local_and_global('doh - -f=1,2').should == [{}, {:fields=>["1", "2"]}]
327
- end
329
+ it "conflicting global option after -" do
330
+ local_and_global('doh - -f=1,2').should == [{}, {:fields=>["1", "2"]}]
331
+ end
328
332
 
329
- test "no options parsed after --" do
330
- local_and_global('doh -f -- -r').should == [{:foo=>true}, {}]
331
- local_and_global('doh -- -r -f').should == [{}, {}]
332
- local_and_global('-- -r -f').should == [{}, {}]
333
- local_and_global('doh -r -- -f').should == [{}, {:render=>true}]
334
- end
333
+ it "no options parsed after --" do
334
+ local_and_global('doh -f -- -r').should == [{:foo=>true}, {}]
335
+ local_and_global('doh -- -r -f').should == [{}, {}]
336
+ local_and_global('-- -r -f').should == [{}, {}]
337
+ local_and_global('doh -r -- -f').should == [{}, {:render=>true}]
335
338
  end
336
339
  end
337
- end
340
+ after_all { Runner.in_shell = false }
341
+ end