puppet-module 0.3.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 (159) hide show
  1. data/CHANGES.markdown +91 -0
  2. data/LICENSE +17 -0
  3. data/README.markdown +221 -0
  4. data/Rakefile +87 -0
  5. data/VERSION +1 -0
  6. data/bin/puppet-module +7 -0
  7. data/lib/puppet/module/tool.rb +124 -0
  8. data/lib/puppet/module/tool/applications.rb +18 -0
  9. data/lib/puppet/module/tool/applications/application.rb +83 -0
  10. data/lib/puppet/module/tool/applications/builder.rb +88 -0
  11. data/lib/puppet/module/tool/applications/checksummer.rb +38 -0
  12. data/lib/puppet/module/tool/applications/cleaner.rb +14 -0
  13. data/lib/puppet/module/tool/applications/freezer.rb +20 -0
  14. data/lib/puppet/module/tool/applications/generator.rb +117 -0
  15. data/lib/puppet/module/tool/applications/installer.rb +83 -0
  16. data/lib/puppet/module/tool/applications/registrar.rb +34 -0
  17. data/lib/puppet/module/tool/applications/releaser.rb +48 -0
  18. data/lib/puppet/module/tool/applications/searcher.rb +34 -0
  19. data/lib/puppet/module/tool/applications/unpacker.rb +69 -0
  20. data/lib/puppet/module/tool/applications/unreleaser.rb +42 -0
  21. data/lib/puppet/module/tool/cache.rb +56 -0
  22. data/lib/puppet/module/tool/checksums.rb +52 -0
  23. data/lib/puppet/module/tool/cli.rb +127 -0
  24. data/lib/puppet/module/tool/contents_description.rb +84 -0
  25. data/lib/puppet/module/tool/dependency.rb +26 -0
  26. data/lib/puppet/module/tool/metadata.rb +80 -0
  27. data/lib/puppet/module/tool/modulefile.rb +47 -0
  28. data/lib/puppet/module/tool/repository.rb +74 -0
  29. data/lib/puppet/module/tool/skeleton.rb +39 -0
  30. data/lib/puppet/module/tool/utils.rb +9 -0
  31. data/lib/puppet/module/tool/utils/interrogation.rb +39 -0
  32. data/lib/puppet/module/tool/utils/settings.rb +36 -0
  33. data/lib/puppet/module/tool/utils/uri.rb +16 -0
  34. data/spec/fixtures/releases/jamtur01-apache/Modulefile +2 -0
  35. data/spec/fixtures/releases/jamtur01-apache/files/httpd +24 -0
  36. data/spec/fixtures/releases/jamtur01-apache/files/test.vhost +18 -0
  37. data/spec/fixtures/releases/jamtur01-apache/lib/puppet/provider/a2mod/debian.rb +21 -0
  38. data/spec/fixtures/releases/jamtur01-apache/lib/puppet/type/a2mod.rb +12 -0
  39. data/spec/fixtures/releases/jamtur01-apache/manifests/dev.pp +5 -0
  40. data/spec/fixtures/releases/jamtur01-apache/manifests/init.pp +34 -0
  41. data/spec/fixtures/releases/jamtur01-apache/manifests/params.pp +17 -0
  42. data/spec/fixtures/releases/jamtur01-apache/manifests/php.pp +5 -0
  43. data/spec/fixtures/releases/jamtur01-apache/manifests/ssl.pp +15 -0
  44. data/spec/fixtures/releases/jamtur01-apache/manifests/vhost.pp +15 -0
  45. data/spec/fixtures/releases/jamtur01-apache/metadata.json +1 -0
  46. data/spec/fixtures/releases/jamtur01-apache/templates/vhost-default.conf.erb +20 -0
  47. data/spec/fixtures/releases/jamtur01-apache/tests/apache.pp +1 -0
  48. data/spec/fixtures/releases/jamtur01-apache/tests/dev.pp +1 -0
  49. data/spec/fixtures/releases/jamtur01-apache/tests/init.pp +1 -0
  50. data/spec/fixtures/releases/jamtur01-apache/tests/php.pp +1 -0
  51. data/spec/fixtures/releases/jamtur01-apache/tests/ssl.pp +1 -0
  52. data/spec/fixtures/releases/jamtur01-apache/tests/vhost.pp +2 -0
  53. data/spec/integration/cli_spec.rb +373 -0
  54. data/spec/spec.opts +1 -0
  55. data/spec/spec_helper.rb +15 -0
  56. data/spec/support/output_support.rb +19 -0
  57. data/spec/support/stub_http_support.rb +14 -0
  58. data/spec/support/testdir_support.rb +26 -0
  59. data/spec/unit/application_spec.rb +25 -0
  60. data/spec/unit/repository_spec.rb +51 -0
  61. data/templates/generator/Modulefile.erb +5 -0
  62. data/templates/generator/README.erb +3 -0
  63. data/templates/generator/files/README.markdown +22 -0
  64. data/templates/generator/lib/puppet/facter/README.markdown +22 -0
  65. data/templates/generator/lib/puppet/parser/functions/README.markdown +17 -0
  66. data/templates/generator/lib/puppet/provider/README.markdown +14 -0
  67. data/templates/generator/lib/puppet/type/README.markdown +14 -0
  68. data/templates/generator/manifests/README.markdown +28 -0
  69. data/templates/generator/manifests/init.pp.erb +17 -0
  70. data/templates/generator/metadata.json +12 -0
  71. data/templates/generator/spec/README.markdown +7 -0
  72. data/templates/generator/spec/spec.opts +6 -0
  73. data/templates/generator/spec/spec_helper.rb +18 -0
  74. data/templates/generator/spec/unit/puppet/provider/README.markdown +4 -0
  75. data/templates/generator/spec/unit/puppet/type/README.markdown +4 -0
  76. data/templates/generator/templates/README.markdown +23 -0
  77. data/templates/generator/tests/init.pp.erb +1 -0
  78. data/vendor/facets-2.8.2-partial/lib/facets/kernel/returning.rb +23 -0
  79. data/vendor/facets-2.8.2-partial/lib/facets/kernel/tap.rb +39 -0
  80. data/vendor/multipart-post-1.0/Manifest.txt +9 -0
  81. data/vendor/multipart-post-1.0/README.txt +61 -0
  82. data/vendor/multipart-post-1.0/Rakefile +21 -0
  83. data/vendor/multipart-post-1.0/lib/composite_io.rb +89 -0
  84. data/vendor/multipart-post-1.0/lib/multipartable.rb +13 -0
  85. data/vendor/multipart-post-1.0/lib/net/http/post/multipart.rb +27 -0
  86. data/vendor/multipart-post-1.0/lib/parts.rb +66 -0
  87. data/vendor/multipart-post-1.0/test/net/http/post/test_multipart.rb +55 -0
  88. data/vendor/multipart-post-1.0/test/test_composite_io.rb +50 -0
  89. data/vendor/thor-852190ae/CHANGELOG.rdoc +89 -0
  90. data/vendor/thor-852190ae/LICENSE +20 -0
  91. data/vendor/thor-852190ae/README.rdoc +297 -0
  92. data/vendor/thor-852190ae/REVISION +1 -0
  93. data/vendor/thor-852190ae/Thorfile +69 -0
  94. data/vendor/thor-852190ae/bin/rake2thor +86 -0
  95. data/vendor/thor-852190ae/bin/thor +6 -0
  96. data/vendor/thor-852190ae/lib/thor.rb +244 -0
  97. data/vendor/thor-852190ae/lib/thor/actions.rb +275 -0
  98. data/vendor/thor-852190ae/lib/thor/actions/create_file.rb +103 -0
  99. data/vendor/thor-852190ae/lib/thor/actions/directory.rb +91 -0
  100. data/vendor/thor-852190ae/lib/thor/actions/empty_directory.rb +134 -0
  101. data/vendor/thor-852190ae/lib/thor/actions/file_manipulation.rb +223 -0
  102. data/vendor/thor-852190ae/lib/thor/actions/inject_into_file.rb +104 -0
  103. data/vendor/thor-852190ae/lib/thor/base.rb +540 -0
  104. data/vendor/thor-852190ae/lib/thor/core_ext/file_binary_read.rb +9 -0
  105. data/vendor/thor-852190ae/lib/thor/core_ext/hash_with_indifferent_access.rb +75 -0
  106. data/vendor/thor-852190ae/lib/thor/core_ext/ordered_hash.rb +100 -0
  107. data/vendor/thor-852190ae/lib/thor/error.rb +30 -0
  108. data/vendor/thor-852190ae/lib/thor/group.rb +271 -0
  109. data/vendor/thor-852190ae/lib/thor/invocation.rb +180 -0
  110. data/vendor/thor-852190ae/lib/thor/parser.rb +4 -0
  111. data/vendor/thor-852190ae/lib/thor/parser/argument.rb +67 -0
  112. data/vendor/thor-852190ae/lib/thor/parser/arguments.rb +150 -0
  113. data/vendor/thor-852190ae/lib/thor/parser/option.rb +128 -0
  114. data/vendor/thor-852190ae/lib/thor/parser/options.rb +169 -0
  115. data/vendor/thor-852190ae/lib/thor/rake_compat.rb +66 -0
  116. data/vendor/thor-852190ae/lib/thor/runner.rb +314 -0
  117. data/vendor/thor-852190ae/lib/thor/shell.rb +83 -0
  118. data/vendor/thor-852190ae/lib/thor/shell/basic.rb +239 -0
  119. data/vendor/thor-852190ae/lib/thor/shell/color.rb +108 -0
  120. data/vendor/thor-852190ae/lib/thor/task.rb +102 -0
  121. data/vendor/thor-852190ae/lib/thor/util.rb +230 -0
  122. data/vendor/thor-852190ae/lib/thor/version.rb +3 -0
  123. data/vendor/thor-852190ae/spec/actions/create_file_spec.rb +170 -0
  124. data/vendor/thor-852190ae/spec/actions/directory_spec.rb +131 -0
  125. data/vendor/thor-852190ae/spec/actions/empty_directory_spec.rb +91 -0
  126. data/vendor/thor-852190ae/spec/actions/file_manipulation_spec.rb +271 -0
  127. data/vendor/thor-852190ae/spec/actions/inject_into_file_spec.rb +135 -0
  128. data/vendor/thor-852190ae/spec/actions_spec.rb +292 -0
  129. data/vendor/thor-852190ae/spec/base_spec.rb +263 -0
  130. data/vendor/thor-852190ae/spec/core_ext/hash_with_indifferent_access_spec.rb +43 -0
  131. data/vendor/thor-852190ae/spec/core_ext/ordered_hash_spec.rb +115 -0
  132. data/vendor/thor-852190ae/spec/fixtures/application.rb +2 -0
  133. data/vendor/thor-852190ae/spec/fixtures/bundle/execute.rb +6 -0
  134. data/vendor/thor-852190ae/spec/fixtures/bundle/main.thor +1 -0
  135. data/vendor/thor-852190ae/spec/fixtures/doc/%file_name%.rb.tt +1 -0
  136. data/vendor/thor-852190ae/spec/fixtures/doc/README +3 -0
  137. data/vendor/thor-852190ae/spec/fixtures/doc/config.rb +1 -0
  138. data/vendor/thor-852190ae/spec/fixtures/group.thor +83 -0
  139. data/vendor/thor-852190ae/spec/fixtures/invoke.thor +112 -0
  140. data/vendor/thor-852190ae/spec/fixtures/script.thor +140 -0
  141. data/vendor/thor-852190ae/spec/fixtures/task.thor +10 -0
  142. data/vendor/thor-852190ae/spec/group_spec.rb +171 -0
  143. data/vendor/thor-852190ae/spec/invocation_spec.rb +107 -0
  144. data/vendor/thor-852190ae/spec/parser/argument_spec.rb +47 -0
  145. data/vendor/thor-852190ae/spec/parser/arguments_spec.rb +64 -0
  146. data/vendor/thor-852190ae/spec/parser/option_spec.rb +202 -0
  147. data/vendor/thor-852190ae/spec/parser/options_spec.rb +292 -0
  148. data/vendor/thor-852190ae/spec/rake_compat_spec.rb +68 -0
  149. data/vendor/thor-852190ae/spec/runner_spec.rb +202 -0
  150. data/vendor/thor-852190ae/spec/shell/basic_spec.rb +205 -0
  151. data/vendor/thor-852190ae/spec/shell/color_spec.rb +41 -0
  152. data/vendor/thor-852190ae/spec/shell_spec.rb +34 -0
  153. data/vendor/thor-852190ae/spec/spec.opts +1 -0
  154. data/vendor/thor-852190ae/spec/spec_helper.rb +54 -0
  155. data/vendor/thor-852190ae/spec/task_spec.rb +69 -0
  156. data/vendor/thor-852190ae/spec/thor_spec.rb +237 -0
  157. data/vendor/thor-852190ae/spec/util_spec.rb +167 -0
  158. data/vendor/thor-852190ae/thor.gemspec +120 -0
  159. metadata +229 -0
@@ -0,0 +1,10 @@
1
+ # module: random
2
+
3
+ class Amazing < Thor
4
+ desc "describe NAME", "say that someone is amazing"
5
+ method_options :forcefully => :boolean
6
+ def describe(name, opts)
7
+ ret = "#{name} is amazing"
8
+ puts opts["forcefully"] ? ret.upcase : ret
9
+ end
10
+ end
@@ -0,0 +1,171 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+
3
+ describe Thor::Group do
4
+ describe "#start" do
5
+ it "invokes all the tasks under the Thor group" do
6
+ MyCounter.start(["1", "2", "--third", "3"]).must == [ 1, 2, 3 ]
7
+ end
8
+
9
+ it "uses argument default value" do
10
+ MyCounter.start(["1", "--third", "3"]).must == [ 1, 2, 3 ]
11
+ end
12
+
13
+ it "invokes all the tasks in the Thor group and his parents" do
14
+ BrokenCounter.start(["1", "2", "--third", "3"]).must == [ nil, 2, 3, false, 5 ]
15
+ end
16
+
17
+ it "raises an error if a required argument is added after a non-required" do
18
+ lambda {
19
+ MyCounter.argument(:foo, :type => :string)
20
+ }.must raise_error(ArgumentError, 'You cannot have "foo" as required argument after the non-required argument "second".')
21
+ end
22
+
23
+ it "raises when an exception happens within the task call" do
24
+ lambda { BrokenCounter.start(["1", "2", "--fail"]) }.must raise_error
25
+ end
26
+
27
+ it "raises an error when a Thor group task expects arguments" do
28
+ lambda { WhinyGenerator.start }.must raise_error(ArgumentError, /Are you sure it has arity equals to 0\?/)
29
+ end
30
+
31
+ it "invokes help message if any of the shortcuts is given" do
32
+ MyCounter.should_receive(:help)
33
+ MyCounter.start(["-h"])
34
+ end
35
+ end
36
+
37
+ describe "#desc" do
38
+ it "sets the description for a given class" do
39
+ MyCounter.desc.must == "Description:\n This generator run three tasks: one, two and three.\n"
40
+ end
41
+
42
+ it "can be inherited" do
43
+ BrokenCounter.desc.must == "Description:\n This generator run three tasks: one, two and three.\n"
44
+ end
45
+
46
+ it "can be nil" do
47
+ WhinyGenerator.desc.must be_nil
48
+ end
49
+ end
50
+
51
+ describe "#help" do
52
+ before(:each) do
53
+ @content = capture(:stdout){ MyCounter.help(Thor::Base.shell.new) }
54
+ end
55
+
56
+ it "provides usage information" do
57
+ @content.must =~ /my_counter N \[N\]/
58
+ end
59
+
60
+ it "shows description" do
61
+ @content.must =~ /Description:/
62
+ @content.must =~ /This generator run three tasks: one, two and three./
63
+ end
64
+
65
+ it "shows options information" do
66
+ @content.must =~ /Options/
67
+ @content.must =~ /\[\-\-third=THREE\]/
68
+ end
69
+ end
70
+
71
+ describe "#invoke" do
72
+ before(:each) do
73
+ @content = capture(:stdout){ E.start }
74
+ end
75
+
76
+ it "allows to invoke a class from the class binding" do
77
+ @content.must =~ /1\n2\n3\n4\n5\n/
78
+ end
79
+
80
+ it "shows invocation information to the user" do
81
+ @content.must =~ /invoke Defined/
82
+ end
83
+
84
+ it "uses padding on status generated by the invoked class" do
85
+ @content.must =~ /finished counting/
86
+ end
87
+
88
+ it "allows invocation to be configured with blocks" do
89
+ capture(:stdout) do
90
+ F.start.must == ["Valim, Jose"]
91
+ end
92
+ end
93
+
94
+ it "shows invoked options on help" do
95
+ content = capture(:stdout){ E.help(Thor::Base.shell.new) }
96
+ content.must =~ /Defined options:/
97
+ content.must =~ /\[--unused\]/
98
+ content.must =~ /# This option has no use/
99
+ end
100
+ end
101
+
102
+ describe "#invoke_from_option" do
103
+ describe "with default type" do
104
+ before(:each) do
105
+ @content = capture(:stdout){ G.start }
106
+ end
107
+
108
+ it "allows to invoke a class from the class binding by a default option" do
109
+ @content.must =~ /1\n2\n3\n4\n5\n/
110
+ end
111
+
112
+ it "does not invoke if the option is nil" do
113
+ capture(:stdout){ G.start(["--skip-invoked"]) }.must_not =~ /invoke/
114
+ end
115
+
116
+ it "prints a message if invocation cannot be found" do
117
+ content = capture(:stdout){ G.start(["--invoked", "unknown"]) }
118
+ content.must =~ /error unknown \[not found\]/
119
+ end
120
+
121
+ it "allows to invoke a class from the class binding by the given option" do
122
+ content = capture(:stdout){ G.start(["--invoked", "e"]) }
123
+ content.must =~ /invoke e/
124
+ end
125
+
126
+ it "shows invocation information to the user" do
127
+ @content.must =~ /invoke defined/
128
+ end
129
+
130
+ it "uses padding on status generated by the invoked class" do
131
+ @content.must =~ /finished counting/
132
+ end
133
+
134
+ it "shows invoked options on help" do
135
+ content = capture(:stdout){ G.help(Thor::Base.shell.new) }
136
+ content.must =~ /defined options:/
137
+ content.must =~ /\[--unused\]/
138
+ content.must =~ /# This option has no use/
139
+ end
140
+ end
141
+
142
+ describe "with boolean type" do
143
+ before(:each) do
144
+ @content = capture(:stdout){ H.start }
145
+ end
146
+
147
+ it "allows to invoke a class from the class binding by a default option" do
148
+ @content.must =~ /1\n2\n3\n4\n5\n/
149
+ end
150
+
151
+ it "does not invoke if the option is false" do
152
+ capture(:stdout){ H.start(["--no-defined"]) }.must_not =~ /invoke/
153
+ end
154
+
155
+ it "shows invocation information to the user" do
156
+ @content.must =~ /invoke defined/
157
+ end
158
+
159
+ it "uses padding on status generated by the invoked class" do
160
+ @content.must =~ /finished counting/
161
+ end
162
+
163
+ it "shows invoked options on help" do
164
+ content = capture(:stdout){ H.help(Thor::Base.shell.new) }
165
+ content.must =~ /defined options:/
166
+ content.must =~ /\[--unused\]/
167
+ content.must =~ /# This option has no use/
168
+ end
169
+ end
170
+ end
171
+ end
@@ -0,0 +1,107 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/spec_helper')
2
+ require 'thor/base'
3
+
4
+ describe Thor::Invocation do
5
+ describe "#invoke" do
6
+ it "invokes a task inside another task" do
7
+ capture(:stdout){ A.new.invoke(:two) }.must == "2\n3\n"
8
+ end
9
+
10
+ it "invokes a task just once" do
11
+ capture(:stdout){ A.new.invoke(:one) }.must == "1\n2\n3\n"
12
+ end
13
+
14
+ it "invokes a task just once even if they belongs to different classes" do
15
+ capture(:stdout){ Defined.new.invoke(:one) }.must == "1\n2\n3\n4\n5\n"
16
+ end
17
+
18
+ it "invokes a task with arguments" do
19
+ A.new.invoke(:five, [5]).must be_true
20
+ A.new.invoke(:five, [7]).must be_false
21
+ end
22
+
23
+ it "invokes the default task if none is given to a Thor class" do
24
+ content = capture(:stdout){ A.new.invoke("b") }
25
+ content.must =~ /Tasks/
26
+ content.must =~ /LAST_NAME/
27
+ end
28
+
29
+ it "accepts a class as argument without a task to invoke" do
30
+ content = capture(:stdout){ A.new.invoke(B) }
31
+ content.must =~ /Tasks/
32
+ content.must =~ /LAST_NAME/
33
+ end
34
+
35
+ it "accepts a class as argument with a task to invoke" do
36
+ base = A.new([], :last_name => "Valim")
37
+ base.invoke(B, :one, ["Jose"]).must == "Valim, Jose"
38
+ end
39
+
40
+ it "accepts a Thor instance as argument" do
41
+ invoked = B.new([], :last_name => "Valim")
42
+ base = A.new
43
+ base.invoke(invoked, :one, ["Jose"]).must == "Valim, Jose"
44
+ base.invoke(invoked, :one, ["Jose"]).must be_nil
45
+ end
46
+
47
+ it "allows customized options to be given" do
48
+ base = A.new([], :last_name => "Wrong")
49
+ base.invoke(B, :one, ["Jose"], :last_name => "Valim").must == "Valim, Jose"
50
+ end
51
+
52
+ it "reparses options in the new class" do
53
+ A.start(["invoker", "--last-name", "Valim"]).must == "Valim, Jose"
54
+ end
55
+
56
+ it "shares initialize options with invoked class" do
57
+ A.new([], :foo => :bar).invoke("b:two").must == { "foo" => :bar }
58
+ end
59
+
60
+ it "dump configuration values to be used in the invoked class" do
61
+ base = A.new
62
+ base.invoke("b:three").shell.must == base.shell
63
+ end
64
+
65
+ it "allow extra configuration values to be given" do
66
+ base, shell = A.new, Thor::Base.shell.new
67
+ base.invoke("b:three", [], {}, :shell => shell).shell.must == shell
68
+ end
69
+
70
+ it "invokes a Thor::Group and all of its tasks" do
71
+ capture(:stdout){ A.new.invoke(:c) }.must == "1\n2\n3\n"
72
+ end
73
+
74
+ it "does not invoke a Thor::Group twice" do
75
+ base = A.new
76
+ silence(:stdout){ base.invoke(:c) }
77
+ capture(:stdout){ base.invoke(:c) }.must be_empty
78
+ end
79
+
80
+ it "does not invoke any of Thor::Group tasks twice" do
81
+ base = A.new
82
+ silence(:stdout){ base.invoke(:c) }
83
+ capture(:stdout){ base.invoke("c:one") }.must be_empty
84
+ end
85
+
86
+ it "raises Thor::UndefinedTaskError if the task can't be found" do
87
+ lambda do
88
+ A.new.invoke("foo:bar")
89
+ end.must raise_error(Thor::UndefinedTaskError)
90
+ end
91
+
92
+ it "raises Thor::UndefinedTaskError if the task can't be found even if all tasks where already executed" do
93
+ base = C.new
94
+ silence(:stdout){ base.invoke }
95
+
96
+ lambda do
97
+ base.invoke("foo:bar")
98
+ end.must raise_error(Thor::UndefinedTaskError)
99
+ end
100
+
101
+ it "raises an error if a non Thor class is given" do
102
+ lambda do
103
+ A.new.invoke(Object)
104
+ end.must raise_error(RuntimeError, "Expected Thor class, got Object")
105
+ end
106
+ end
107
+ end
@@ -0,0 +1,47 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
+ require 'thor/parser'
3
+
4
+ describe Thor::Argument do
5
+
6
+ def argument(name, type=:string, default=nil, required=nil)
7
+ @argument ||= Thor::Argument.new(name, nil, required || default.nil?, type, default)
8
+ end
9
+
10
+ describe "errors" do
11
+ it "raises an error if name is not supplied" do
12
+ lambda {
13
+ argument(nil)
14
+ }.must raise_error(ArgumentError, "Argument name can't be nil.")
15
+ end
16
+
17
+ it "raises an error if type is unknown" do
18
+ lambda {
19
+ argument(:task, :unknown)
20
+ }.must raise_error(ArgumentError, "Type :unknown is not valid for arguments.")
21
+ end
22
+
23
+ it "raises an error if argument is required and have default values" do
24
+ lambda {
25
+ argument(:task, :string, "bar", true)
26
+ }.must raise_error(ArgumentError, "An argument cannot be required and have default value.")
27
+ end
28
+ end
29
+
30
+ describe "#usage" do
31
+ it "returns usage for string types" do
32
+ argument(:foo, :string).usage.must == "FOO"
33
+ end
34
+
35
+ it "returns usage for numeric types" do
36
+ argument(:foo, :numeric).usage.must == "N"
37
+ end
38
+
39
+ it "returns usage for array types" do
40
+ argument(:foo, :array).usage.must == "one two three"
41
+ end
42
+
43
+ it "returns usage for hash types" do
44
+ argument(:foo, :hash).usage.must == "key:value"
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,64 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
+ require 'thor/parser'
3
+
4
+ describe Thor::Arguments do
5
+ def create(opts={})
6
+ arguments = opts.map do |type, default|
7
+ Thor::Argument.new(type.to_s, nil, default.nil?, type, default)
8
+ end
9
+
10
+ arguments.sort!{ |a,b| b.name <=> a.name }
11
+ @opt = Thor::Arguments.new(arguments)
12
+ end
13
+
14
+ def parse(*args)
15
+ @opt.parse(args)
16
+ end
17
+
18
+ describe "#parse" do
19
+ it "parses arguments in the given order" do
20
+ create :string => nil, :numeric => nil
21
+ parse("name", "13")["string"].must == "name"
22
+ parse("name", "13")["numeric"].must == 13
23
+ end
24
+
25
+ it "accepts hashes" do
26
+ create :string => nil, :hash => nil
27
+ parse("product", "title:string", "age:integer")["string"].must == "product"
28
+ parse("product", "title:string", "age:integer")["hash"].must == { "title" => "string", "age" => "integer"}
29
+ end
30
+
31
+ it "accepts arrays" do
32
+ create :string => nil, :array => nil
33
+ parse("product", "title", "age")["string"].must == "product"
34
+ parse("product", "title", "age")["array"].must == %w(title age)
35
+ end
36
+
37
+ describe "with no inputs" do
38
+ it "and no arguments returns an empty hash" do
39
+ create
40
+ parse.must == {}
41
+ end
42
+
43
+ it "and required arguments raises an error" do
44
+ create :string => nil, :numeric => nil
45
+ lambda { parse }.must raise_error(Thor::RequiredArgumentMissingError, "No value provided for required arguments 'string', 'numeric'")
46
+ end
47
+
48
+ it "and default arguments returns default values" do
49
+ create :string => "name", :numeric => 13
50
+ parse.must == { "string" => "name", "numeric" => 13 }
51
+ end
52
+ end
53
+
54
+ it "returns the input if it's already parsed" do
55
+ create :string => nil, :hash => nil, :array => nil, :numeric => nil
56
+ parse("", 0, {}, []).must == { "string" => "", "numeric" => 0, "hash" => {}, "array" => [] }
57
+ end
58
+
59
+ it "returns the default value if none is provided" do
60
+ create :string => "foo", :numeric => 3.0
61
+ parse("bar").must == { "string" => "bar", "numeric" => 3.0 }
62
+ end
63
+ end
64
+ end
@@ -0,0 +1,202 @@
1
+ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
2
+ require 'thor/parser'
3
+
4
+ describe Thor::Option do
5
+ def parse(key, value)
6
+ Thor::Option.parse(key, value)
7
+ end
8
+
9
+ def option(name, description=nil, required=false, type=nil, default=nil, banner=nil, group=nil, aliases=[])
10
+ @option ||= Thor::Option.new(name, description, required, type, default, banner, group, aliases)
11
+ end
12
+
13
+ describe "#parse" do
14
+
15
+ describe "with value as a symbol" do
16
+ describe "and symbol is a valid type" do
17
+ it "has type equals to the symbol" do
18
+ parse(:foo, :string).type.must == :string
19
+ parse(:foo, :numeric).type.must == :numeric
20
+ end
21
+
22
+ it "has not default value" do
23
+ parse(:foo, :string).default.must be_nil
24
+ parse(:foo, :numeric).default.must be_nil
25
+ end
26
+ end
27
+
28
+ describe "equals to :required" do
29
+ it "has type equals to :string" do
30
+ parse(:foo, :required).type.must == :string
31
+ end
32
+
33
+ it "has no default value" do
34
+ parse(:foo, :required).default.must be_nil
35
+ end
36
+ end
37
+
38
+ describe "and symbol is not a reserved key" do
39
+ it "has type equals to :string" do
40
+ parse(:foo, :bar).type.must == :string
41
+ end
42
+
43
+ it "has no default value" do
44
+ parse(:foo, :bar).default.must be_nil
45
+ end
46
+ end
47
+ end
48
+
49
+ describe "with value as hash" do
50
+ it "has default type :hash" do
51
+ parse(:foo, :a => :b).type.must == :hash
52
+ end
53
+
54
+ it "has default value equals to the hash" do
55
+ parse(:foo, :a => :b).default.must == { :a => :b }
56
+ end
57
+ end
58
+
59
+ describe "with value as array" do
60
+ it "has default type :array" do
61
+ parse(:foo, [:a, :b]).type.must == :array
62
+ end
63
+
64
+ it "has default value equals to the array" do
65
+ parse(:foo, [:a, :b]).default.must == [:a, :b]
66
+ end
67
+ end
68
+
69
+ describe "with value as string" do
70
+ it "has default type :string" do
71
+ parse(:foo, "bar").type.must == :string
72
+ end
73
+
74
+ it "has default value equals to the string" do
75
+ parse(:foo, "bar").default.must == "bar"
76
+ end
77
+ end
78
+
79
+ describe "with value as numeric" do
80
+ it "has default type :numeric" do
81
+ parse(:foo, 2.0).type.must == :numeric
82
+ end
83
+
84
+ it "has default value equals to the numeric" do
85
+ parse(:foo, 2.0).default.must == 2.0
86
+ end
87
+ end
88
+
89
+ describe "with value as boolean" do
90
+ it "has default type :boolean" do
91
+ parse(:foo, true).type.must == :boolean
92
+ parse(:foo, false).type.must == :boolean
93
+ end
94
+
95
+ it "has default value equals to the boolean" do
96
+ parse(:foo, true).default.must == true
97
+ parse(:foo, false).default.must == false
98
+ end
99
+ end
100
+
101
+ describe "with key as a symbol" do
102
+ it "sets the name equals to the key" do
103
+ parse(:foo, true).name.must == "foo"
104
+ end
105
+ end
106
+
107
+ describe "with key as an array" do
108
+ it "sets the first items in the array to the name" do
109
+ parse([:foo, :bar, :baz], true).name.must == "foo"
110
+ end
111
+
112
+ it "sets all other items as aliases" do
113
+ parse([:foo, :bar, :baz], true).aliases.must == [:bar, :baz]
114
+ end
115
+ end
116
+ end
117
+
118
+ it "returns the switch name" do
119
+ option("foo").switch_name.must == "--foo"
120
+ option("--foo").switch_name.must == "--foo"
121
+ end
122
+
123
+ it "returns the human name" do
124
+ option("foo").human_name.must == "foo"
125
+ option("--foo").human_name.must == "foo"
126
+ end
127
+
128
+ it "converts underscores to dashes" do
129
+ option("foo_bar").switch_name.must == "--foo-bar"
130
+ end
131
+
132
+ it "can be required and have default values" do
133
+ option = option("foo", nil, true, :string, "bar")
134
+ option.default.must == "bar"
135
+ option.must be_required
136
+ end
137
+
138
+ it "cannot be required and have type boolean" do
139
+ lambda {
140
+ option("foo", nil, true, :boolean)
141
+ }.must raise_error(ArgumentError, "An option cannot be boolean and required.")
142
+ end
143
+
144
+ it "allows type predicates" do
145
+ parse(:foo, :string).must be_string
146
+ parse(:foo, :boolean).must be_boolean
147
+ parse(:foo, :numeric).must be_numeric
148
+ end
149
+
150
+ it "raises an error on method missing" do
151
+ lambda {
152
+ parse(:foo, :string).unknown?
153
+ }.must raise_error(NoMethodError)
154
+ end
155
+
156
+ describe "#usage" do
157
+
158
+ it "returns usage for string types" do
159
+ parse(:foo, :string).usage.must == "[--foo=FOO]"
160
+ end
161
+
162
+ it "returns usage for numeric types" do
163
+ parse(:foo, :numeric).usage.must == "[--foo=N]"
164
+ end
165
+
166
+ it "returns usage for array types" do
167
+ parse(:foo, :array).usage.must == "[--foo=one two three]"
168
+ end
169
+
170
+ it "returns usage for hash types" do
171
+ parse(:foo, :hash).usage.must == "[--foo=key:value]"
172
+ end
173
+
174
+ it "returns usage for boolean types" do
175
+ parse(:foo, :boolean).usage.must == "[--foo]"
176
+ end
177
+
178
+ it "uses padding when no aliases is given" do
179
+ parse(:foo, :boolean).usage(4).must == " [--foo]"
180
+ end
181
+
182
+ it "uses banner when supplied" do
183
+ option(:foo, nil, false, :string, nil, "BAR").usage.must == "[--foo=BAR]"
184
+ end
185
+
186
+ it "checkes when banner is an empty string" do
187
+ option(:foo, nil, false, :string, nil, "").usage.must == "[--foo]"
188
+ end
189
+
190
+ describe "with required values" do
191
+ it "does not show the usage between brackets" do
192
+ parse(:foo, :required).usage.must == "--foo=FOO"
193
+ end
194
+ end
195
+
196
+ describe "with aliases" do
197
+ it "does not show the usage between brackets" do
198
+ parse([:foo, "-f", "-b"], :required).usage.must == "-f, -b, --foo=FOO"
199
+ end
200
+ end
201
+ end
202
+ end