boson 0.4.0 → 1.0.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.
Files changed (64) hide show
  1. data/.gemspec +6 -7
  2. data/.rspec +2 -0
  3. data/.travis.yml +7 -0
  4. data/CHANGELOG.rdoc +1 -1
  5. data/README.md +144 -0
  6. data/README.rdoc +2 -2
  7. data/Upgrading.md +23 -0
  8. data/bin/boson +2 -2
  9. data/lib/boson.rb +44 -52
  10. data/lib/boson/bare_runner.rb +83 -0
  11. data/lib/boson/bin_runner.rb +114 -0
  12. data/lib/boson/command.rb +92 -132
  13. data/lib/boson/inspector.rb +49 -48
  14. data/lib/boson/library.rb +71 -120
  15. data/lib/boson/loader.rb +73 -84
  16. data/lib/boson/manager.rb +131 -135
  17. data/lib/boson/method_inspector.rb +112 -0
  18. data/lib/boson/option_command.rb +71 -154
  19. data/lib/boson/option_parser.rb +178 -173
  20. data/lib/boson/options.rb +46 -32
  21. data/lib/boson/runner.rb +58 -66
  22. data/lib/boson/runner_library.rb +31 -0
  23. data/lib/boson/scientist.rb +48 -81
  24. data/lib/boson/util.rb +46 -61
  25. data/lib/boson/version.rb +1 -1
  26. data/test/bin_runner_test.rb +53 -191
  27. data/test/command_test.rb +5 -9
  28. data/test/deps.rip +2 -2
  29. data/test/loader_test.rb +18 -216
  30. data/test/manager_test.rb +69 -79
  31. data/test/method_inspector_test.rb +12 -36
  32. data/test/option_parser_test.rb +45 -32
  33. data/test/runner_library_test.rb +10 -0
  34. data/test/runner_test.rb +158 -28
  35. data/test/scientist_test.rb +9 -147
  36. data/test/test_helper.rb +87 -52
  37. metadata +30 -72
  38. data/deps.rip +0 -2
  39. data/lib/boson/commands.rb +0 -7
  40. data/lib/boson/commands/core.rb +0 -77
  41. data/lib/boson/commands/web_core.rb +0 -153
  42. data/lib/boson/index.rb +0 -48
  43. data/lib/boson/inspectors/argument_inspector.rb +0 -97
  44. data/lib/boson/inspectors/comment_inspector.rb +0 -100
  45. data/lib/boson/inspectors/method_inspector.rb +0 -98
  46. data/lib/boson/libraries/file_library.rb +0 -144
  47. data/lib/boson/libraries/gem_library.rb +0 -30
  48. data/lib/boson/libraries/local_file_library.rb +0 -30
  49. data/lib/boson/libraries/module_library.rb +0 -37
  50. data/lib/boson/libraries/require_library.rb +0 -23
  51. data/lib/boson/namespace.rb +0 -31
  52. data/lib/boson/pipe.rb +0 -147
  53. data/lib/boson/pipes.rb +0 -75
  54. data/lib/boson/repo.rb +0 -107
  55. data/lib/boson/runners/bin_runner.rb +0 -208
  56. data/lib/boson/runners/console_runner.rb +0 -58
  57. data/lib/boson/view.rb +0 -95
  58. data/test/argument_inspector_test.rb +0 -62
  59. data/test/commands_test.rb +0 -22
  60. data/test/comment_inspector_test.rb +0 -126
  61. data/test/file_library_test.rb +0 -42
  62. data/test/pipes_test.rb +0 -65
  63. data/test/repo_index_test.rb +0 -122
  64. data/test/repo_test.rb +0 -23
data/test/command_test.rb CHANGED
@@ -2,21 +2,17 @@ require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
3
  describe "Command" do
4
4
  describe ".find" do
5
- before_all {
5
+ before do
6
6
  reset_boson
7
- Boson.libraries << Library.new(:name=>'bling', :namespace=>true)
8
- @namespace_command = Command.new(:name=>'blah', :lib=>'bling', :namespace=>'bling')
9
- @top_level_command = Command.new(:name=>'blah', :lib=>'bling')
10
- Boson.commands << @namespace_command
11
- Boson.commands << @top_level_command
12
- }
7
+ @top_level_command = create_command(:name=>'blah', :lib=>'bling')
8
+ end
13
9
 
14
10
  it 'finds correct command when a subcommand of the same name exists' do
15
11
  Command.find('blah').should == @top_level_command
16
12
  end
17
13
 
18
- it 'finds correct command when a top level command of the same name exists' do
19
- Command.find('bling.blah').should == @namespace_command
14
+ it 'finds nothing given nil' do
15
+ Command.find(nil).should == nil
20
16
  end
21
17
  end
22
18
  end
data/test/deps.rip CHANGED
@@ -1,5 +1,5 @@
1
- mocha =0.9.8
1
+ mocha ~>0.10.4
2
2
  bacon >=1.1.0
3
3
  mocha-on-bacon >=0
4
4
  bacon-bits >=0
5
- rake >=0
5
+ bahia >=0.4.0
data/test/loader_test.rb CHANGED
@@ -1,235 +1,37 @@
1
1
  require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
3
  describe "Loader" do
4
- def load_namespace_library
5
- Manager.load([Boson::Commands::Namespace])
6
- end
7
-
8
- before { Gem.stubs(:loaded_specs).returns({}) } if RUBY_VERSION >= '1.9.2' && defined? Gem
9
- describe "config" do
10
- before { reset }
11
- it "from callback overridden by user's config" do
12
- with_config(:libraries=>{'blih'=>{:namespace=>false}}) do
13
- load :blih, :file_string=>"module Blah; def self.config; {:namespace=>'bling'}; end; end"
14
- library('blih').namespace.should == false
15
- end
16
- end
17
-
18
- # if this test fails, other exists? using methods fail
19
- it "from callback recursively merges with user's config" do
20
- with_config(:libraries=>{'blah'=>{:commands=>{'bling'=>{:desc=>'bling', :options=>{:num=>3}}}}}) do
21
- File.stubs(:exists?).returns(true)
22
- load :blah, :file_string=> "module Blah; def self.config; {:commands=>{'blang'=>{:alias=>'ba'}, " +
23
- "'bling'=>{:options=>{:verbose=>:boolean}}}}; end; end"
24
- library('blah').command_object('bling').options.should == {:verbose=>:boolean, :num=>3}
25
- library('blah').command_object('bling').desc.should == 'bling'
26
- library('blah').command_object('blang').alias.should == 'ba'
27
- end
28
- end
29
-
30
- it "non-hash from inspector overridden by user's config" do
31
- with_config(:libraries=>{'blah'=>{:commands=>{'bling'=>{:desc=>'already'}}}}) do
32
- load :blah, :file_string=>"module Blah; #from file\ndef bling; end; end"
33
- library('blah').command_object('bling').desc.should == 'already'
34
- end
35
- end
36
-
37
- it "from inspector attribute config sets command's config" do
38
- load :blah, :file_string=>"module Blah; config :alias=>'ok'\n; def bling; end; end"
39
- library('blah').command_object('bling').alias.should == 'ok'
40
- end
41
-
42
- it "hash from inspector recursively merged with user's config" do
43
- with_config(:libraries=>{'blah'=>{:commands=>{'blung'=>{:args=>[], :render_options=>{:sort=>'this'}}}}}) do
44
- CommentInspector.expects(:scrape).returns({:render_options=>{:fields=>['this']}})
45
- load :blah, :file_string=>"module Blah; def blung; end; end"
46
- library('blah').command_object('blung').render_options.should == {:fields=>["this"], :sort=>"this"}
47
- end
48
- end
49
- end
50
-
51
4
  describe "load" do
52
5
  before { reset }
53
- it "calls included callback" do
54
- capture_stdout {
55
- load :blah, :file_string=>"module Blah; def self.included(mod); puts 'included blah'; end; def blah; end; end"
56
- }.should =~ /included blah/
57
- end
58
6
 
59
- it "calls after_included callback" do
60
- capture_stdout {
61
- load :blah, :file_string=>"module Blah; def self.after_included; puts 'yo'; end; end"
62
- }.should == "yo\n"
7
+ it "prints error for method conflicts with main_object method" do
8
+ runner = create_runner :require
9
+ manager_load runner
10
+ stderr.should =~ /Unable to load library Blarg.*conflict.*commands: require/
63
11
  end
64
12
 
65
- it "prints error if library module conflicts with top level constant/module" do
66
- capture_stderr {
67
- load :blah, :file_string=>"module Object; def self.blah; end; end"
68
- }.should =~ /conflict.*'Object'/
69
- library_loaded?('blah')
13
+ it "prints error for method conflicts between libraries" do
14
+ create_runner :whoops
15
+ create_runner :whoops, library: :Blorg
16
+ Manager.load Blarg
17
+ manager_load Blorg
18
+ stderr.should =~ /^Unable to load library Blorg.*conflict.*commands: whoops/
70
19
  end
71
20
 
72
- it "prints error and returns false for existing library" do
73
- libs = create_library('blah', :loaded=>true)
74
- Manager.stubs(:loader_create).returns(libs[0])
75
- capture_stderr { load('blah', :no_mock=>true, :verbose=>true).should == false }.should =~ /already exists/
21
+ it "sets loaded to true after loading a library" do
22
+ Manager.load create_runner
23
+ library('blarg').loaded.should == true
76
24
  end
77
25
 
78
26
  it "loads and strips aliases from a library's commands" do
79
27
  with_config(:command_aliases=>{"blah"=>'b'}) do
80
- load :blah, :file_string=>"module Blah; def blah; end; alias_method(:b, :blah); end"
81
- library_loaded?('blah')
82
- library('blah').commands.should == ['blah']
83
- end
84
- end
85
-
86
- it "loads a library and creates its class commands" do
87
- with_config(:libraries=>{"blah"=>{:class_commands=>{"bling"=>"Blah.bling", "Blah"=>['hmm']}}}) do
88
- load :blah, :file_string=>"module Blah; def self.bling; end; def self.hmm; end; end"
89
- command_exists? 'bling'
90
- command_exists? 'hmm'
91
- end
92
- end
93
-
94
- it "loads a library with dependencies" do
95
- File.stubs(:exists?).returns(true)
96
- File.stubs(:read).returns("module Water; def water; end; end", "module Oaks; def oaks; end; end")
97
- with_config(:libraries=>{"water"=>{:dependencies=>"oaks"}}) do
98
- load 'water', :no_mock=>true
99
- library_has_module('water', "Boson::Commands::Water")
100
- library_has_module('oaks', "Boson::Commands::Oaks")
101
- command_exists?('water')
102
- command_exists?('oaks')
103
- end
104
- end
105
-
106
- it "prints error for library with invalid dependencies" do
107
- GemLibrary.stubs(:is_a_gem?).returns(true) #mock all as gem libs
108
- Util.stubs(:safe_require).returns(true)
109
- with_config(:libraries=>{"water"=>{:dependencies=>"fire"}, "fire"=>{:dependencies=>"man"}}) do
110
- capture_stderr {
111
- load('water', :no_mock=>true)
112
- }.should == "Unable to load library fire. Reason: Can't load dependency man\nUnable to load"+
113
- " library water. Reason: Can't load dependency fire\n"
114
- end
115
- end
116
-
117
- it "prints error for method conflicts with main_object method" do
118
- with_config(:error_method_conflicts=>true) do
119
- capture_stderr {
120
- load('blah', :file_string=>"module Blah; def require; end; end")
121
- }.should =~ /Unable to load library blah.*conflict.*require/
122
- end
123
- end
124
-
125
- it "prints error for method conflicts with config error_method_conflicts" do
126
- with_config(:error_method_conflicts=>true) do
127
- load('blah', :file_string=>"module Blah; def chwhat; end; end")
128
- capture_stderr {
129
- load('chwhat', :file_string=>"module Chwhat; def chwhat; end; end")
130
- }.should =~ /Unable to load library chwhat.*conflict.*chwhat/
131
- end
132
- end
133
-
134
- it "namespaces a library that has a method conflict" do
135
- load('blah', :file_string=>"module Blah; def chwhat; end; end")
136
- capture_stderr {
137
- load('chwhat2', :file_string=>"module Chwhat2; def chwhat; end; end")
138
- }.should =~ /conflict.*chwhat.*chwhat2/
139
- library_has_command('namespace', 'chwhat2')
140
- library_has_command('chwhat2', 'chwhat')
141
- end
142
-
143
- describe "module library" do
144
- def mock_library(*args); end
145
-
146
- it "loads a module library and all its class methods by default" do
147
- eval %[module ::Harvey; def self.bird; end; def self.eagle; end; end]
148
- load ::Harvey, :no_mock=>true
149
- library_has_command('harvey', 'bird')
150
- library_has_command('harvey', 'eagle')
151
- end
152
-
153
- it "loads a module library with specified commands" do
154
- eval %[module ::Peanut; def self.bird; end; def self.eagle; end; end]
155
- load ::Peanut, :no_mock=>true, :commands=>%w{bird}
156
- library('peanut').commands.size.should == 1
157
- library_has_command('peanut', 'bird')
158
- end
159
-
160
- it "loads a module library as a class" do
161
- eval %[class ::Mentok; def self.bird; end; def self.eagle; end; end]
162
- load ::Mentok, :no_mock=>true, :commands=>%w{bird}
163
- library('mentok').commands.size.should == 1
164
- library_has_command('mentok', 'bird')
165
- end
166
- end
167
-
168
- describe "gem library" do
169
- def mock_library(lib, options={})
170
- options[:file_string] ||= ''
171
- File.stubs(:exists?).returns(false)
172
- GemLibrary.expects(:is_a_gem?).returns(true)
173
- Util.expects(:safe_require).with { eval options.delete(:file_string) || ''; true}.returns(true)
174
- end
175
-
176
- it "loads" do
177
- with_config(:libraries=>{"dude"=>{:module=>'Dude'}}) do
178
- load "dude", :file_string=>"module ::Dude; def blah; end; end"
179
- library_has_module('dude', "Dude")
180
- command_exists?("blah")
181
- end
182
- end
183
-
184
- it "with kernel methods loads" do
185
- load "dude", :file_string=>"module ::Kernel; def dude; end; end"
186
- library_loaded? 'dude'
187
- library('dude').module.should == nil
188
- command_exists?("dude")
189
- end
190
-
191
- it "prints error when nonexistent" do
192
- capture_stderr { load('blah') }.should =~ /Library blah did not/
193
- end
194
-
195
- it "with invalid module prints error" do
196
- with_config(:libraries=>{"coolio"=>{:module=>"Cool"}}) do
197
- capture_stderr {
198
- load('coolio', :file_string=>"module ::Coolio; def coolio; end; end")
199
- }.should =~ /Unable.*coolio.*No module/
28
+ runner = create_runner do
29
+ def blah; end
30
+ alias :b :blah
200
31
  end
32
+ Manager.load runner
33
+ library('blarg').commands.should == ['blah']
201
34
  end
202
35
  end
203
36
  end
204
-
205
- describe "library with namespace" do
206
- before_all { reset_main_object }
207
- before { reset_boson }
208
-
209
- it "loads and defaults to library name" do
210
- with_config(:libraries=>{'blang'=>{:namespace=>true}}) do
211
- load 'blang', :file_string=>"module Blang; def bling; end; end"
212
- library_has_command('blang', 'bling')
213
- end
214
- end
215
-
216
- it "loads with config namespace" do
217
- with_config(:libraries=>{'blung'=>{:namespace=>'dope'}}) do
218
- load 'blung', :file_string=>"module Blung; def bling; end; end"
219
- library_has_command('blung', 'bling')
220
- library('blung').commands.size.should == 1
221
- end
222
- end
223
-
224
- it "prints error if namespace conflicts with existing commands" do
225
- eval "module ::Conflict; def self.bleng; end; end"
226
- load Conflict, :no_mock=>true
227
- with_config(:libraries=>{'bleng'=>{:namespace=>true}}) do
228
- capture_stderr {
229
- load 'bleng', :file_string=>"module Bleng; def bling; end; end"
230
- }.should =~ /conflict.*bleng/
231
- end
232
- end
233
- end
234
- after_all { FileUtils.rm_r File.dirname(__FILE__)+'/commands/', :force=>true }
235
37
  end
data/test/manager_test.rb CHANGED
@@ -1,114 +1,104 @@
1
1
  require File.join(File.dirname(__FILE__), 'test_helper')
2
2
 
3
3
  describe "Manager" do
4
- describe ".after_load" do
5
- def load_library(hash)
6
- new_attributes = {:name=>hash[:name], :commands=>[], :created_dependencies=>[], :loaded=>true}
7
- [:module, :commands].each {|e| new_attributes[e] = hash.delete(e) if hash[e] }
8
- Manager.expects(:rescue_load_action).returns(Library.new(new_attributes))
9
- Manager.load([hash[:name]])
10
- end
4
+ def manager
5
+ Manager.instance
6
+ end
7
+
8
+ before do
9
+ reset_boson
10
+ Manager.instance = nil
11
+ end
11
12
 
12
- before { reset_boson }
13
+ describe ".load" do
14
+ def load_library(hash={})
15
+ meths = hash.delete(:commands) || []
16
+ manager_load create_runner(*(meths + [{library: :Blah}])), hash
17
+ end
13
18
 
14
19
  it "loads basic library" do
15
- load_library :name=>'blah'
20
+ load_library
16
21
  library_loaded? 'blah'
17
22
  end
18
23
 
19
- it "loads library with commands" do
20
- load_library :name=>'blah', :commands=>['frylock','meatwad']
24
+ it "loads basic library with verbose" do
25
+ capture_stdout {
26
+ load_library verbose: true
27
+ }.chomp.should == 'Loaded library blah'
21
28
  library_loaded? 'blah'
22
- command_exists?('frylock')
23
- command_exists?('meatwad')
24
29
  end
25
30
 
26
- it "prints error for library with SyntaxError" do
27
- Manager.expects(:loader_create).raises(SyntaxError)
28
- capture_stderr {
29
- Manager.load 'blah'
30
- }.should =~ /Unable to load library blah. Reason: SyntaxError/
31
+ it "loads library with commands" do
32
+ load_library :commands=>['frylock','meatwad']
33
+ library_loaded? 'blah'
34
+ library_has_command 'blah', 'frylock'
35
+ library_has_command 'blah', 'meatwad'
31
36
  end
32
37
 
33
- it "prints error for library with LoadError" do
34
- Manager.expects(:loader_create).raises(LoadError)
35
- capture_stderr {
36
- Manager.load 'blah'
37
- }.should =~ /Unable to load library blah. Reason: LoadError/
38
+ it "prints error if library does not load" do
39
+ RunnerLibrary.any_instance.expects(:load).returns false
40
+ load_library
41
+ stderr.should == "Library blah did not load successfully."
38
42
  end
39
43
 
40
- describe "command aliases" do
41
- before { eval %[module ::Aquateen; def frylock; end; end] }
42
- after { Object.send(:remove_const, "Aquateen") }
43
-
44
- it "created with command specific config" do
45
- with_config(:command_aliases=>{'frylock'=>'fr'}) do
46
- Manager.expects(:create_instance_aliases).with({"Aquateen"=>{"frylock"=>"fr"}})
47
- load_library :name=>'aquateen', :commands=>['frylock'], :module=>Aquateen
48
- library_loaded? 'aquateen'
49
- end
44
+ [SyntaxError, StandardError, LoaderError].each do |klass|
45
+ it "prints error if library fails with #{klass}" do
46
+ RunnerLibrary.expects(:new).raises(klass)
47
+ load_library
48
+ stderr.should == "Unable to load library Blah. Reason: #{klass}"
49
+ manager.failed_libraries.should == [Blah]
50
50
  end
51
+ end
51
52
 
52
- it "created with config command_aliases" do
53
- with_config(:command_aliases=>{"frylock"=>"fr"}) do
54
- Manager.expects(:create_instance_aliases).with({"Aquateen"=>{"frylock"=>"fr"}})
55
- load_library :name=>'aquateen', :commands=>['frylock'], :module=>Aquateen
56
- library_loaded? 'aquateen'
57
- end
53
+ [SyntaxError, StandardError].each do |klass|
54
+ it "with verbose prints verbose error if library fails with #{klass}" do
55
+ RunnerLibrary.expects(:new).raises(klass)
56
+ load_library verbose: true
57
+ stderr.should =~ /^Unable to load library Blah. Reason: #{klass}\n\s*\//
58
+ manager.failed_libraries.should == [Blah]
58
59
  end
60
+ end
59
61
 
60
- it "not created and warns for commands with no module" do
61
- with_config(:command_aliases=>{'frylock'=>'fr'}) do
62
- capture_stderr {
63
- load_library(:name=>'aquateen', :commands=>['frylock'])
64
- }.should =~ /No aliases/
65
- library_loaded? 'aquateen'
66
- Aquateen.method_defined?(:fr).should == false
67
- end
68
- end
62
+ it "prints error if no library is found" do
63
+ manager_load 'dude'
64
+ stderr.should ==
65
+ 'Unable to load library dude. Reason: Library dude not found.'
66
+ end
67
+
68
+ it "prints error for library that's already loaded" do
69
+ runner = create_runner
70
+ Manager.load runner
71
+ manager_load runner, verbose: true
72
+ stderr.should == "Library blarg already exists."
69
73
  end
70
74
 
71
75
  it "merges with existing created library" do
72
- create_library('blah')
73
- load_library :name=>'blah'
76
+ create_library(name: 'blah')
77
+ load_library
74
78
  library_loaded? 'blah'
75
79
  Boson.libraries.size.should == 1
76
80
  end
77
81
  end
78
82
 
79
- describe "option commands without args" do
80
- before_all {
81
- reset_boson
82
- @library = Library.new(:name=>'blah', :commands=>['foo', 'bar'])
83
- Boson.libraries << @library
84
- @foo = Command.new(:name=>'foo', :lib=>'blah', :options=>{:fool=>:string}, :args=>'*')
85
- Boson.commands << @foo
86
- Boson.commands << Command.new(:name=>'bar', :lib=>'blah', :options=>{:bah=>:string})
87
- }
88
-
89
- it "are deleted" do
90
- Scientist.expects(:redefine_command).with(anything, @foo)
91
- Manager.redefine_commands(@library, @library.commands)
83
+ describe ".redefine_commands" do
84
+ before do
85
+ @library = create_library(:name=>'blah', :commands=>['foo', 'bar'])
86
+ @foo = create_command(name: 'foo', lib: 'blah', options: {fool: :string},
87
+ args: '*')
88
+ create_command(name: 'bar', lib: 'blah', options: {bah: :string})
92
89
  end
93
90
 
94
- it "are deleted and printed when verbose" do
91
+ it "only redefines commands with args" do
95
92
  Scientist.expects(:redefine_command).with(anything, @foo)
96
- @library.instance_eval("@options = {:verbose=>true}")
97
- capture_stdout { Manager.redefine_commands(@library, @library.commands) } =~ /options.*blah/
93
+ manager.redefine_commands(@library, @library.commands)
98
94
  end
99
- end
100
-
101
- describe ".loaded?" do
102
- before { reset_libraries }
103
95
 
104
- it "returns false when library isn't loaded" do
105
- create_library('blah')
106
- Manager.loaded?('blah').should == false
107
- end
108
-
109
- it "returns true when library is loaded" do
110
- create_library('blah', :loaded=>true)
111
- Manager.loaded?('blah').should == true
96
+ it "with verbose only redefines commands with args and prints rejected" do
97
+ Manager.instance.verbose = true
98
+ Scientist.expects(:redefine_command).with(anything, @foo)
99
+ capture_stdout {
100
+ manager.redefine_commands(@library, @library.commands)
101
+ }.should =~ /cannot have options.*bar/
112
102
  end
113
103
  end
114
- end
104
+ end