capistrano 2.1.0 → 3.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 (166) hide show
  1. checksums.yaml +7 -0
  2. data/.gitignore +20 -0
  3. data/.travis.yml +7 -0
  4. data/CHANGELOG.md +89 -0
  5. data/Gemfile +4 -0
  6. data/LICENSE.txt +674 -0
  7. data/README.md +226 -0
  8. data/Rakefile +5 -0
  9. data/bin/cap +2 -3
  10. data/bin/capify +7 -77
  11. data/capistrano-public_cert.pem +22 -0
  12. data/capistrano.gemspec +35 -0
  13. data/features/deploy.feature +52 -0
  14. data/features/installation.feature +16 -0
  15. data/features/remote_file_task.feature +14 -0
  16. data/features/step_definitions/assertions.rb +90 -0
  17. data/features/step_definitions/cap_commands.rb +8 -0
  18. data/features/step_definitions/setup.rb +25 -0
  19. data/features/support/env.rb +12 -0
  20. data/features/support/remote_command_helpers.rb +20 -0
  21. data/lib/Capfile +3 -0
  22. data/lib/capistrano/all.rb +16 -0
  23. data/lib/capistrano/application.rb +60 -0
  24. data/lib/capistrano/configuration/question.rb +42 -0
  25. data/lib/capistrano/configuration/server.rb +133 -0
  26. data/lib/capistrano/configuration/servers/role_filter.rb +86 -0
  27. data/lib/capistrano/configuration/servers.rb +53 -58
  28. data/lib/capistrano/configuration.rb +84 -30
  29. data/lib/capistrano/console.rb +1 -0
  30. data/lib/capistrano/defaults.rb +13 -0
  31. data/lib/capistrano/deploy.rb +3 -0
  32. data/lib/capistrano/dotfile.rb +3 -0
  33. data/lib/capistrano/dsl/env.rb +64 -0
  34. data/lib/capistrano/dsl/paths.rb +94 -0
  35. data/lib/capistrano/dsl/stages.rb +15 -0
  36. data/lib/capistrano/dsl/task_enhancements.rb +53 -0
  37. data/lib/capistrano/dsl.rb +48 -0
  38. data/lib/capistrano/git.rb +1 -0
  39. data/lib/capistrano/hg.rb +1 -0
  40. data/lib/capistrano/i18n.rb +34 -0
  41. data/lib/capistrano/install.rb +1 -0
  42. data/lib/capistrano/setup.rb +21 -0
  43. data/lib/capistrano/tasks/console.rake +21 -0
  44. data/lib/capistrano/tasks/deploy.rake +204 -0
  45. data/lib/capistrano/tasks/framework.rake +67 -0
  46. data/lib/capistrano/tasks/git.rake +62 -0
  47. data/lib/capistrano/tasks/hg.rake +39 -0
  48. data/lib/capistrano/tasks/install.rake +39 -0
  49. data/lib/capistrano/templates/Capfile +26 -0
  50. data/lib/capistrano/templates/deploy.rb.erb +40 -0
  51. data/lib/capistrano/templates/stage.rb.erb +42 -0
  52. data/lib/capistrano/version.rb +1 -20
  53. data/lib/capistrano/version_validator.rb +37 -0
  54. data/lib/capistrano.rb +0 -2
  55. data/spec/integration/dsl_spec.rb +344 -0
  56. data/spec/integration_spec_helper.rb +7 -0
  57. data/spec/lib/capistrano/application_spec.rb +61 -0
  58. data/spec/lib/capistrano/configuration/question_spec.rb +54 -0
  59. data/spec/lib/capistrano/configuration/server_spec.rb +249 -0
  60. data/spec/lib/capistrano/configuration/servers/role_filter_spec.rb +140 -0
  61. data/spec/lib/capistrano/configuration/servers_spec.rb +184 -0
  62. data/spec/lib/capistrano/configuration_spec.rb +101 -0
  63. data/spec/lib/capistrano/dsl/env_spec.rb +10 -0
  64. data/spec/lib/capistrano/dsl/paths_spec.rb +69 -0
  65. data/spec/lib/capistrano/dsl_spec.rb +63 -0
  66. data/spec/lib/capistrano/version_validator_spec.rb +103 -0
  67. data/spec/lib/capistrano_spec.rb +8 -0
  68. data/spec/spec_helper.rb +15 -0
  69. data/spec/support/.gitignore +1 -0
  70. data/spec/support/Vagrantfile +13 -0
  71. data/spec/support/matchers.rb +5 -0
  72. data/spec/support/tasks/database.cap +11 -0
  73. data/spec/support/test_app.rb +138 -0
  74. metadata +251 -179
  75. data/CHANGELOG +0 -512
  76. data/MIT-LICENSE +0 -20
  77. data/README +0 -43
  78. data/examples/sample.rb +0 -14
  79. data/lib/capistrano/callback.rb +0 -45
  80. data/lib/capistrano/cli/execute.rb +0 -82
  81. data/lib/capistrano/cli/help.rb +0 -102
  82. data/lib/capistrano/cli/help.txt +0 -53
  83. data/lib/capistrano/cli/options.rb +0 -183
  84. data/lib/capistrano/cli/ui.rb +0 -28
  85. data/lib/capistrano/cli.rb +0 -47
  86. data/lib/capistrano/command.rb +0 -161
  87. data/lib/capistrano/configuration/actions/file_transfer.rb +0 -35
  88. data/lib/capistrano/configuration/actions/inspect.rb +0 -46
  89. data/lib/capistrano/configuration/actions/invocation.rb +0 -134
  90. data/lib/capistrano/configuration/callbacks.rb +0 -148
  91. data/lib/capistrano/configuration/connections.rb +0 -159
  92. data/lib/capistrano/configuration/execution.rb +0 -126
  93. data/lib/capistrano/configuration/loading.rb +0 -198
  94. data/lib/capistrano/configuration/namespaces.rb +0 -196
  95. data/lib/capistrano/configuration/roles.rb +0 -51
  96. data/lib/capistrano/configuration/variables.rb +0 -127
  97. data/lib/capistrano/errors.rb +0 -15
  98. data/lib/capistrano/extensions.rb +0 -57
  99. data/lib/capistrano/gateway.rb +0 -131
  100. data/lib/capistrano/logger.rb +0 -59
  101. data/lib/capistrano/recipes/compat.rb +0 -32
  102. data/lib/capistrano/recipes/deploy/dependencies.rb +0 -44
  103. data/lib/capistrano/recipes/deploy/local_dependency.rb +0 -46
  104. data/lib/capistrano/recipes/deploy/remote_dependency.rb +0 -96
  105. data/lib/capistrano/recipes/deploy/scm/accurev.rb +0 -169
  106. data/lib/capistrano/recipes/deploy/scm/base.rb +0 -192
  107. data/lib/capistrano/recipes/deploy/scm/bzr.rb +0 -86
  108. data/lib/capistrano/recipes/deploy/scm/cvs.rb +0 -151
  109. data/lib/capistrano/recipes/deploy/scm/darcs.rb +0 -85
  110. data/lib/capistrano/recipes/deploy/scm/git.rb +0 -191
  111. data/lib/capistrano/recipes/deploy/scm/mercurial.rb +0 -129
  112. data/lib/capistrano/recipes/deploy/scm/perforce.rb +0 -126
  113. data/lib/capistrano/recipes/deploy/scm/subversion.rb +0 -114
  114. data/lib/capistrano/recipes/deploy/scm.rb +0 -19
  115. data/lib/capistrano/recipes/deploy/strategy/base.rb +0 -64
  116. data/lib/capistrano/recipes/deploy/strategy/checkout.rb +0 -20
  117. data/lib/capistrano/recipes/deploy/strategy/copy.rb +0 -144
  118. data/lib/capistrano/recipes/deploy/strategy/export.rb +0 -20
  119. data/lib/capistrano/recipes/deploy/strategy/remote.rb +0 -52
  120. data/lib/capistrano/recipes/deploy/strategy/remote_cache.rb +0 -47
  121. data/lib/capistrano/recipes/deploy/strategy.rb +0 -19
  122. data/lib/capistrano/recipes/deploy/templates/maintenance.rhtml +0 -53
  123. data/lib/capistrano/recipes/deploy.rb +0 -494
  124. data/lib/capistrano/recipes/standard.rb +0 -37
  125. data/lib/capistrano/recipes/templates/maintenance.rhtml +0 -53
  126. data/lib/capistrano/recipes/upgrade.rb +0 -33
  127. data/lib/capistrano/server_definition.rb +0 -51
  128. data/lib/capistrano/shell.rb +0 -256
  129. data/lib/capistrano/ssh.rb +0 -109
  130. data/lib/capistrano/task_definition.rb +0 -69
  131. data/lib/capistrano/upload.rb +0 -146
  132. data/test/cli/execute_test.rb +0 -132
  133. data/test/cli/help_test.rb +0 -139
  134. data/test/cli/options_test.rb +0 -226
  135. data/test/cli/ui_test.rb +0 -28
  136. data/test/cli_test.rb +0 -17
  137. data/test/command_test.rb +0 -309
  138. data/test/configuration/actions/file_transfer_test.rb +0 -40
  139. data/test/configuration/actions/inspect_test.rb +0 -62
  140. data/test/configuration/actions/invocation_test.rb +0 -202
  141. data/test/configuration/callbacks_test.rb +0 -206
  142. data/test/configuration/connections_test.rb +0 -288
  143. data/test/configuration/execution_test.rb +0 -159
  144. data/test/configuration/loading_test.rb +0 -127
  145. data/test/configuration/namespace_dsl_test.rb +0 -297
  146. data/test/configuration/roles_test.rb +0 -47
  147. data/test/configuration/servers_test.rb +0 -90
  148. data/test/configuration/variables_test.rb +0 -180
  149. data/test/configuration_test.rb +0 -81
  150. data/test/deploy/scm/accurev_test.rb +0 -23
  151. data/test/deploy/scm/base_test.rb +0 -55
  152. data/test/deploy/scm/git_test.rb +0 -112
  153. data/test/deploy/strategy/copy_test.rb +0 -147
  154. data/test/extensions_test.rb +0 -69
  155. data/test/fixtures/cli_integration.rb +0 -5
  156. data/test/fixtures/config.rb +0 -5
  157. data/test/fixtures/custom.rb +0 -3
  158. data/test/gateway_test.rb +0 -167
  159. data/test/logger_test.rb +0 -123
  160. data/test/server_definition_test.rb +0 -108
  161. data/test/shell_test.rb +0 -64
  162. data/test/ssh_test.rb +0 -97
  163. data/test/task_definition_test.rb +0 -101
  164. data/test/upload_test.rb +0 -131
  165. data/test/utils.rb +0 -42
  166. data/test/version_test.rb +0 -24
@@ -0,0 +1,249 @@
1
+ require 'spec_helper'
2
+
3
+ module Capistrano
4
+ class Configuration
5
+ describe Server do
6
+ let(:server) { Server.new('hostname') }
7
+
8
+ describe 'adding a role' do
9
+ subject { server.add_role(:test) }
10
+ it 'adds the role' do
11
+ expect{subject}.to change{server.roles.size}.from(0).to(1)
12
+ end
13
+ end
14
+
15
+ describe 'adding roles' do
16
+ subject { server.add_roles([:things, :stuff]) }
17
+ it 'adds the roles' do
18
+ expect{subject}.to change{server.roles.size}.from(0).to(2)
19
+ end
20
+ end
21
+
22
+
23
+ describe 'checking roles' do
24
+ subject { server.has_role?(:test) }
25
+
26
+ before do
27
+ server.add_role(:test)
28
+ end
29
+
30
+ it 'adds the role' do
31
+ expect{subject}.to be_true
32
+ end
33
+ end
34
+
35
+ describe 'comparing identity' do
36
+ subject { server.matches? hostname }
37
+
38
+ context 'with the same hostname' do
39
+ let(:hostname) { 'hostname' }
40
+ it { should be_true }
41
+ end
42
+
43
+ context 'with the same hostname and a user' do
44
+ let(:hostname) { 'user@hostname' }
45
+ it { should be_true }
46
+ end
47
+
48
+ context 'with a different hostname' do
49
+ let(:hostname) { 'otherserver' }
50
+ it { should be_false }
51
+ end
52
+ end
53
+
54
+ describe 'identifying as primary' do
55
+ subject { server.primary }
56
+ context 'server is primary' do
57
+ before do
58
+ server.set(:primary, true)
59
+ end
60
+ it 'returns self' do
61
+ expect(subject).to eq server
62
+ end
63
+ end
64
+
65
+ context 'server is not primary' do
66
+ it 'is falesy' do
67
+ expect(subject).to be_false
68
+ end
69
+ end
70
+ end
71
+
72
+ describe 'assigning properties' do
73
+
74
+ before do
75
+ server.with(properties)
76
+ end
77
+
78
+ context 'properties contains roles' do
79
+ let(:properties) { {roles: [:clouds]} }
80
+
81
+ it 'adds the roles' do
82
+ expect(server.roles.first).to eq :clouds
83
+ end
84
+ end
85
+
86
+ context 'properties contains user' do
87
+ let(:properties) { {user: 'tomc'} }
88
+
89
+ it 'sets the user' do
90
+ expect(server.user).to eq 'tomc'
91
+ end
92
+ end
93
+
94
+ context 'properties contains port' do
95
+ let(:properties) { {port: 2222} }
96
+
97
+ it 'sets the port' do
98
+ expect(server.port).to eq 2222
99
+ end
100
+ end
101
+
102
+ context 'properties contains key' do
103
+ let(:properties) { {key: '/key'} }
104
+
105
+ it 'adds the key' do
106
+ expect(server.keys).to include '/key'
107
+ end
108
+ end
109
+
110
+ context 'properties contains password' do
111
+ let(:properties) { {password: 'supersecret'} }
112
+
113
+ it 'adds the key' do
114
+ expect(server.password).to eq 'supersecret'
115
+ end
116
+ end
117
+
118
+ context 'new properties' do
119
+ let(:properties) { { webscales: 5 } }
120
+
121
+ it 'adds the properties' do
122
+ expect(server.properties.webscales).to eq 5
123
+ end
124
+ end
125
+
126
+ context 'existing properties' do
127
+ let(:properties) { { webscales: 6 } }
128
+
129
+ it 'keeps the existing properties' do
130
+ expect(server.properties.webscales).to eq 6
131
+ server.properties.webscales = 5
132
+ expect(server.properties.webscales).to eq 5
133
+ end
134
+ end
135
+ end
136
+
137
+ describe '#include?' do
138
+ let(:options) { {} }
139
+
140
+ subject { server.select?(options) }
141
+
142
+ before do
143
+ server.properties.active = true
144
+ end
145
+
146
+ context 'options are empty' do
147
+ it { should be_true }
148
+ end
149
+
150
+ context 'value is a symbol' do
151
+ context 'value matches server property' do
152
+
153
+ context 'with :filter' do
154
+ let(:options) { { filter: :active }}
155
+ it { should be_true }
156
+ end
157
+
158
+ context 'with :select' do
159
+ let(:options) { { select: :active }}
160
+ it { should be_true }
161
+ end
162
+ end
163
+
164
+ context 'value does not match server properly' do
165
+ context 'with :filter' do
166
+ let(:options) { { filter: :inactive }}
167
+ it { should be_false }
168
+ end
169
+
170
+ context 'with :select' do
171
+ let(:options) { { select: :inactive }}
172
+ it { should be_false }
173
+ end
174
+ end
175
+ end
176
+
177
+ context 'value is a proc' do
178
+ context 'value matches server property' do
179
+
180
+ context 'with :filter' do
181
+ let(:options) { { filter: ->(s) { s.properties.active } } }
182
+ it { should be_true }
183
+ end
184
+
185
+ context 'with :select' do
186
+ let(:options) { { select: ->(s) { s.properties.active } } }
187
+ it { should be_true }
188
+ end
189
+ end
190
+
191
+ context 'value does not match server properly' do
192
+ context 'with :filter' do
193
+ let(:options) { { filter: ->(s) { s.properties.inactive } } }
194
+ it { should be_false }
195
+ end
196
+
197
+ context 'with :select' do
198
+ let(:options) { { select: ->(s) { s.properties.inactive } } }
199
+ it { should be_false }
200
+ end
201
+ end
202
+ end
203
+
204
+ end
205
+
206
+ describe 'assign ssh_options' do
207
+ let(:server) { Server.new('user_name@hostname') }
208
+
209
+ context 'defaults' do
210
+ it 'forward agent' do
211
+ expect(server.netssh_options[:forward_agent]).to eq true
212
+ end
213
+ it 'contains user' do
214
+ expect(server.netssh_options[:user]).to eq 'user_name'
215
+ end
216
+ end
217
+
218
+ context 'custom' do
219
+ let(:properties) do
220
+ { ssh_options: {
221
+ user: 'another_user',
222
+ keys: %w(/home/another_user/.ssh/id_rsa),
223
+ forward_agent: false,
224
+ auth_methods: %w(publickey password) } }
225
+ end
226
+
227
+ before do
228
+ server.with(properties)
229
+ end
230
+
231
+ it 'not forward agent' do
232
+ expect(server.netssh_options[:forward_agent]).to eq false
233
+ end
234
+ it 'contains correct user' do
235
+ expect(server.netssh_options[:user]).to eq 'another_user'
236
+ end
237
+ it 'contains keys' do
238
+ expect(server.netssh_options[:keys]).to eq %w(/home/another_user/.ssh/id_rsa)
239
+ end
240
+ it 'contains auth_methods' do
241
+ expect(server.netssh_options[:auth_methods]).to eq %w(publickey password)
242
+ end
243
+ end
244
+
245
+ end
246
+
247
+ end
248
+ end
249
+ end
@@ -0,0 +1,140 @@
1
+ require 'spec_helper'
2
+
3
+ module Capistrano
4
+ class Configuration
5
+ class Servers
6
+
7
+ describe RoleFilter do
8
+ let(:role_filter) { RoleFilter.new(required, available) }
9
+ let(:required) { [] }
10
+ let(:available) { [:web, :app, :db] }
11
+
12
+ describe '#new' do
13
+ it 'takes two arrays of role names' do
14
+ expect(role_filter)
15
+ end
16
+ end
17
+
18
+ describe '.for' do
19
+
20
+ subject { RoleFilter.for(required, available) }
21
+
22
+ context 'without env vars' do
23
+ context ':all required' do
24
+ let(:required) { [:all] }
25
+
26
+ it 'returns all available names' do
27
+ expect(subject).to eq available
28
+ end
29
+ end
30
+
31
+ context 'role names required' do
32
+ let(:required) { [:web, :app] }
33
+ it 'returns all required names' do
34
+ expect(subject).to eq required
35
+ end
36
+ end
37
+ end
38
+
39
+ context 'with ENV vars' do
40
+ before do
41
+ ENV.stubs(:[]).with('ROLES').returns('app,web')
42
+ end
43
+
44
+ context ':all required' do
45
+ let(:required) { [:all] }
46
+
47
+ it 'returns available names defined in ROLES' do
48
+ expect(subject).to eq [:app, :web]
49
+ end
50
+ end
51
+
52
+ context 'role names required' do
53
+ let(:required) { [:web, :db] }
54
+ it 'returns all required names defined in ROLES' do
55
+ expect(subject).to eq [:web]
56
+ end
57
+ end
58
+ end
59
+
60
+ context 'with configuration filters' do
61
+ before do
62
+ Configuration.env.set(:filter, roles: %w{app web})
63
+ end
64
+
65
+ context ':all required' do
66
+ let(:required) { [:all] }
67
+
68
+ it 'returns available names defined in the filter' do
69
+ expect(subject).to eq [:app, :web]
70
+ end
71
+ end
72
+
73
+ context 'role names required' do
74
+ let(:required) { [:web, :db] }
75
+ it 'returns all required names defined in the filter' do
76
+ expect(subject).to eq [:web]
77
+ end
78
+ end
79
+
80
+ after do
81
+ Configuration.env.delete(:filter)
82
+ end
83
+ end
84
+
85
+ context 'with a single configuration filter' do
86
+ before do
87
+ Configuration.env.set(:filter, roles: 'web')
88
+ end
89
+
90
+ context ':all required' do
91
+ let(:required) { [:all] }
92
+
93
+ it 'returns available names defined in the filter' do
94
+ expect(subject).to eq [:web]
95
+ end
96
+ end
97
+
98
+ context 'role names required' do
99
+ let(:required) { [:web, :db] }
100
+ it 'returns all required names defined in the filter' do
101
+ expect(subject).to eq [:web]
102
+ end
103
+ end
104
+
105
+ after do
106
+ Configuration.env.delete(:filter)
107
+ end
108
+ end
109
+
110
+ context 'with configuration filters and ENV vars' do
111
+ before do
112
+ Configuration.env.set(:filter, roles: %w{app})
113
+ ENV.stubs(:[]).with('ROLES').returns('web')
114
+ end
115
+
116
+ context ':all required' do
117
+ let(:required) { [:all] }
118
+
119
+ it 'returns available names defined in the filter' do
120
+ expect(subject).to eq [:web, :app]
121
+ end
122
+ end
123
+
124
+ context 'role names required' do
125
+ let(:required) { [:web, :db] }
126
+ it 'returns all required names defined in the filter' do
127
+ expect(subject).to eq [:web]
128
+ end
129
+ end
130
+
131
+ after do
132
+ Configuration.env.delete(:filter)
133
+ end
134
+ end
135
+ end
136
+ end
137
+
138
+ end
139
+ end
140
+ end
@@ -0,0 +1,184 @@
1
+ require 'spec_helper'
2
+
3
+ module Capistrano
4
+ class Configuration
5
+ describe Servers do
6
+ let(:servers) { Servers.new }
7
+
8
+ describe 'adding a role' do
9
+
10
+ it 'adds two new server instances' do
11
+ expect{servers.add_role(:app, %w{1 2})}.
12
+ to change{servers.count}.from(0).to(2)
13
+ end
14
+
15
+ it 'handles de-duplification within roles' do
16
+ servers.add_role(:app, %w{1})
17
+ servers.add_role(:app, %w{1})
18
+ expect(servers.count).to eq 1
19
+ end
20
+
21
+ it 'accepts instances of server objects' do
22
+ servers.add_role(:app, [Capistrano::Configuration::Server.new('example.net'), 'example.com'])
23
+ expect(servers.roles_for([:app]).length).to eq 2
24
+ end
25
+
26
+ it 'accepts non-enumerable types' do
27
+ servers.add_role(:app, '1')
28
+ expect(servers.roles_for([:app]).count).to eq 1
29
+ end
30
+
31
+ end
32
+
33
+ describe 'adding a role to an existing server' do
34
+ before do
35
+ servers.add_role(:web, %w{1 2})
36
+ servers.add_role(:app, %w{1 2})
37
+ end
38
+
39
+ it 'adds new roles to existing servers' do
40
+ expect(servers.count).to eq 2
41
+ end
42
+
43
+ end
44
+
45
+ describe 'collecting server roles' do
46
+ let(:app) { Set.new([:app]) }
47
+ let(:web_app) { Set.new([:web, :app]) }
48
+ let(:web) { Set.new([:web]) }
49
+
50
+ before do
51
+ servers.add_role(:app, %w{1 2 3})
52
+ servers.add_role(:web, %w{2 3 4})
53
+ end
54
+
55
+ it 'returns an array of the roles' do
56
+ expect(servers.roles_for([:app]).collect(&:roles)).to eq [app, web_app, web_app]
57
+ expect(servers.roles_for([:web]).collect(&:roles)).to eq [web_app, web_app, web]
58
+ end
59
+ end
60
+
61
+ describe 'finding the primary server' do
62
+ it 'takes the first server if none have the primary property' do
63
+ servers.add_role(:app, %w{1 2})
64
+ servers.fetch_primary(:app).hostname.should == '1'
65
+ end
66
+
67
+ it 'takes the first server with the primary have the primary flag' do
68
+ servers.add_role(:app, %w{1 2})
69
+ servers.add_host('2', primary: true)
70
+ servers.fetch_primary(:app).hostname.should == '2'
71
+ end
72
+ end
73
+
74
+ describe 'fetching servers' do
75
+ before do
76
+ servers.add_role(:app, %w{1 2})
77
+ servers.add_role(:web, %w{2 3})
78
+ end
79
+
80
+ it 'returns the correct app servers' do
81
+ expect(servers.roles_for([:app]).map(&:hostname)).to eq %w{1 2}
82
+ end
83
+
84
+ it 'returns the correct web servers' do
85
+ expect(servers.roles_for([:web]).map(&:hostname)).to eq %w{2 3}
86
+ end
87
+
88
+ it 'returns the correct app and web servers' do
89
+ expect(servers.roles_for([:app, :web]).map(&:hostname)).to eq %w{1 2 3}
90
+ end
91
+
92
+ it 'returns all servers' do
93
+ expect(servers.roles_for([:all]).map(&:hostname)).to eq %w{1 2 3}
94
+ end
95
+ end
96
+
97
+ describe 'adding a server' do
98
+
99
+ before do
100
+ servers.add_host('1', roles: [:app, 'web'], test: :value)
101
+ end
102
+
103
+ it 'can create a server with properties' do
104
+ expect(servers.roles_for([:app]).first.hostname).to eq '1'
105
+ expect(servers.roles_for([:web]).first.hostname).to eq '1'
106
+ expect(servers.roles_for([:all]).first.properties.test).to eq :value
107
+ end
108
+
109
+ end
110
+
111
+ describe 'selecting roles' do
112
+
113
+ before do
114
+ servers.add_host('1', roles: :app, active: true)
115
+ servers.add_host('2', roles: :app)
116
+ end
117
+
118
+ it 'is empty if the filter would remove all matching hosts' do
119
+ expect(servers.roles_for([:app, select: :inactive])).to be_empty
120
+ end
121
+
122
+ it 'can filter hosts by properties on the host object using symbol as shorthand' do
123
+ expect(servers.roles_for([:app, filter: :active]).length).to eq 1
124
+ end
125
+
126
+ it 'can select hosts by properties on the host object using symbol as shorthand' do
127
+ expect(servers.roles_for([:app, select: :active]).length).to eq 1
128
+ end
129
+
130
+ it 'can filter hosts by properties on the host using a regular proc' do
131
+ expect(servers.roles_for([:app, filter: ->(h) { h.properties.active }]).length).to eq 1
132
+ end
133
+
134
+ it 'can select hosts by properties on the host using a regular proc' do
135
+ expect(servers.roles_for([:app, select: ->(h) { h.properties.active }]).length).to eq 1
136
+ end
137
+
138
+ it 'is empty if the regular proc filter would remove all matching hosts' do
139
+ expect(servers.roles_for([:app, select: ->(h) { h.properties.inactive }])).to be_empty
140
+ end
141
+
142
+ end
143
+
144
+ describe 'filtering roles' do
145
+
146
+ before do
147
+ ENV.stubs(:[]).with('ROLES').returns('web,db')
148
+ servers.add_host('1', roles: :app, active: true)
149
+ servers.add_host('2', roles: :app)
150
+ servers.add_host('3', roles: :web)
151
+ servers.add_host('4', roles: :web)
152
+ servers.add_host('5', roles: :db)
153
+ end
154
+
155
+ subject { servers.roles_for(roles).map(&:hostname) }
156
+
157
+ context 'when selecting all roles' do
158
+ let(:roles) { [:all] }
159
+
160
+ it 'returns the roles specified by ROLE' do
161
+ expect(subject).to eq %w{3 4 5}
162
+ end
163
+ end
164
+
165
+ context 'when selecting roles included in ROLE' do
166
+ let(:roles) { [:app, :web] }
167
+
168
+ it 'returns only roles that match ROLE' do
169
+ expect(subject).to eq %w{3 4}
170
+ end
171
+ end
172
+
173
+ context 'when selecting roles not included in ROLE' do
174
+ let(:roles) { [:app] }
175
+
176
+ it 'is empty' do
177
+ expect(subject).to be_empty
178
+ end
179
+ end
180
+ end
181
+
182
+ end
183
+ end
184
+ end
@@ -0,0 +1,101 @@
1
+ require 'spec_helper'
2
+
3
+ module Capistrano
4
+ describe Configuration do
5
+ let(:config) { Configuration.new }
6
+ let(:servers) { stub }
7
+
8
+ describe '.env' do
9
+ it 'is a global accessor to a single instance' do
10
+ Configuration.env.set(:test, true)
11
+ expect(Configuration.env.fetch(:test)).to be_true
12
+ end
13
+ end
14
+
15
+ describe 'roles' do
16
+ context 'adding a role' do
17
+ subject { config.role(:app, %w{server1 server2}) }
18
+
19
+ before do
20
+ Configuration::Servers.expects(:new).returns(servers)
21
+ servers.expects(:add_role).with(:app, %w{server1 server2}, {})
22
+ end
23
+
24
+ it 'adds the role' do
25
+ expect(subject)
26
+ end
27
+ end
28
+ end
29
+
30
+ describe 'setting and fetching' do
31
+ subject { config.fetch(:key, :default) }
32
+
33
+ context 'value is set' do
34
+ before do
35
+ config.set(:key, :value)
36
+ end
37
+
38
+ it 'returns the set value' do
39
+ expect(subject).to eq :value
40
+ end
41
+ end
42
+
43
+ context 'value is not set' do
44
+ it 'returns the default value' do
45
+ expect(subject).to eq :default
46
+ end
47
+ end
48
+
49
+ context 'value is a proc' do
50
+ subject { config.fetch(:key, Proc.new { :proc } ) }
51
+ it 'calls the proc' do
52
+ expect(subject).to eq :proc
53
+ end
54
+ end
55
+
56
+ context 'block is passed to fetch' do
57
+ subject { config.fetch(:key, :default) { fail 'we need this!' } }
58
+
59
+ it 'returns the block value' do
60
+ expect { subject }.to raise_error
61
+ end
62
+ end
63
+ end
64
+
65
+ describe 'deleting' do
66
+ before do
67
+ config.set(:key, :value)
68
+ end
69
+
70
+ it 'deletes the value' do
71
+ config.delete(:key)
72
+ expect(config.fetch(:key)).to be_nil
73
+ end
74
+ end
75
+
76
+ describe 'asking' do
77
+ let(:question) { stub }
78
+
79
+ before do
80
+ Configuration::Question.expects(:new).with(config, :branch, :default).
81
+ returns(question)
82
+ end
83
+
84
+ it 'prompts for the value when fetching' do
85
+ config.ask(:branch, :default)
86
+ expect(config.fetch(:branch)).to eq question
87
+ end
88
+ end
89
+
90
+ describe 'setting the backend' do
91
+ it 'by default, is SSHKit' do
92
+ expect(config.backend).to eq SSHKit
93
+ end
94
+
95
+ it 'can be set to another class' do
96
+ config.backend = :test
97
+ expect(config.backend).to eq :test
98
+ end
99
+ end
100
+ end
101
+ end
@@ -0,0 +1,10 @@
1
+ require 'spec_helper'
2
+
3
+ module Capistrano
4
+ module DSL
5
+
6
+ describe Env do
7
+
8
+ end
9
+ end
10
+ end