capistrano 3.6.0 → 3.7.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 (59) hide show
  1. checksums.yaml +4 -4
  2. data/.github/issue_template.md +19 -0
  3. data/.github/pull_request_template.md +26 -0
  4. data/.gitignore +1 -0
  5. data/.travis.yml +10 -2
  6. data/CHANGELOG.md +63 -1
  7. data/DEVELOPMENT.md +7 -1
  8. data/Dangerfile +54 -0
  9. data/README.md +4 -5
  10. data/capistrano.gemspec +3 -2
  11. data/features/support/vagrant_helpers.rb +3 -5
  12. data/lib/capistrano/all.rb +1 -0
  13. data/lib/capistrano/configuration/host_filter.rb +1 -1
  14. data/lib/capistrano/configuration/plugin_installer.rb +20 -2
  15. data/lib/capistrano/configuration/role_filter.rb +1 -1
  16. data/lib/capistrano/configuration/scm_resolver.rb +144 -0
  17. data/lib/capistrano/configuration/validated_variables.rb +48 -13
  18. data/lib/capistrano/configuration/variables.rb +0 -8
  19. data/lib/capistrano/configuration.rb +30 -3
  20. data/lib/capistrano/defaults.rb +3 -1
  21. data/lib/capistrano/doctor/variables_doctor.rb +1 -1
  22. data/lib/capistrano/dsl/env.rb +2 -9
  23. data/lib/capistrano/dsl/paths.rb +1 -1
  24. data/lib/capistrano/dsl/task_enhancements.rb +0 -8
  25. data/lib/capistrano/dsl.rb +2 -1
  26. data/lib/capistrano/i18n.rb +1 -0
  27. data/lib/capistrano/scm/git.rb +73 -0
  28. data/lib/capistrano/scm/hg.rb +48 -0
  29. data/lib/capistrano/scm/plugin.rb +13 -0
  30. data/lib/capistrano/scm/svn.rb +47 -0
  31. data/lib/capistrano/{tasks → scm/tasks}/git.rake +9 -24
  32. data/lib/capistrano/{tasks → scm/tasks}/hg.rake +11 -10
  33. data/lib/capistrano/{tasks → scm/tasks}/svn.rake +11 -10
  34. data/lib/capistrano/setup.rb +1 -1
  35. data/lib/capistrano/tasks/deploy.rake +4 -5
  36. data/lib/capistrano/templates/Capfile +18 -7
  37. data/lib/capistrano/templates/deploy.rb.erb +7 -10
  38. data/lib/capistrano/templates/stage.rb.erb +8 -8
  39. data/lib/capistrano/version.rb +1 -1
  40. data/lib/capistrano/version_validator.rb +2 -5
  41. data/spec/lib/capistrano/configuration/host_filter_spec.rb +5 -0
  42. data/spec/lib/capistrano/configuration/plugin_installer_spec.rb +98 -0
  43. data/spec/lib/capistrano/configuration/role_filter_spec.rb +17 -1
  44. data/spec/lib/capistrano/configuration_spec.rb +61 -2
  45. data/spec/lib/capistrano/doctor/variables_doctor_spec.rb +0 -7
  46. data/spec/lib/capistrano/dsl/task_enhancements_spec.rb +0 -15
  47. data/spec/lib/capistrano/scm/git_spec.rb +131 -0
  48. data/spec/lib/capistrano/scm/hg_spec.rb +104 -0
  49. data/spec/lib/capistrano/scm/svn_spec.rb +116 -0
  50. data/spec/lib/capistrano/scm_spec.rb +1 -1
  51. metadata +37 -19
  52. data/features/remote_file_task.feature +0 -14
  53. data/issue_template.md +0 -21
  54. data/lib/capistrano/git.rb +0 -54
  55. data/lib/capistrano/hg.rb +0 -43
  56. data/lib/capistrano/svn.rb +0 -42
  57. data/spec/lib/capistrano/git_spec.rb +0 -109
  58. data/spec/lib/capistrano/hg_spec.rb +0 -90
  59. data/spec/lib/capistrano/svn_spec.rb +0 -105
@@ -3,9 +3,9 @@
3
3
  # Defines a single server with a list of roles and multiple properties.
4
4
  # You can define all roles on a single server, or split them:
5
5
 
6
- # server 'example.com', user: 'deploy', roles: %w{app db web}, my_property: :my_value
7
- # server 'example.com', user: 'deploy', roles: %w{app web}, other_property: :other_value
8
- # server 'db.example.com', user: 'deploy', roles: %w{db}
6
+ # server "example.com", user: "deploy", roles: %w{app db web}, my_property: :my_value
7
+ # server "example.com", user: "deploy", roles: %w{app web}, other_property: :other_value
8
+ # server "db.example.com", user: "deploy", roles: %w{db}
9
9
 
10
10
 
11
11
 
@@ -13,7 +13,7 @@
13
13
  # ==================
14
14
 
15
15
  # Defines a role with one or multiple servers. The primary server in each
16
- # group is considered to be the first unless any hosts have the primary
16
+ # group is considered to be the first unless any hosts have the primary
17
17
  # property set. Specify the username and a domain or IP for the server.
18
18
  # Don't use `:all`, it's a meta role.
19
19
 
@@ -49,13 +49,13 @@
49
49
  #
50
50
  # The server-based syntax can be used to override options:
51
51
  # ------------------------------------
52
- # server 'example.com',
53
- # user: 'user_name',
52
+ # server "example.com",
53
+ # user: "user_name",
54
54
  # roles: %w{web app},
55
55
  # ssh_options: {
56
- # user: 'user_name', # overrides user setting above
56
+ # user: "user_name", # overrides user setting above
57
57
  # keys: %w(/home/user_name/.ssh/id_rsa),
58
58
  # forward_agent: false,
59
59
  # auth_methods: %w(publickey password)
60
- # # password: 'please use keys'
60
+ # # password: "please use keys"
61
61
  # }
@@ -1,3 +1,3 @@
1
1
  module Capistrano
2
- VERSION = "3.6.0".freeze
2
+ VERSION = "3.7.0".freeze
3
3
  end
@@ -5,11 +5,8 @@ module Capistrano
5
5
  end
6
6
 
7
7
  def verify
8
- if match?
9
- self
10
- else
11
- raise "Capfile locked at #{version}, but #{current_version} is loaded"
12
- end
8
+ return self if match?
9
+ raise "Capfile locked at #{version}, but #{current_version} is loaded"
13
10
  end
14
11
 
15
12
  private
@@ -55,6 +55,11 @@ module Capistrano
55
55
  let(:values) { 'server\d{1,3}$' }
56
56
  it_behaves_like "it filters hosts correctly", %w{server1 server2 server3 server4 server5}
57
57
  end
58
+
59
+ context "without number" do
60
+ let(:values) { "server" }
61
+ it_behaves_like "it filters hosts correctly", %w{}
62
+ end
58
63
  end
59
64
  end
60
65
  end
@@ -0,0 +1,98 @@
1
+ require "spec_helper"
2
+ require "capistrano/plugin"
3
+ require "capistrano/scm/plugin"
4
+
5
+ module Capistrano
6
+ class Configuration
7
+ class ExamplePlugin < Capistrano::Plugin
8
+ def set_defaults
9
+ set_if_empty :example_variable, "foo"
10
+ end
11
+
12
+ def define_tasks
13
+ task :example
14
+ task :example_prerequisite
15
+ end
16
+
17
+ def register_hooks
18
+ before :example, :example_prerequisite
19
+ end
20
+ end
21
+
22
+ class ExampleSCMPlugin < Capistrano::SCM::Plugin
23
+ end
24
+
25
+ describe PluginInstaller do
26
+ include Capistrano::DSL
27
+
28
+ let(:installer) { PluginInstaller.new }
29
+ let(:options) { {} }
30
+ let(:plugin) { ExamplePlugin.new }
31
+
32
+ before do
33
+ installer.install(plugin, **options)
34
+ end
35
+
36
+ after do
37
+ Rake::Task.clear
38
+ Capistrano::Configuration.reset!
39
+ end
40
+
41
+ context "installing plugin" do
42
+ it "defines tasks" do
43
+ expect(Rake::Task[:example]).to_not be_nil
44
+ expect(Rake::Task[:example_prerequisite]).to_not be_nil
45
+ end
46
+
47
+ it "registers hooks" do
48
+ task = Rake::Task[:example]
49
+ expect(task.prerequisites).to eq([:example_prerequisite])
50
+ end
51
+
52
+ it "sets defaults when load:defaults is invoked" do
53
+ expect(fetch(:example_variable)).to be_nil
54
+ invoke "load:defaults"
55
+ expect(fetch(:example_variable)).to eq("foo")
56
+ end
57
+
58
+ it "doesn't say an SCM is installed" do
59
+ expect(installer.scm_installed?).to be_falsey
60
+ end
61
+ end
62
+
63
+ context "installing plugin class" do
64
+ let(:plugin) { ExamplePlugin }
65
+
66
+ it "defines tasks" do
67
+ expect(Rake::Task[:example]).to_not be_nil
68
+ expect(Rake::Task[:example_prerequisite]).to_not be_nil
69
+ end
70
+ end
71
+
72
+ context "installing plugin without hooks" do
73
+ let(:options) { { load_hooks: false } }
74
+
75
+ it "doesn't register hooks" do
76
+ task = Rake::Task[:example]
77
+ expect(task.prerequisites).to be_empty
78
+ end
79
+ end
80
+
81
+ context "installing plugin and loading immediately" do
82
+ let(:options) { { load_immediately: true } }
83
+
84
+ it "sets defaults immediately" do
85
+ expect(fetch(:example_variable)).to eq("foo")
86
+ end
87
+ end
88
+
89
+ context "installing an SCM plugin" do
90
+ let(:plugin) { ExampleSCMPlugin }
91
+
92
+ it "says an SCM is installed" do
93
+ expect(installer.scm_installed?).to be_truthy
94
+ end
95
+ end
96
+ end
97
+ end
98
+ end
@@ -11,7 +11,8 @@ module Capistrano
11
11
  Server.new("server2").add_role(:web),
12
12
  Server.new("server3").add_role(:redis),
13
13
  Server.new("server4").add_role(:db),
14
- Server.new("server5").add_role(:stageweb)
14
+ Server.new("server5").add_role(:stageweb),
15
+ Server.new("server6").add_role(:"db.new")
15
16
  ]
16
17
  end
17
18
 
@@ -58,6 +59,21 @@ module Capistrano
58
59
  let(:values) { "db,/red/" }
59
60
  it_behaves_like "it filters roles correctly", 3, %w{server1 server3 server4}
60
61
  end
62
+
63
+ context "with a dot wildcard" do
64
+ let(:values) { "db.*" }
65
+ it_behaves_like "it filters roles correctly", 0, %w{}
66
+ end
67
+
68
+ context "with a dot" do
69
+ let(:values) { "db.new" }
70
+ it_behaves_like "it filters roles correctly", 1, %w{server6}
71
+ end
72
+
73
+ context "with a dot wildcard regex" do
74
+ let(:values) { "/db.*/" }
75
+ it_behaves_like "it filters roles correctly", 3, %w{server1 server4 server6}
76
+ end
61
77
  end
62
78
  end
63
79
  end
@@ -154,19 +154,29 @@ module Capistrano
154
154
  config.set(:key, "longer_value")
155
155
  end
156
156
 
157
- it "validates proc without error" do
157
+ it "validates block without error" do
158
158
  config.set(:key) { "longer_value" }
159
159
  expect(config.fetch(:key)).to eq "longer_value"
160
160
  end
161
161
 
162
+ it "validates lambda without error" do
163
+ config.set :key, -> { "longer_value" }
164
+ expect(config.fetch(:key)).to eq "longer_value"
165
+ end
166
+
162
167
  it "raises an exception on invalid string" do
163
168
  expect { config.set(:key, "sho") }.to raise_error(Capistrano::ValidationError)
164
169
  end
165
170
 
166
- it "raises an exception on invalid string provided by proc" do
171
+ it "raises an exception on invalid string provided by block" do
167
172
  config.set(:key) { "sho" }
168
173
  expect { config.fetch(:key) }.to raise_error(Capistrano::ValidationError)
169
174
  end
175
+
176
+ it "raises an exception on invalid string provided by lambda" do
177
+ config.set :key, -> { "sho" }
178
+ expect { config.fetch(:key) }.to raise_error(Capistrano::ValidationError)
179
+ end
170
180
  end
171
181
 
172
182
  context "appending" do
@@ -294,5 +304,54 @@ module Capistrano
294
304
  expect(config.dry_run?).to eq(true)
295
305
  end
296
306
  end
307
+
308
+ describe "custom filtering" do
309
+ it "accepts a custom filter object" do
310
+ filter = Object.new
311
+ def filter.filter(servers)
312
+ servers
313
+ end
314
+ config.add_filter(filter)
315
+ end
316
+
317
+ it "accepts a custom filter as a block" do
318
+ config.add_filter { |servers| servers }
319
+ end
320
+
321
+ it "raises an error if passed a block and an object" do
322
+ filter = Object.new
323
+ def filter.filter(servers)
324
+ servers
325
+ end
326
+
327
+ expect { config.add_filter(filter) { |servers| servers } }.to raise_error(ArgumentError)
328
+ end
329
+
330
+ it "raises an error if the filter lacks a filter method" do
331
+ filter = Object.new
332
+ expect { config.add_filter(filter) }.to raise_error(TypeError)
333
+ end
334
+
335
+ it "calls the filter method of a custom filter" do
336
+ ENV.delete "ROLES"
337
+ ENV.delete "HOSTS"
338
+
339
+ servers = Configuration::Servers.new
340
+
341
+ servers.add_host("test1")
342
+ servers.add_host("test2")
343
+ servers.add_host("test3")
344
+
345
+ filtered_servers = servers.take(2)
346
+
347
+ filter = mock("custom filter")
348
+ filter.expects(:filter)
349
+ .with { |subset| subset.is_a? Configuration::Servers }
350
+ .returns(filtered_servers)
351
+
352
+ config.add_filter(filter)
353
+ expect(config.filter(servers)).to eq(filtered_servers)
354
+ end
355
+ end
297
356
  end
298
357
  end
@@ -15,7 +15,6 @@ module Capistrano
15
15
  env.variables.untrusted! do
16
16
  set :application, "my_app"
17
17
  set :repo_url, ".git"
18
- set :git_strategy, "Capistrano::Git::DefaultStrategy"
19
18
  set :copy_strategy, :scp
20
19
  set :custom_setting, "hello"
21
20
  set "string_setting", "hello"
@@ -57,12 +56,6 @@ module Capistrano
57
56
  .to_stdout
58
57
  end
59
58
 
60
- it "does not print warning for the whitelisted git_strategy variable" do
61
- expect { doc.call }.not_to \
62
- output(/:git_strategy is not a recognized Capistrano setting/)\
63
- .to_stdout
64
- end
65
-
66
59
  describe "Rake" do
67
60
  before do
68
61
  load File.expand_path("../../../../../lib/capistrano/doctor.rb",
@@ -104,20 +104,5 @@ module Capistrano
104
104
  expect { Rake::Task["task"].invoke order }.to raise_error(ArgumentError, 'Task "non_existent_task" not found')
105
105
  end
106
106
  end
107
-
108
- describe "remote_file" do
109
- subject(:remote_file) { task_enhancements.remote_file("source" => "destination") }
110
-
111
- it { expect(remote_file.name).to eq("source") }
112
- it { is_expected.to be_a(Capistrano::UploadTask) }
113
-
114
- describe "namespaced" do
115
- let(:app) { Rake.application }
116
- around { |ex| app.in_namespace("namespace", &ex) }
117
-
118
- it { expect(remote_file.name).to eq("source") }
119
- it { is_expected.to be_a(Capistrano::UploadTask) }
120
- end
121
- end
122
107
  end
123
108
  end
@@ -0,0 +1,131 @@
1
+ require "spec_helper"
2
+
3
+ require "capistrano/scm/git"
4
+
5
+ module Capistrano
6
+ describe SCM::Git do
7
+ subject { Capistrano::SCM::Git.new }
8
+
9
+ # This allows us to easily use `set`, `fetch`, etc. in the examples.
10
+ let(:env) { Capistrano::Configuration.env }
11
+
12
+ # Stub the SSHKit backend so we can set up expectations without the plugin
13
+ # actually executing any commands.
14
+ let(:backend) { stub }
15
+ before { SSHKit::Backend.stubs(:current).returns(backend) }
16
+
17
+ # Mimic the deploy flow tasks so that the plugin can register its hooks.
18
+ before do
19
+ Rake::Task.define_task("deploy:new_release_path")
20
+ Rake::Task.define_task("deploy:check")
21
+ Rake::Task.define_task("deploy:set_current_revision")
22
+ end
23
+
24
+ # Clean up any tasks or variables that the plugin defined.
25
+ after do
26
+ Rake::Task.clear
27
+ Capistrano::Configuration.reset!
28
+ end
29
+
30
+ describe "#git" do
31
+ it "should call execute git in the context, with arguments" do
32
+ backend.expects(:execute).with(:git, :init)
33
+ subject.git(:init)
34
+ end
35
+ end
36
+
37
+ describe "#repo_mirror_exists?" do
38
+ it "should call test for repo HEAD" do
39
+ env.set(:repo_path, "/path/to/repo")
40
+ backend.expects(:test).with " [ -f /path/to/repo/HEAD ] "
41
+
42
+ subject.repo_mirror_exists?
43
+ end
44
+ end
45
+
46
+ describe "#check_repo_is_reachable" do
47
+ it "should test the repo url" do
48
+ env.set(:repo_url, "url")
49
+ backend.expects(:execute).with(:git, :'ls-remote --heads', "url").returns(true)
50
+
51
+ subject.check_repo_is_reachable
52
+ end
53
+ end
54
+
55
+ describe "#clone_repo" do
56
+ it "should run git clone" do
57
+ env.set(:repo_url, "url")
58
+ env.set(:repo_path, "path")
59
+ backend.expects(:execute).with(:git, :clone, "--mirror", "url", "path")
60
+
61
+ subject.clone_repo
62
+ end
63
+
64
+ it "should run git clone in shallow mode" do
65
+ env.set(:git_shallow_clone, "1")
66
+ env.set(:repo_url, "url")
67
+ env.set(:repo_path, "path")
68
+
69
+ backend.expects(:execute).with(:git, :clone, "--mirror", "--depth", "1", "--no-single-branch", "url", "path")
70
+
71
+ subject.clone_repo
72
+ end
73
+ end
74
+
75
+ describe "#update_mirror" do
76
+ it "should run git update" do
77
+ backend.expects(:execute).with(:git, :remote, :update, "--prune")
78
+
79
+ subject.update_mirror
80
+ end
81
+
82
+ it "should run git update in shallow mode" do
83
+ env.set(:git_shallow_clone, "1")
84
+ env.set(:branch, "branch")
85
+ backend.expects(:execute).with(:git, :fetch, "--depth", "1", "origin", "branch")
86
+
87
+ subject.update_mirror
88
+ end
89
+ end
90
+
91
+ describe "#archive_to_release_path" do
92
+ it "should run git archive without a subtree" do
93
+ env.set(:branch, "branch")
94
+ env.set(:release_path, "path")
95
+
96
+ backend.expects(:execute).with(:git, :archive, "branch", "| /usr/bin/env tar -x -f - -C", "path")
97
+
98
+ subject.archive_to_release_path
99
+ end
100
+
101
+ it "should run git archive with a subtree" do
102
+ env.set(:repo_tree, "tree")
103
+ env.set(:branch, "branch")
104
+ env.set(:release_path, "path")
105
+
106
+ backend.expects(:execute).with(:git, :archive, "branch", "tree", "| /usr/bin/env tar -x --strip-components 1 -f - -C", "path")
107
+
108
+ subject.archive_to_release_path
109
+ end
110
+
111
+ it "should run tar with an overridden name" do
112
+ env.set(:branch, "branch")
113
+ env.set(:release_path, "path")
114
+ SSHKit.config.command_map.expects(:[]).with(:tar).returns("/usr/bin/env gtar")
115
+
116
+ backend.expects(:execute).with(:git, :archive, "branch", "| /usr/bin/env gtar -x -f - -C", "path")
117
+
118
+ subject.archive_to_release_path
119
+ end
120
+ end
121
+
122
+ describe "#fetch_revision" do
123
+ it "should capture git rev-list" do
124
+ env.set(:branch, "branch")
125
+ backend.expects(:capture).with(:git, "rev-list --max-count=1 branch").returns("81cec13b777ff46348693d327fc8e7832f79bf43")
126
+ revision = subject.fetch_revision
127
+ expect(revision).to eq("81cec13b777ff46348693d327fc8e7832f79bf43")
128
+ end
129
+ end
130
+ end
131
+ end
@@ -0,0 +1,104 @@
1
+ require "spec_helper"
2
+
3
+ require "capistrano/scm/hg"
4
+
5
+ module Capistrano
6
+ describe SCM::Hg do
7
+ subject { Capistrano::SCM::Hg.new }
8
+
9
+ # This allows us to easily use `set`, `fetch`, etc. in the examples.
10
+ let(:env) { Capistrano::Configuration.env }
11
+
12
+ # Stub the SSHKit backend so we can set up expectations without the plugin
13
+ # actually executing any commands.
14
+ let(:backend) { stub }
15
+ before { SSHKit::Backend.stubs(:current).returns(backend) }
16
+
17
+ # Mimic the deploy flow tasks so that the plugin can register its hooks.
18
+ before do
19
+ Rake::Task.define_task("deploy:new_release_path")
20
+ Rake::Task.define_task("deploy:check")
21
+ Rake::Task.define_task("deploy:set_current_revision")
22
+ end
23
+
24
+ # Clean up any tasks or variables that the plugin defined.
25
+ after do
26
+ Rake::Task.clear
27
+ Capistrano::Configuration.reset!
28
+ end
29
+
30
+ describe "#hg" do
31
+ it "should call execute hg in the context, with arguments" do
32
+ backend.expects(:execute).with(:hg, :init)
33
+ subject.hg(:init)
34
+ end
35
+ end
36
+
37
+ describe "#repo_mirror_exists?" do
38
+ it "should call test for repo HEAD" do
39
+ env.set(:repo_path, "/path/to/repo")
40
+ backend.expects(:test).with " [ -d /path/to/repo/.hg ] "
41
+
42
+ subject.repo_mirror_exists?
43
+ end
44
+ end
45
+
46
+ describe "#check_repo_is_reachable" do
47
+ it "should test the repo url" do
48
+ env.set(:repo_url, :url)
49
+ backend.expects(:execute).with(:hg, "id", :url)
50
+
51
+ subject.check_repo_is_reachable
52
+ end
53
+ end
54
+
55
+ describe "#clone_repo" do
56
+ it "should run hg clone" do
57
+ env.set(:repo_url, :url)
58
+ env.set(:repo_path, "path")
59
+
60
+ backend.expects(:execute).with(:hg, "clone", "--noupdate", :url, "path")
61
+
62
+ subject.clone_repo
63
+ end
64
+ end
65
+
66
+ describe "#update_mirror" do
67
+ it "should run hg update" do
68
+ backend.expects(:execute).with(:hg, "pull")
69
+
70
+ subject.update_mirror
71
+ end
72
+ end
73
+
74
+ describe "#archive_to_release_path" do
75
+ it "should run hg archive without a subtree" do
76
+ env.set(:branch, :branch)
77
+ env.set(:release_path, "path")
78
+
79
+ backend.expects(:execute).with(:hg, "archive", "path", "--rev", :branch)
80
+
81
+ subject.archive_to_release_path
82
+ end
83
+
84
+ it "should run hg archive with a subtree" do
85
+ env.set(:repo_tree, "tree")
86
+ env.set(:branch, :branch)
87
+ env.set(:release_path, "path")
88
+
89
+ backend.expects(:execute).with(:hg, "archive --type tgz -p . -I", "tree", "--rev", :branch, "| tar -x --strip-components 1 -f - -C", "path")
90
+
91
+ subject.archive_to_release_path
92
+ end
93
+ end
94
+
95
+ describe "#fetch_revision" do
96
+ it "should capture hg log" do
97
+ env.set(:branch, :branch)
98
+ backend.expects(:capture).with(:hg, "log --rev branch --template \"{node}\n\"").returns("01abcde")
99
+ revision = subject.fetch_revision
100
+ expect(revision).to eq("01abcde")
101
+ end
102
+ end
103
+ end
104
+ end
@@ -0,0 +1,116 @@
1
+ require "spec_helper"
2
+
3
+ require "capistrano/scm/svn"
4
+
5
+ module Capistrano
6
+ describe SCM::Svn do
7
+ subject { Capistrano::SCM::Svn.new }
8
+
9
+ # This allows us to easily use `set`, `fetch`, etc. in the examples.
10
+ let(:env) { Capistrano::Configuration.env }
11
+
12
+ # Stub the SSHKit backend so we can set up expectations without the plugin
13
+ # actually executing any commands.
14
+ let(:backend) { stub }
15
+ before { SSHKit::Backend.stubs(:current).returns(backend) }
16
+
17
+ # Mimic the deploy flow tasks so that the plugin can register its hooks.
18
+ before do
19
+ Rake::Task.define_task("deploy:new_release_path")
20
+ Rake::Task.define_task("deploy:check")
21
+ Rake::Task.define_task("deploy:set_current_revision")
22
+ end
23
+
24
+ # Clean up any tasks or variables that the plugin defined.
25
+ after do
26
+ Rake::Task.clear
27
+ Capistrano::Configuration.reset!
28
+ end
29
+
30
+ describe "#svn" do
31
+ it "should call execute svn in the context, with arguments" do
32
+ env.set(:svn_username, "someuser")
33
+ env.set(:svn_password, "somepassword")
34
+ backend.expects(:execute).with(:svn, :init, "--username someuser", "--password somepassword")
35
+ subject.svn(:init)
36
+ end
37
+ end
38
+
39
+ describe "#repo_mirror_exists?" do
40
+ it "should call test for repo HEAD" do
41
+ env.set(:repo_path, "/path/to/repo")
42
+ backend.expects(:test).with " [ -d /path/to/repo/.svn ] "
43
+
44
+ subject.repo_mirror_exists?
45
+ end
46
+ end
47
+
48
+ describe "#check_repo_is_reachable" do
49
+ it "should test the repo url" do
50
+ env.set(:repo_url, :url)
51
+ env.set(:svn_username, "someuser")
52
+ env.set(:svn_password, "somepassword")
53
+ backend.expects(:test).with(:svn, :info, :url, "--username someuser", "--password somepassword").returns(true)
54
+
55
+ subject.check_repo_is_reachable
56
+ end
57
+ end
58
+
59
+ describe "#clone_repo" do
60
+ it "should run svn checkout" do
61
+ env.set(:repo_url, :url)
62
+ env.set(:repo_path, "path")
63
+ env.set(:svn_username, "someuser")
64
+ env.set(:svn_password, "somepassword")
65
+
66
+ backend.expects(:execute).with(:svn, :checkout, :url, "path", "--username someuser", "--password somepassword")
67
+
68
+ subject.clone_repo
69
+ end
70
+ end
71
+
72
+ describe "#update_mirror" do
73
+ it "should run svn update" do
74
+ env.set(:svn_username, "someuser")
75
+ env.set(:svn_password, "somepassword")
76
+ backend.expects(:execute).with(:svn, :update, "--username someuser", "--password somepassword")
77
+
78
+ subject.update_mirror
79
+ end
80
+
81
+ context "for specific revision" do
82
+ it "should run svn update" do
83
+ env.set(:svn_username, "someuser")
84
+ env.set(:svn_password, "somepassword")
85
+ env.set(:svn_revision, "12345")
86
+ backend.expects(:execute).with(:svn, :update, "--username someuser", "--password somepassword", "--revision 12345")
87
+
88
+ subject.update_mirror
89
+ end
90
+ end
91
+ end
92
+
93
+ describe "#archive_to_release_path" do
94
+ it "should run svn export" do
95
+ env.set(:release_path, "path")
96
+ env.set(:svn_username, "someuser")
97
+ env.set(:svn_password, "somepassword")
98
+
99
+ backend.expects(:execute).with(:svn, :export, "--force", ".", "path", "--username someuser", "--password somepassword")
100
+
101
+ subject.archive_to_release_path
102
+ end
103
+ end
104
+
105
+ describe "#fetch_revision" do
106
+ it "should capture svn version" do
107
+ env.set(:repo_path, "path")
108
+
109
+ backend.expects(:capture).with(:svnversion, "path").returns("12345")
110
+
111
+ revision = subject.fetch_revision
112
+ expect(revision).to eq("12345")
113
+ end
114
+ end
115
+ end
116
+ end