capistrano 1.4.2 → 2.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 (113) hide show
  1. data/CHANGELOG +140 -4
  2. data/MIT-LICENSE +1 -1
  3. data/README +22 -14
  4. data/bin/cap +1 -8
  5. data/bin/capify +77 -0
  6. data/examples/sample.rb +10 -109
  7. data/lib/capistrano.rb +1 -0
  8. data/lib/capistrano/callback.rb +41 -0
  9. data/lib/capistrano/cli.rb +17 -317
  10. data/lib/capistrano/cli/execute.rb +82 -0
  11. data/lib/capistrano/cli/help.rb +102 -0
  12. data/lib/capistrano/cli/help.txt +53 -0
  13. data/lib/capistrano/cli/options.rb +183 -0
  14. data/lib/capistrano/cli/ui.rb +28 -0
  15. data/lib/capistrano/command.rb +62 -29
  16. data/lib/capistrano/configuration.rb +25 -226
  17. data/lib/capistrano/configuration/actions/file_transfer.rb +35 -0
  18. data/lib/capistrano/configuration/actions/inspect.rb +46 -0
  19. data/lib/capistrano/configuration/actions/invocation.rb +127 -0
  20. data/lib/capistrano/configuration/callbacks.rb +148 -0
  21. data/lib/capistrano/configuration/connections.rb +159 -0
  22. data/lib/capistrano/configuration/execution.rb +126 -0
  23. data/lib/capistrano/configuration/loading.rb +112 -0
  24. data/lib/capistrano/configuration/namespaces.rb +190 -0
  25. data/lib/capistrano/configuration/roles.rb +51 -0
  26. data/lib/capistrano/configuration/servers.rb +75 -0
  27. data/lib/capistrano/configuration/variables.rb +127 -0
  28. data/lib/capistrano/errors.rb +15 -0
  29. data/lib/capistrano/extensions.rb +27 -8
  30. data/lib/capistrano/gateway.rb +54 -29
  31. data/lib/capistrano/logger.rb +11 -11
  32. data/lib/capistrano/recipes/compat.rb +32 -0
  33. data/lib/capistrano/recipes/deploy.rb +483 -0
  34. data/lib/capistrano/recipes/deploy/dependencies.rb +44 -0
  35. data/lib/capistrano/recipes/deploy/local_dependency.rb +46 -0
  36. data/lib/capistrano/recipes/deploy/remote_dependency.rb +65 -0
  37. data/lib/capistrano/recipes/deploy/scm.rb +19 -0
  38. data/lib/capistrano/recipes/deploy/scm/base.rb +180 -0
  39. data/lib/capistrano/recipes/deploy/scm/bzr.rb +86 -0
  40. data/lib/capistrano/recipes/deploy/scm/cvs.rb +151 -0
  41. data/lib/capistrano/recipes/deploy/scm/darcs.rb +85 -0
  42. data/lib/capistrano/recipes/deploy/scm/mercurial.rb +129 -0
  43. data/lib/capistrano/recipes/deploy/scm/perforce.rb +126 -0
  44. data/lib/capistrano/recipes/deploy/scm/subversion.rb +103 -0
  45. data/lib/capistrano/recipes/deploy/strategy.rb +19 -0
  46. data/lib/capistrano/recipes/deploy/strategy/base.rb +64 -0
  47. data/lib/capistrano/recipes/deploy/strategy/checkout.rb +20 -0
  48. data/lib/capistrano/recipes/deploy/strategy/copy.rb +143 -0
  49. data/lib/capistrano/recipes/deploy/strategy/export.rb +20 -0
  50. data/lib/capistrano/recipes/deploy/strategy/remote.rb +52 -0
  51. data/lib/capistrano/recipes/deploy/strategy/remote_cache.rb +47 -0
  52. data/lib/capistrano/recipes/deploy/templates/maintenance.rhtml +53 -0
  53. data/lib/capistrano/recipes/standard.rb +26 -276
  54. data/lib/capistrano/recipes/templates/maintenance.rhtml +1 -1
  55. data/lib/capistrano/recipes/upgrade.rb +33 -0
  56. data/lib/capistrano/server_definition.rb +51 -0
  57. data/lib/capistrano/shell.rb +125 -81
  58. data/lib/capistrano/ssh.rb +80 -36
  59. data/lib/capistrano/task_definition.rb +69 -0
  60. data/lib/capistrano/upload.rb +146 -0
  61. data/lib/capistrano/version.rb +13 -17
  62. data/test/cli/execute_test.rb +132 -0
  63. data/test/cli/help_test.rb +139 -0
  64. data/test/cli/options_test.rb +226 -0
  65. data/test/cli/ui_test.rb +28 -0
  66. data/test/cli_test.rb +17 -0
  67. data/test/command_test.rb +284 -25
  68. data/test/configuration/actions/file_transfer_test.rb +40 -0
  69. data/test/configuration/actions/inspect_test.rb +62 -0
  70. data/test/configuration/actions/invocation_test.rb +195 -0
  71. data/test/configuration/callbacks_test.rb +206 -0
  72. data/test/configuration/connections_test.rb +288 -0
  73. data/test/configuration/execution_test.rb +159 -0
  74. data/test/configuration/loading_test.rb +119 -0
  75. data/test/configuration/namespace_dsl_test.rb +283 -0
  76. data/test/configuration/roles_test.rb +47 -0
  77. data/test/configuration/servers_test.rb +90 -0
  78. data/test/configuration/variables_test.rb +180 -0
  79. data/test/configuration_test.rb +60 -212
  80. data/test/deploy/scm/base_test.rb +55 -0
  81. data/test/deploy/strategy/copy_test.rb +146 -0
  82. data/test/extensions_test.rb +69 -0
  83. data/test/fixtures/cli_integration.rb +5 -0
  84. data/test/fixtures/custom.rb +2 -2
  85. data/test/gateway_test.rb +167 -0
  86. data/test/logger_test.rb +123 -0
  87. data/test/server_definition_test.rb +108 -0
  88. data/test/shell_test.rb +64 -0
  89. data/test/ssh_test.rb +67 -154
  90. data/test/task_definition_test.rb +101 -0
  91. data/test/upload_test.rb +131 -0
  92. data/test/utils.rb +31 -39
  93. data/test/version_test.rb +24 -0
  94. metadata +145 -98
  95. data/THANKS +0 -4
  96. data/lib/capistrano/actor.rb +0 -567
  97. data/lib/capistrano/generators/rails/deployment/deployment_generator.rb +0 -25
  98. data/lib/capistrano/generators/rails/deployment/templates/capistrano.rake +0 -49
  99. data/lib/capistrano/generators/rails/deployment/templates/deploy.rb +0 -122
  100. data/lib/capistrano/generators/rails/loader.rb +0 -20
  101. data/lib/capistrano/scm/base.rb +0 -61
  102. data/lib/capistrano/scm/baz.rb +0 -118
  103. data/lib/capistrano/scm/bzr.rb +0 -70
  104. data/lib/capistrano/scm/cvs.rb +0 -129
  105. data/lib/capistrano/scm/darcs.rb +0 -27
  106. data/lib/capistrano/scm/mercurial.rb +0 -83
  107. data/lib/capistrano/scm/perforce.rb +0 -139
  108. data/lib/capistrano/scm/subversion.rb +0 -128
  109. data/lib/capistrano/transfer.rb +0 -97
  110. data/lib/capistrano/utils.rb +0 -26
  111. data/test/actor_test.rb +0 -402
  112. data/test/scm/cvs_test.rb +0 -196
  113. data/test/scm/subversion_test.rb +0 -145
@@ -0,0 +1,283 @@
1
+ require "#{File.dirname(__FILE__)}/../utils"
2
+ require 'capistrano/configuration/namespaces'
3
+
4
+ class ConfigurationNamespacesDSLTest < Test::Unit::TestCase
5
+ class MockConfig
6
+ attr_reader :original_initialize_called, :options
7
+
8
+ def initialize
9
+ @original_initialize_called = true
10
+ @options = {}
11
+ end
12
+
13
+ include Capistrano::Configuration::Namespaces
14
+ end
15
+
16
+ def setup
17
+ @config = MockConfig.new
18
+ end
19
+
20
+ def test_initialize_should_initialize_collections
21
+ assert @config.original_initialize_called
22
+ assert @config.tasks.empty?
23
+ assert @config.namespaces.empty?
24
+ end
25
+
26
+ def test_unqualified_task_should_define_task_at_top_namespace
27
+ assert !@config.tasks.key?(:testing)
28
+ @config.task(:testing) { puts "something" }
29
+ assert @config.tasks.key?(:testing)
30
+ end
31
+
32
+ def test_qualification_should_define_task_within_namespace
33
+ @config.namespace(:testing) do
34
+ task(:nested) { puts "nested" }
35
+ end
36
+
37
+ assert !@config.tasks.key?(:nested)
38
+ assert @config.namespaces.key?(:testing)
39
+ assert @config.namespaces[:testing].tasks.key?(:nested)
40
+ end
41
+
42
+ def test_namespace_within_namespace_should_define_task_within_nested_namespace
43
+ @config.namespace :outer do
44
+ namespace :inner do
45
+ task :nested do
46
+ puts "nested"
47
+ end
48
+ end
49
+ end
50
+
51
+ assert !@config.tasks.key?(:nested)
52
+ assert @config.namespaces.key?(:outer)
53
+ assert @config.namespaces[:outer].namespaces.key?(:inner)
54
+ assert @config.namespaces[:outer].namespaces[:inner].tasks.key?(:nested)
55
+ end
56
+
57
+ def test_pending_desc_should_apply_only_to_immediately_subsequent_task
58
+ @config.desc "A description"
59
+ @config.task(:testing) { puts "foo" }
60
+ @config.task(:another) { puts "bar" }
61
+ assert_equal "A description", @config.tasks[:testing].desc
62
+ assert_nil @config.tasks[:another].desc
63
+ end
64
+
65
+ def test_pending_desc_should_apply_only_to_next_task_in_any_namespace
66
+ @config.desc "A description"
67
+ @config.namespace(:outer) { task(:testing) { puts "foo" } }
68
+ assert_equal "A description", @config.namespaces[:outer].tasks[:testing].desc
69
+ end
70
+
71
+ def test_defining_task_without_block_should_raise_error
72
+ assert_raises(ArgumentError) do
73
+ @config.task(:testing)
74
+ end
75
+ end
76
+
77
+ def test_defining_task_that_shadows_existing_method_should_raise_error
78
+ assert_raises(ArgumentError) do
79
+ @config.task(:sprintf) { puts "foo" }
80
+ end
81
+ end
82
+
83
+ def test_defining_task_that_shadows_existing_namespace_should_raise_error
84
+ @config.namespace(:outer) {}
85
+ assert_raises(ArgumentError) do
86
+ @config.task(:outer) { puts "foo" }
87
+ end
88
+ end
89
+
90
+ def test_defining_namespace_that_shadows_existing_method_should_raise_error
91
+ assert_raises(ArgumentError) do
92
+ @config.namespace(:sprintf) {}
93
+ end
94
+ end
95
+
96
+ def test_defining_namespace_that_shadows_existing_task_should_raise_error
97
+ @config.task(:testing) { puts "foo" }
98
+ assert_raises(ArgumentError) do
99
+ @config.namespace(:testing) {}
100
+ end
101
+ end
102
+
103
+ def test_defining_task_that_shadows_existing_task_should_not_raise_error
104
+ @config.task(:original) { puts "foo" }
105
+ assert_nothing_raised do
106
+ @config.task(:original) { puts "bar" }
107
+ end
108
+ end
109
+
110
+ def test_defining_ask_should_add_task_as_method
111
+ assert !@config.methods.include?("original")
112
+ @config.task(:original) { puts "foo" }
113
+ assert @config.methods.include?("original")
114
+ end
115
+
116
+ def test_calling_defined_task_should_delegate_to_execute_task
117
+ @config.task(:original) { puts "foo" }
118
+ @config.expects(:execute_task).with(@config.tasks[:original])
119
+ @config.original
120
+ end
121
+
122
+ def test_role_inside_namespace_should_raise_error
123
+ assert_raises(NotImplementedError) do
124
+ @config.namespace(:outer) do
125
+ role :app, "hello"
126
+ end
127
+ end
128
+ end
129
+
130
+ def test_name_for_top_level_should_be_nil
131
+ assert_nil @config.name
132
+ end
133
+
134
+ def test_parent_for_top_level_should_be_nil
135
+ assert_nil @config.parent
136
+ end
137
+
138
+ def test_fqn_for_top_level_should_be_nil
139
+ assert_nil @config.fully_qualified_name
140
+ end
141
+
142
+ def test_fqn_for_namespace_should_be_the_name_of_the_namespace
143
+ @config.namespace(:outer) {}
144
+ assert_equal "outer", @config.namespaces[:outer].fully_qualified_name
145
+ end
146
+
147
+ def test_parent_for_namespace_should_be_the_top_level
148
+ @config.namespace(:outer) {}
149
+ assert_equal @config, @config.namespaces[:outer].parent
150
+ end
151
+
152
+ def test_fqn_for_nested_namespace_should_be_color_delimited
153
+ @config.namespace(:outer) { namespace(:inner) {} }
154
+ assert_equal "outer:inner", @config.namespaces[:outer].namespaces[:inner].fully_qualified_name
155
+ end
156
+
157
+ def test_parent_for_nested_namespace_should_be_the_nesting_namespace
158
+ @config.namespace(:outer) { namespace(:inner) {} }
159
+ assert_equal @config.namespaces[:outer], @config.namespaces[:outer].namespaces[:inner].parent
160
+ end
161
+
162
+ def test_find_task_should_dereference_nested_tasks
163
+ @config.namespace(:outer) do
164
+ namespace(:inner) { task(:nested) { puts "nested" } }
165
+ end
166
+
167
+ task = @config.find_task("outer:inner:nested")
168
+ assert_not_nil task
169
+ assert_equal "outer:inner:nested", task.fully_qualified_name
170
+ end
171
+
172
+ def test_find_task_should_return_nil_if_no_task_matches
173
+ assert_nil @config.find_task("outer:inner:nested")
174
+ end
175
+
176
+ def test_find_task_should_return_default_if_deferences_to_namespace_and_namespace_has_default
177
+ @config.namespace(:outer) do
178
+ namespace(:inner) { task(:default) { puts "nested" } }
179
+ end
180
+
181
+ task = @config.find_task("outer:inner")
182
+ assert_not_nil task
183
+ assert_equal :default, task.name
184
+ assert_equal "outer:inner", task.namespace.fully_qualified_name
185
+ end
186
+
187
+ def test_find_task_should_return_nil_if_deferences_to_namespace_and_namespace_has_no_default
188
+ @config.namespace(:outer) do
189
+ namespace(:inner) { task(:nested) { puts "nested" } }
190
+ end
191
+
192
+ assert_nil @config.find_task("outer:inner")
193
+ end
194
+
195
+ def test_default_task_should_return_nil_for_top_level
196
+ @config.task(:default) {}
197
+ assert_nil @config.default_task
198
+ end
199
+
200
+ def test_default_task_should_return_nil_for_namespace_without_default
201
+ @config.namespace(:outer) { task(:nested) { puts "nested" } }
202
+ assert_nil @config.namespaces[:outer].default_task
203
+ end
204
+
205
+ def test_default_task_should_return_task_for_namespace_with_default
206
+ @config.namespace(:outer) { task(:default) { puts "nested" } }
207
+ task = @config.namespaces[:outer].default_task
208
+ assert_not_nil task
209
+ assert_equal :default, task.name
210
+ end
211
+
212
+ def test_task_list_should_return_only_tasks_immediately_within_namespace
213
+ @config.task(:first) { puts "here" }
214
+ @config.namespace(:outer) do
215
+ task(:second) { puts "here" }
216
+ namespace(:inner) do
217
+ task(:third) { puts "here" }
218
+ end
219
+ end
220
+
221
+ assert_equal %w(first), @config.task_list.map { |t| t.fully_qualified_name }
222
+ end
223
+
224
+ def test_task_list_with_all_should_return_all_tasks_under_this_namespace_recursively
225
+ @config.task(:first) { puts "here" }
226
+ @config.namespace(:outer) do
227
+ task(:second) { puts "here" }
228
+ namespace(:inner) do
229
+ task(:third) { puts "here" }
230
+ end
231
+ end
232
+
233
+ assert_equal %w(first outer:inner:third outer:second), @config.task_list(:all).map { |t| t.fully_qualified_name }.sort
234
+ end
235
+
236
+ def test_namespace_should_respond_to_its_parents_methods
237
+ @config.namespace(:outer) {}
238
+ ns = @config.namespaces[:outer]
239
+ assert ns.respond_to?(:original_initialize_called)
240
+ end
241
+
242
+ def test_namespace_should_delegate_unknown_messages_to_its_parent
243
+ @config.namespace(:outer) {}
244
+ ns = @config.namespaces[:outer]
245
+ assert ns.original_initialize_called
246
+ end
247
+
248
+ def test_namespace_should_not_understand_messages_that_neither_it_nor_its_parent_understands
249
+ @config.namespace(:outer) {}
250
+ ns = @config.namespaces[:outer]
251
+ assert_raises(NoMethodError) { ns.alskdfjlsf }
252
+ end
253
+
254
+ def test_search_task_should_find_tasks_in_current_namespace
255
+ @config.namespace(:outer) do
256
+ namespace(:inner) do
257
+ task(:third) { puts "here" }
258
+ end
259
+ end
260
+
261
+ inner = @config.namespaces[:outer].namespaces[:inner]
262
+ assert_equal inner.tasks[:third], inner.search_task(:third)
263
+ end
264
+
265
+ def test_search_task_should_find_tasks_in_parent_namespace
266
+ @config.task(:first) { puts "here" }
267
+ @config.namespace(:outer) do
268
+ task(:second) { puts "here" }
269
+ namespace(:inner) do
270
+ task(:third) { puts "here" }
271
+ end
272
+ end
273
+
274
+ inner = @config.namespaces[:outer].namespaces[:inner]
275
+ assert_equal @config.tasks[:first], inner.search_task(:first)
276
+ end
277
+
278
+ def test_search_task_should_return_nil_if_no_tasks_are_found
279
+ @config.namespace(:outer) { namespace(:inner) {} }
280
+ inner = @config.namespaces[:outer].namespaces[:inner]
281
+ assert_nil inner.search_task(:first)
282
+ end
283
+ end
@@ -0,0 +1,47 @@
1
+ require "#{File.dirname(__FILE__)}/../utils"
2
+ require 'capistrano/configuration/roles'
3
+
4
+ class ConfigurationRolesTest < Test::Unit::TestCase
5
+ class MockConfig
6
+ attr_reader :original_initialize_called
7
+
8
+ def initialize
9
+ @original_initialize_called = true
10
+ end
11
+
12
+ include Capistrano::Configuration::Roles
13
+ end
14
+
15
+ def setup
16
+ @config = MockConfig.new
17
+ end
18
+
19
+ def test_initialize_should_initialize_roles_collection
20
+ assert @config.original_initialize_called
21
+ assert @config.roles.empty?
22
+ end
23
+
24
+ def test_role_should_allow_empty_list
25
+ @config.role :app
26
+ assert @config.roles[:app].empty?
27
+ end
28
+
29
+ def test_role_with_one_argument_should_add_to_roles_collection
30
+ @config.role :app, "app1.capistrano.test"
31
+ assert_equal [:app], @config.roles.keys
32
+ assert_equal %w(app1.capistrano.test), @config.roles[:app].map { |s| s.host }
33
+ end
34
+
35
+ def test_role_with_multiple_arguments_should_add_each_to_roles_collection
36
+ @config.role :app, "app1.capistrano.test", "app2.capistrano.test"
37
+ assert_equal [:app], @config.roles.keys
38
+ assert_equal %w(app1.capistrano.test app2.capistrano.test), @config.roles[:app].map { |s| s.host }
39
+ end
40
+
41
+ def test_role_with_options_should_apply_options_to_each_argument
42
+ @config.role :app, "app1.capistrano.test", "app2.capistrano.test", :extra => :value
43
+ @config.roles[:app].each do |server|
44
+ assert_equal({:extra => :value}, server.options)
45
+ end
46
+ end
47
+ end
@@ -0,0 +1,90 @@
1
+ require "#{File.dirname(__FILE__)}/../utils"
2
+ require 'capistrano/task_definition'
3
+ require 'capistrano/configuration/servers'
4
+
5
+ class ConfigurationServersTest < Test::Unit::TestCase
6
+ class MockConfig
7
+ attr_reader :roles
8
+
9
+ def initialize
10
+ @roles = {}
11
+ end
12
+
13
+ include Capistrano::Configuration::Servers
14
+ end
15
+
16
+ def setup
17
+ @config = MockConfig.new
18
+ role(@config, :app, "app1", :primary => true)
19
+ role(@config, :app, "app2", "app3")
20
+ role(@config, :web, "web1", "web2")
21
+ role(@config, :report, "app2", :no_deploy => true)
22
+ role(@config, :file, "file", :no_deploy => true)
23
+ end
24
+
25
+ def test_task_without_roles_should_apply_to_all_defined_hosts
26
+ task = new_task(:testing)
27
+ assert_equal %w(app1 app2 app3 web1 web2 file).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
28
+ end
29
+
30
+ def test_task_with_explicit_role_list_should_apply_only_to_those_roles
31
+ task = new_task(:testing, @config, :roles => %w(app web))
32
+ assert_equal %w(app1 app2 app3 web1 web2).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
33
+ end
34
+
35
+ def test_task_with_single_role_should_apply_only_to_that_role
36
+ task = new_task(:testing, @config, :roles => :web)
37
+ assert_equal %w(web1 web2).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
38
+ end
39
+
40
+ def test_task_with_hosts_option_should_apply_only_to_those_hosts
41
+ task = new_task(:testing, @config, :hosts => %w(foo bar))
42
+ assert_equal %w(foo bar).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
43
+ end
44
+
45
+ def test_task_with_single_hosts_option_should_apply_only_to_that_host
46
+ task = new_task(:testing, @config, :hosts => "foo")
47
+ assert_equal %w(foo).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
48
+ end
49
+
50
+ def test_task_with_roles_as_environment_variable_should_apply_only_to_that_role
51
+ ENV['ROLES'] = "app,file"
52
+ task = new_task(:testing)
53
+ assert_equal %w(app1 app2 app3 file).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
54
+ ensure
55
+ ENV['ROLES'] = nil
56
+ end
57
+
58
+ def test_task_with_hosts_as_environment_variable_should_apply_only_to_those_hosts
59
+ ENV['HOSTS'] = "foo,bar"
60
+ task = new_task(:testing)
61
+ assert_equal %w(foo bar).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
62
+ ensure
63
+ ENV['HOSTS'] = nil
64
+ end
65
+
66
+ def test_task_with_only_should_apply_only_to_matching_tasks
67
+ task = new_task(:testing, @config, :roles => :app, :only => { :primary => true })
68
+ assert_equal %w(app1), @config.find_servers_for_task(task).map { |s| s.host }
69
+ end
70
+
71
+ def test_task_with_except_should_apply_only_to_matching_tasks
72
+ task = new_task(:testing, @config, :except => { :no_deploy => true })
73
+ assert_equal %w(app1 app2 app3 web1 web2).sort, @config.find_servers_for_task(task).map { |s| s.host }.sort
74
+ end
75
+
76
+ def test_options_to_find_servers_for_task_should_override_options_in_task
77
+ task = new_task(:testing, @config, :roles => :web)
78
+ assert_equal %w(app1 app2 app3).sort, @config.find_servers_for_task(task, :roles => :app).map { |s| s.host }.sort
79
+ end
80
+
81
+ def test_find_servers_with_lambda_for_hosts_should_be_evaluated
82
+ assert_equal %w(foo), @config.find_servers(:hosts => lambda { "foo" }).map { |s| s.host }.sort
83
+ assert_equal %w(bar foo), @config.find_servers(:hosts => lambda { %w(foo bar) }).map { |s| s.host }.sort
84
+ end
85
+
86
+ def test_find_servers_with_lambda_for_roles_should_be_evaluated
87
+ assert_equal %w(app1 app2 app3), @config.find_servers(:roles => lambda { :app }).map { |s| s.host }.sort
88
+ assert_equal %w(app2 file), @config.find_servers(:roles => lambda { [:report, :file] }).map { |s| s.host }.sort
89
+ end
90
+ end
@@ -0,0 +1,180 @@
1
+ require "#{File.dirname(__FILE__)}/../utils"
2
+ require 'capistrano/configuration/variables'
3
+
4
+ class ConfigurationVariablesTest < Test::Unit::TestCase
5
+ class MockConfig
6
+ attr_reader :original_initialize_called
7
+
8
+ def initialize
9
+ @original_initialize_called = true
10
+ end
11
+
12
+ include Capistrano::Configuration::Variables
13
+ end
14
+
15
+ def setup
16
+ MockConfig.any_instance.stubs(:logger).returns(stub_everything)
17
+ @config = MockConfig.new
18
+ end
19
+
20
+ def test_initialize_should_initialize_variables_hash
21
+ assert @config.original_initialize_called
22
+ assert_equal({:ssh_options => {}, :logger => @config.logger}, @config.variables)
23
+ end
24
+
25
+ def test_set_should_add_variable_to_hash
26
+ @config.set :sample, :value
27
+ assert_equal :value, @config.variables[:sample]
28
+ end
29
+
30
+ def test_set_should_convert_variable_name_to_symbol
31
+ @config.set "sample", :value
32
+ assert_equal :value, @config.variables[:sample]
33
+ end
34
+
35
+ def test_set_should_be_aliased_to_square_brackets
36
+ @config[:sample] = :value
37
+ assert_equal :value, @config.variables[:sample]
38
+ end
39
+
40
+ def test_variables_should_be_accessible_as_read_accessors
41
+ @config[:sample] = :value
42
+ assert_equal :value, @config.sample
43
+ end
44
+
45
+ def test_method_missing_should_raise_error_if_no_variable_matches
46
+ assert_raises(NoMethodError) do
47
+ @config.sample
48
+ end
49
+ end
50
+
51
+ def test_respond_to_should_look_for_variables
52
+ assert !@config.respond_to?(:sample)
53
+ @config[:sample] = :value
54
+ assert @config.respond_to?(:sample)
55
+ end
56
+
57
+ def test_set_should_require_value
58
+ assert_raises(ArgumentError) do
59
+ @config.set(:sample)
60
+ end
61
+ end
62
+
63
+ def test_set_should_allow_value_to_be_omitted_if_block_is_given
64
+ assert_nothing_raised do
65
+ @config.set(:sample) { :value }
66
+ end
67
+ assert_instance_of Proc, @config.variables[:sample]
68
+ end
69
+
70
+ def test_set_should_not_allow_multiple_values
71
+ assert_raises(ArgumentError) do
72
+ @config.set(:sample, :value, :another)
73
+ end
74
+ end
75
+
76
+ def test_set_should_not_allow_both_a_value_and_a_block
77
+ assert_raises(ArgumentError) do
78
+ @config.set(:sample, :value) { :block }
79
+ end
80
+ end
81
+
82
+ def test_set_should_not_allow_capitalized_variables
83
+ assert_raises(ArgumentError) do
84
+ @config.set :Sample, :value
85
+ end
86
+ end
87
+
88
+ def test_unset_should_remove_variable_from_hash
89
+ @config.set :sample, :value
90
+ assert @config.variables.key?(:sample)
91
+ @config.unset :sample
92
+ assert !@config.variables.key?(:sample)
93
+ end
94
+
95
+ def test_unset_should_clear_memory_of_original_proc
96
+ @config.set(:sample) { :value }
97
+ @config.fetch(:sample)
98
+ @config.unset(:sample)
99
+ assert_equal false, @config.reset!(:sample)
100
+ end
101
+
102
+ def test_exists_should_report_existance_of_variable_in_hash
103
+ assert !@config.exists?(:sample)
104
+ @config[:sample] = :value
105
+ assert @config.exists?(:sample)
106
+ end
107
+
108
+ def test_reset_should_do_nothing_if_variable_does_not_exist
109
+ assert_equal false, @config.reset!(:sample)
110
+ assert !@config.variables.key?(:sample)
111
+ end
112
+
113
+ def test_reset_should_do_nothing_if_variable_is_not_a_proc
114
+ @config.set(:sample, :value)
115
+ assert_equal false, @config.reset!(:sample)
116
+ assert_equal :value, @config.variables[:sample]
117
+ end
118
+
119
+ def test_reset_should_do_nothing_if_proc_variable_has_not_been_dereferenced
120
+ @config.set(:sample) { :value }
121
+ assert_equal false, @config.reset!(:sample)
122
+ assert_instance_of Proc, @config.variables[:sample]
123
+ end
124
+
125
+ def test_reset_should_restore_variable_to_original_proc_value
126
+ @config.set(:sample) { :value }
127
+ assert_instance_of Proc, @config.variables[:sample]
128
+ @config.fetch(:sample)
129
+ assert_instance_of Symbol, @config.variables[:sample]
130
+ assert @config.reset!(:sample)
131
+ assert_instance_of Proc, @config.variables[:sample]
132
+ end
133
+
134
+ def test_fetch_should_return_stored_non_proc_value
135
+ @config.set(:sample, :value)
136
+ assert_equal :value, @config.fetch(:sample)
137
+ end
138
+
139
+ def test_fetch_should_raise_index_error_if_variable_does_not_exist
140
+ assert_raises(IndexError) do
141
+ @config.fetch(:sample)
142
+ end
143
+ end
144
+
145
+ def test_fetch_should_return_default_if_variable_does_not_exist_and_default_is_given
146
+ assert_nothing_raised do
147
+ assert_equal :default_value, @config.fetch(:sample, :default_value)
148
+ end
149
+ end
150
+
151
+ def test_fetch_should_invoke_block_if_variable_does_not_exist_and_block_is_given
152
+ assert_nothing_raised do
153
+ assert_equal :default_value, @config.fetch(:sample) { :default_value }
154
+ end
155
+ end
156
+
157
+ def test_fetch_should_raise_argument_error_if_both_default_and_block_are_given
158
+ assert_raises(ArgumentError) do
159
+ @config.fetch(:sample, :default1) { :default2 }
160
+ end
161
+ end
162
+
163
+ def test_fetch_should_dereference_proc_values
164
+ @config.set(:sample) { :value }
165
+ assert_instance_of Proc, @config.variables[:sample]
166
+ assert_equal :value, @config.fetch(:sample)
167
+ assert_instance_of Symbol, @config.variables[:sample]
168
+ end
169
+
170
+ def test_square_brackets_should_alias_fetch
171
+ @config.set(:sample, :value)
172
+ assert_equal :value, @config[:sample]
173
+ end
174
+
175
+ def test_square_brackets_should_return_nil_for_non_existant_variable
176
+ assert_nothing_raised do
177
+ assert_nil @config[:sample]
178
+ end
179
+ end
180
+ end