capistrano 2.5.22 → 2.6.0

Sign up to get free protection for your applications and to get access to all the features.
data/CHANGELOG CHANGED
@@ -1,3 +1,24 @@
1
+ ## 2.6.0 / May 3 2011
2
+
3
+ A rather large release, feature-version bump because of the new
4
+ multiple-gateways feature as implemented by Ryan Duryea (way to go!)
5
+
6
+ Please also note from this release that if you use Git submodules, the
7
+ Git-version requirement for the new implementation is now >= 1.5.6, from
8
+ previously un-documented. (1.5.6 is new-enough that I think this is
9
+ acceptable)
10
+
11
+ * Upgrade Net::SSH-gateway dependency to 1.1 (fixes a thread-deadlocking bug on MRI 1.9)
12
+ * Respect "dry-run" on transfer methods (Florian Frank)
13
+ * Add support for multiple gateways: (Ryan Duryea)
14
+ set :gateway, {
15
+ 'gate1.example.com' => 'server1.example.com',
16
+ [ 'gate2.example.com', 'gate3.example.com' ] => [ 'server5.example.com', 'server6.example.com' ]
17
+ }
18
+ * Properly support nested Git submodules, moves Git requirement to >= 1.5.6 [if you rely upon submodules] (Ken Miller)
19
+ * Fetch tags into the remote cache, allows deploying a tag when using Git, with the remote_cache strategy (Florian Frank)
20
+ * Various fixes to path handling bugs in the copt strategy. (Philippe Rathé)
21
+
1
22
  ## 2.5.21 / April 6 2011
2
23
 
3
24
  * Fixed to follow best-practice guidelines from Bundler (Ben Langfeld)
@@ -1,25 +1,25 @@
1
1
  ## Capistrano
2
2
 
3
- Capistrano is a utility and framework for executing commands in parallel on multiple remote machines, via SSH. It uses a simple DSL (borrowed in part from Rake, [[http://rake.rubyforge.org/]]) that allows you to define _tasks_, which may be applied to machines in certain roles. It also supports tunneling connections via some gateway machine to allow operations to be performed behind VPN's and firewalls.
3
+ Capistrano is a utility and framework for executing commands in parallel on multiple remote machines, via SSH. It uses a simple DSL (borrowed in part from [Rake](http://rake.rubyforge.org/)) that allows you to define _tasks_, which may be applied to machines in certain roles. It also supports tunneling connections via some gateway machine to allow operations to be performed behind VPN's and firewalls.
4
4
 
5
5
  Capistrano was originally designed to simplify and automate deployment of web applications to distributed environments, and originally came bundled with a set of tasks designed for deploying Rails applications.
6
6
 
7
7
  ## Documentation
8
8
 
9
- * [[http://github.com/capistrano/capistrano/wiki/Documentation-v2.x]]
9
+ * [http://github.com/capistrano/capistrano/wiki/Documentation-v2.x](http://github.com/capistrano/capistrano/wiki/Documentation-v2.x)
10
10
 
11
11
  ## DEPENDENCIES
12
12
 
13
- * [[Net::SSH|http://net-ssh.rubyforge.org]]
14
- * [[Net::SFTP|http://net-ssh.rubyforge.org]]
15
- * [[Net::SCP|http://net-ssh.rubyforge.org]]
16
- * [[Net::SSH::Gateway|http://net-ssh.rubyforge.org]]
17
- * [[HighLine|http://highline.rubyforge.org]]
13
+ * [Net::SSH](http://net-ssh.rubyforge.org)
14
+ * [Net::SFTP](http://net-ssh.rubyforge.org)
15
+ * [Net::SCP](http://net-ssh.rubyforge.org)
16
+ * [Net::SSH::Gateway](http://net-ssh.rubyforge.org)
17
+ * [HighLine](http://highline.rubyforge.org)
18
18
 
19
19
  If you want to run the tests, you'll also need to have the following dependencies installed:
20
20
 
21
- * Echoe (for the Rakefile)
22
- * Mocha (http://mocha.rubyforge.org)
21
+ * [Echoe](https://github.com/fauna/echoe)
22
+ * [Mocha](http://mocha.rubyforge.org)
23
23
 
24
24
  ## ASSUMPTIONS
25
25
 
data/VERSION CHANGED
@@ -1 +1 @@
1
- 2.5.22
1
+ 2.6.0
@@ -12,7 +12,6 @@ Gem::Specification.new do |s|
12
12
  s.summary = %q{Capistrano - Welcome to easy deployment with Ruby over SSH}
13
13
  s.description = %q{Capistrano is a utility and framework for executing commands in parallel on multiple remote machines, via SSH.}
14
14
  s.date = %q{2011-03-22}
15
-
16
15
  s.files = `git ls-files`.split("\n")
17
16
  s.test_files = `git ls-files -- {test,spec,features}/*`.split("\n")
18
17
  s.executables = `git ls-files -- bin/*`.split("\n").map{ |f| File.basename(f) }
@@ -28,13 +27,13 @@ Gem::Specification.new do |s|
28
27
  s.add_runtime_dependency(%q<net-ssh>, [">= 2.0.14"])
29
28
  s.add_runtime_dependency(%q<net-sftp>, [">= 2.0.0"])
30
29
  s.add_runtime_dependency(%q<net-scp>, [">= 1.0.0"])
31
- s.add_runtime_dependency(%q<net-ssh-gateway>, [">= 1.0.0"])
30
+ s.add_runtime_dependency(%q<net-ssh-gateway>, [">= 1.1.0"])
32
31
  s.add_development_dependency(%q<mocha>, [">= 0"])
33
32
  else
34
33
  s.add_dependency(%q<net-ssh>, [">= 2.0.14"])
35
34
  s.add_dependency(%q<net-sftp>, [">= 2.0.0"])
36
35
  s.add_dependency(%q<net-scp>, [">= 1.0.0"])
37
- s.add_dependency(%q<net-ssh-gateway>, [">= 1.0.0"])
36
+ s.add_dependency(%q<net-ssh-gateway>, [">= 1.1.0"])
38
37
  s.add_dependency(%q<highline>, [">= 0"])
39
38
  s.add_dependency(%q<mocha>, [">= 0"])
40
39
  end
@@ -42,7 +41,7 @@ Gem::Specification.new do |s|
42
41
  s.add_dependency(%q<net-ssh>, [">= 2.0.14"])
43
42
  s.add_dependency(%q<net-sftp>, [">= 2.0.0"])
44
43
  s.add_dependency(%q<net-scp>, [">= 1.0.0"])
45
- s.add_dependency(%q<net-ssh-gateway>, [">= 1.0.0"])
44
+ s.add_dependency(%q<net-ssh-gateway>, [">= 1.1.0"])
46
45
  s.add_dependency(%q<highline>, [">= 0"])
47
46
  s.add_dependency(%q<mocha>, [">= 0"])
48
47
  end
@@ -37,7 +37,11 @@ module Capistrano
37
37
  def transfer(direction, from, to, options={}, &block)
38
38
  execute_on_servers(options) do |servers|
39
39
  targets = servers.map { |s| sessions[s] }
40
- Transfer.process(direction, from, to, targets, options.merge(:logger => logger), &block)
40
+ if dry_run
41
+ logger.debug "transfering: #{[direction, from, to, targets, options.merge(:logger => logger).inspect ] * ', '}"
42
+ else
43
+ Transfer.process(direction, from, to, targets, options.merge(:logger => logger), &block)
44
+ end
41
45
  end
42
46
  end
43
47
 
@@ -24,13 +24,29 @@ module Capistrano
24
24
  class GatewayConnectionFactory #:nodoc:
25
25
  def initialize(gateway, options)
26
26
  @options = options
27
- @options[:logger].debug "Creating gateway using #{[*gateway].join(', ')}" if @options[:logger]
28
27
  Thread.abort_on_exception = true
29
- @gateways = [*gateway].collect { |g| ServerDefinition.new(g) }
30
- tunnel = SSH.connection_strategy(@gateways[0], @options) do |host, user, connect_options|
28
+ @gateways = {}
29
+ if gateway.is_a?(Hash)
30
+ @options[:logger].debug "Creating multiple gateways using #{gateway.inspect}" if @options[:logger]
31
+ gateway.each do |gw, hosts|
32
+ gateway_connection = add_gateway(gw)
33
+ [*hosts].each do |host|
34
+ @gateways[:default] ||= gateway_connection
35
+ @gateways[host] = gateway_connection
36
+ end
37
+ end
38
+ else
39
+ @options[:logger].debug "Creating gateway using #{[*gateway].join(', ')}" if @options[:logger]
40
+ @gateways[:default] = add_gateway(gateway)
41
+ end
42
+ end
43
+
44
+ def add_gateway(gateway)
45
+ gateways = [*gateway].collect { |g| ServerDefinition.new(g) }
46
+ tunnel = SSH.connection_strategy(gateways[0], @options) do |host, user, connect_options|
31
47
  Net::SSH::Gateway.new(host, user, connect_options)
32
48
  end
33
- @gateway = (@gateways[1..-1]).inject(tunnel) do |tunnel, destination|
49
+ (gateways[1..-1]).inject(tunnel) do |tunnel, destination|
34
50
  @options[:logger].debug "Creating tunnel to #{destination}" if @options[:logger]
35
51
  local_host = ServerDefinition.new("127.0.0.1", :user => destination.user, :port => tunnel.open(destination.host, (destination.port || 22)))
36
52
  SSH.connection_strategy(local_host, @options) do |host, user, connect_options|
@@ -41,11 +57,15 @@ module Capistrano
41
57
 
42
58
  def connect_to(server)
43
59
  @options[:logger].debug "establishing connection to `#{server}' via gateway" if @options[:logger]
44
- local_host = ServerDefinition.new("127.0.0.1", :user => server.user, :port => @gateway.open(server.host, server.port || 22))
60
+ local_host = ServerDefinition.new("127.0.0.1", :user => server.user, :port => gateway_for(server).open(server.host, server.port || 22))
45
61
  session = SSH.connect(local_host, @options)
46
62
  session.xserver = server
47
63
  session
48
64
  end
65
+
66
+ def gateway_for(server)
67
+ @gateways[server.host] || @gateways[:default]
68
+ end
49
69
  end
50
70
 
51
71
  # A hash of the SSH sessions that are currently open and available.
@@ -87,7 +107,7 @@ module Capistrano
87
107
  def connection_factory
88
108
  @connection_factory ||= begin
89
109
  if exists?(:gateway)
90
- logger.debug "establishing connection to gateway `#{fetch(:gateway)}'"
110
+ logger.debug "establishing connection to gateway `#{fetch(:gateway).inspect}'"
91
111
  GatewayConnectionFactory.new(fetch(:gateway), self)
92
112
  else
93
113
  DefaultConnectionFactory.new(self)
@@ -148,7 +148,7 @@ module Capistrano
148
148
  if variable(:git_enable_submodules)
149
149
  execute << "#{git} submodule #{verbose} init"
150
150
  execute << "#{git} submodule #{verbose} sync"
151
- execute << "#{git} submodule #{verbose} update --recursive"
151
+ execute << "#{git} submodule #{verbose} update --init --recursive"
152
152
  end
153
153
 
154
154
  execute.join(" && ")
@@ -181,13 +181,13 @@ module Capistrano
181
181
  end
182
182
 
183
183
  # since we're in a local branch already, just reset to specified revision rather than merge
184
- execute << "#{git} fetch #{verbose} #{remote} && #{git} reset #{verbose} --hard #{revision}"
184
+ execute << "#{git} fetch #{verbose} #{remote} && #{git} fetch --tags #{verbose} #{remote} && #{git} reset #{verbose} --hard #{revision}"
185
185
 
186
186
  if variable(:git_enable_submodules)
187
187
  execute << "#{git} submodule #{verbose} init"
188
188
  execute << "for mod in `#{git} submodule status | awk '{ print $2 }'`; do #{git} config -f .git/config submodule.${mod}.url `#{git} config -f .gitmodules --get submodule.${mod}.url` && echo Synced $mod; done"
189
189
  execute << "#{git} submodule #{verbose} sync"
190
- execute << "#{git} submodule #{verbose} update"
190
+ execute << "#{git} submodule #{verbose} update --init --recursive"
191
191
  end
192
192
 
193
193
  # Make sure there's nothing else lying around in the repository (for
@@ -58,9 +58,10 @@ module Capistrano
58
58
  raise Capistrano::Error, "shell command failed with return code #{$?}"
59
59
  end
60
60
 
61
+ FileUtils.mkdir_p(destination)
62
+
61
63
  logger.debug "copying cache to deployment staging area #{destination}"
62
64
  Dir.chdir(copy_cache) do
63
- FileUtils.mkdir_p(destination)
64
65
  queue = Dir.glob("*", File::FNM_DOTMATCH)
65
66
  while queue.any?
66
67
  item = queue.shift
@@ -70,12 +71,12 @@ module Capistrano
70
71
  next if copy_exclude.any? { |pattern| File.fnmatch(pattern, item) }
71
72
 
72
73
  if File.symlink?(item)
73
- FileUtils.ln_s(File.readlink(File.join(copy_cache, item)), File.join(destination, item))
74
+ FileUtils.ln_s(File.readlink(item), File.join(destination, item))
74
75
  elsif File.directory?(item)
75
76
  queue += Dir.glob("#{item}/*", File::FNM_DOTMATCH)
76
77
  FileUtils.mkdir(File.join(destination, item))
77
78
  else
78
- FileUtils.ln(File.join(copy_cache, item), File.join(destination, item))
79
+ FileUtils.ln(item, File.join(destination, item))
79
80
  end
80
81
  end
81
82
  end
@@ -99,7 +100,7 @@ module Capistrano
99
100
  File.open(File.join(destination, "REVISION"), "w") { |f| f.puts(revision) }
100
101
 
101
102
  logger.trace "compressing #{destination} to #{filename}"
102
- Dir.chdir(tmpdir) { system(compress(File.basename(destination), File.basename(filename)).join(" ")) }
103
+ Dir.chdir(copy_dir) { system(compress(File.basename(destination), File.basename(filename)).join(" ")) }
103
104
 
104
105
  distribute!
105
106
  ensure
@@ -121,8 +122,8 @@ module Capistrano
121
122
  # is +true+, a default cache location will be returned.
122
123
  def copy_cache
123
124
  @copy_cache ||= configuration[:copy_cache] == true ?
124
- File.join(Dir.tmpdir, configuration[:application]) :
125
- configuration[:copy_cache]
125
+ File.expand_path(configuration[:application], Dir.tmpdir) :
126
+ File.expand_path(configuration[:copy_cache], Dir.pwd) rescue nil
126
127
  end
127
128
 
128
129
  private
@@ -136,7 +137,7 @@ module Capistrano
136
137
  # Returns the basename of the release_path, which will be used to
137
138
  # name the local copy and archive file.
138
139
  def destination
139
- @destination ||= File.join(tmpdir, File.basename(configuration[:release_path]))
140
+ @destination ||= File.join(copy_dir, File.basename(configuration[:release_path]))
140
141
  end
141
142
 
142
143
  # Returns the value of the :copy_strategy variable, defaulting to
@@ -159,12 +160,12 @@ module Capistrano
159
160
  # Returns the name of the file that the source code will be
160
161
  # compressed to.
161
162
  def filename
162
- @filename ||= File.join(tmpdir, "#{File.basename(destination)}.#{compression.extension}")
163
+ @filename ||= File.join(copy_dir, "#{File.basename(destination)}.#{compression.extension}")
163
164
  end
164
165
 
165
166
  # The directory to which the copy should be checked out
166
- def tmpdir
167
- @tmpdir ||= configuration[:copy_dir] || Dir.tmpdir
167
+ def copy_dir
168
+ @copy_dir ||= File.expand_path(configuration[:copy_dir] || Dir.tmpdir, Dir.pwd)
168
169
  end
169
170
 
170
171
  # The directory on the remote server to which the archive should be
@@ -4,7 +4,7 @@ require 'capistrano/configuration/actions/file_transfer'
4
4
  class ConfigurationActionsFileTransferTest < Test::Unit::TestCase
5
5
  class MockConfig
6
6
  include Capistrano::Configuration::Actions::FileTransfer
7
- attr_accessor :sessions
7
+ attr_accessor :sessions, :dry_run
8
8
  end
9
9
 
10
10
  def setup
@@ -1,5 +1,6 @@
1
1
  require "utils"
2
2
  require 'capistrano/configuration/actions/invocation'
3
+ require 'capistrano/configuration/actions/file_transfer'
3
4
 
4
5
  class ConfigurationActionsInvocationTest < Test::Unit::TestCase
5
6
  class MockConfig
@@ -7,9 +8,11 @@ class ConfigurationActionsInvocationTest < Test::Unit::TestCase
7
8
  attr_accessor :debug
8
9
  attr_accessor :dry_run
9
10
  attr_accessor :preserve_roles
11
+ attr_accessor :servers
10
12
 
11
13
  def initialize
12
14
  @options = {}
15
+ @servers = []
13
16
  end
14
17
 
15
18
  def [](*args)
@@ -24,13 +27,17 @@ class ConfigurationActionsInvocationTest < Test::Unit::TestCase
24
27
  @options.fetch(*args)
25
28
  end
26
29
 
30
+ def execute_on_servers(options = {})
31
+ yield @servers
32
+ end
33
+
27
34
  include Capistrano::Configuration::Actions::Invocation
35
+ include Capistrano::Configuration::Actions::FileTransfer
28
36
  end
29
37
 
30
38
  def setup
31
- @config = MockConfig.new
39
+ @config = make_config
32
40
  @original_io_proc = MockConfig.default_io_proc
33
- @config.stubs(:logger).returns(stub_everything)
34
41
  end
35
42
 
36
43
  def teardown
@@ -48,6 +55,15 @@ class ConfigurationActionsInvocationTest < Test::Unit::TestCase
48
55
  @config.run "ls", :foo => "bar"
49
56
  end
50
57
 
58
+ def test_put_wont_transfer_if_dry_run
59
+ config = make_config
60
+ config.dry_run = true
61
+ config.servers = %w[ foo ]
62
+ config.expects(:sessions).returns({ 'foo-server' => 'bar' })
63
+ ::Capistrano::Transfer.expects(:process).never
64
+ config.put "foo", "bar", :mode => 0644
65
+ end
66
+
51
67
  def test_add_default_command_options_should_return_bare_options_if_there_is_no_env_or_shell_specified
52
68
  assert_equal({:foo => "bar"}, @config.add_default_command_options(:foo => "bar"))
53
69
  end
@@ -203,6 +219,12 @@ class ConfigurationActionsInvocationTest < Test::Unit::TestCase
203
219
 
204
220
  private
205
221
 
222
+ def make_config
223
+ config = MockConfig.new
224
+ config.stubs(:logger).returns(stub_everything)
225
+ config
226
+ end
227
+
206
228
  def inspectable_proc
207
229
  Proc.new do |ch, stream, data|
208
230
  ch.called
@@ -81,6 +81,15 @@ class ConfigurationConnectionsTest < Test::Unit::TestCase
81
81
  assert_instance_of Capistrano::Configuration::Connections::GatewayConnectionFactory, @config.connection_factory
82
82
  end
83
83
 
84
+ def test_connection_factory_as_gateway_should_chain_gateways_if_gateway_variable_is_a_hash
85
+ @config.values[:gateway] = { ["j@gateway1", "k@gateway2"] => :default }
86
+ gateway1 = mock
87
+ Net::SSH::Gateway.expects(:new).with("gateway1", "j", :password => nil, :auth_methods => %w(publickey hostbased), :config => false).returns(gateway1)
88
+ gateway1.expects(:open).returns(65535)
89
+ Net::SSH::Gateway.expects(:new).with("127.0.0.1", "k", :port => 65535, :password => nil, :auth_methods => %w(publickey hostbased), :config => false).returns(stub_everything)
90
+ assert_instance_of Capistrano::Configuration::Connections::GatewayConnectionFactory, @config.connection_factory
91
+ end
92
+
84
93
  def test_connection_factory_as_gateway_should_share_gateway_between_connections
85
94
  @config.values[:gateway] = "j@gateway"
86
95
  Net::SSH::Gateway.expects(:new).once.with("gateway", "j", :password => nil, :auth_methods => %w(publickey hostbased), :config => false).returns(stub_everything)
@@ -89,6 +98,26 @@ class ConfigurationConnectionsTest < Test::Unit::TestCase
89
98
  @config.establish_connections_to(server("capistrano"))
90
99
  @config.establish_connections_to(server("another"))
91
100
  end
101
+
102
+ def test_connection_factory_as_gateway_should_share_gateway_between_like_connections_if_gateway_variable_is_a_hash
103
+ @config.values[:gateway] = { "j@gateway" => [ "capistrano", "another"] }
104
+ Net::SSH::Gateway.expects(:new).once.with("gateway", "j", :password => nil, :auth_methods => %w(publickey hostbased), :config => false).returns(stub_everything)
105
+ Capistrano::SSH.stubs(:connect).returns(stub_everything)
106
+ assert_instance_of Capistrano::Configuration::Connections::GatewayConnectionFactory, @config.connection_factory
107
+ @config.establish_connections_to(server("capistrano"))
108
+ @config.establish_connections_to(server("another"))
109
+ end
110
+
111
+ def test_connection_factory_as_gateways_should_not_share_gateway_between_unlike_connections_if_gateway_variable_is_a_hash
112
+ @config.values[:gateway] = { "j@gateway" => [ "capistrano", "another"], "k@gateway2" => "yafhost" }
113
+ Net::SSH::Gateway.expects(:new).once.with("gateway", "j", :password => nil, :auth_methods => %w(publickey hostbased), :config => false).returns(stub_everything)
114
+ Net::SSH::Gateway.expects(:new).once.with("gateway2", "k", :password => nil, :auth_methods => %w(publickey hostbased), :config => false).returns(stub_everything)
115
+ Capistrano::SSH.stubs(:connect).returns(stub_everything)
116
+ assert_instance_of Capistrano::Configuration::Connections::GatewayConnectionFactory, @config.connection_factory
117
+ @config.establish_connections_to(server("capistrano"))
118
+ @config.establish_connections_to(server("another"))
119
+ @config.establish_connections_to(server("yafhost"))
120
+ end
92
121
 
93
122
  def test_establish_connections_to_should_accept_a_single_nonarray_parameter
94
123
  Capistrano::SSH.expects(:connect).with { |s,| s.host == "capistrano" }.returns(:success)
@@ -40,7 +40,7 @@ class DeploySCMGitTest < Test::Unit::TestCase
40
40
 
41
41
  # with submodules
42
42
  @config[:git_enable_submodules] = true
43
- assert_equal "#{git} clone -q git@somehost.com:project.git /var/www && cd /var/www && #{git} checkout -q -b deploy #{rev} && #{git} submodule -q init && #{git} submodule -q sync && #{git} submodule -q update --recursive", @source.checkout(rev, dest).gsub(/\s+/, ' ')
43
+ assert_equal "#{git} clone -q git@somehost.com:project.git /var/www && cd /var/www && #{git} checkout -q -b deploy #{rev} && #{git} submodule -q init && #{git} submodule -q sync && #{git} submodule -q update --init --recursive", @source.checkout(rev, dest).gsub(/\s+/, ' ')
44
44
  end
45
45
 
46
46
  def test_checkout_with_verbose_should_not_use_q_switch
@@ -92,16 +92,16 @@ class DeploySCMGitTest < Test::Unit::TestCase
92
92
  def test_sync
93
93
  dest = "/var/www"
94
94
  rev = 'c2d9e79'
95
- assert_equal "cd #{dest} && git fetch -q origin && git reset -q --hard #{rev} && git clean -q -d -x -f", @source.sync(rev, dest)
95
+ assert_equal "cd #{dest} && git fetch -q origin && git fetch --tags -q origin && git reset -q --hard #{rev} && git clean -q -d -x -f", @source.sync(rev, dest)
96
96
 
97
97
  # With :scm_command
98
98
  git = "/opt/local/bin/git"
99
99
  @config[:scm_command] = git
100
- assert_equal "cd #{dest} && #{git} fetch -q origin && #{git} reset -q --hard #{rev} && #{git} clean -q -d -x -f", @source.sync(rev, dest)
100
+ assert_equal "cd #{dest} && #{git} fetch -q origin && #{git} fetch --tags -q origin && #{git} reset -q --hard #{rev} && #{git} clean -q -d -x -f", @source.sync(rev, dest)
101
101
 
102
102
  # with submodules
103
103
  @config[:git_enable_submodules] = true
104
- assert_equal "cd #{dest} && #{git} fetch -q origin && #{git} reset -q --hard #{rev} && #{git} submodule -q init && for mod in `#{git} submodule status | awk '{ print $2 }'`; do #{git} config -f .git/config submodule.${mod}.url `#{git} config -f .gitmodules --get submodule.${mod}.url` && echo Synced $mod; done && #{git} submodule -q sync && #{git} submodule -q update && #{git} clean -q -d -x -f", @source.sync(rev, dest)
104
+ assert_equal "cd #{dest} && #{git} fetch -q origin && #{git} fetch --tags -q origin && #{git} reset -q --hard #{rev} && #{git} submodule -q init && for mod in `#{git} submodule status | awk '{ print $2 }'`; do #{git} config -f .git/config submodule.${mod}.url `#{git} config -f .gitmodules --get submodule.${mod}.url` && echo Synced $mod; done && #{git} submodule -q sync && #{git} submodule -q update --init --recursive && #{git} clean -q -d -x -f", @source.sync(rev, dest)
105
105
  end
106
106
 
107
107
  def test_sync_with_remote
@@ -113,7 +113,7 @@ class DeploySCMGitTest < Test::Unit::TestCase
113
113
  @config[:repository] = repository
114
114
  @config[:remote] = remote
115
115
 
116
- assert_equal "cd #{dest} && git config remote.#{remote}.url #{repository} && git config remote.#{remote}.fetch +refs/heads/*:refs/remotes/#{remote}/* && git fetch -q #{remote} && git reset -q --hard #{rev} && git clean -q -d -x -f", @source.sync(rev, dest)
116
+ assert_equal "cd #{dest} && git config remote.#{remote}.url #{repository} && git config remote.#{remote}.fetch +refs/heads/*:refs/remotes/#{remote}/* && git fetch -q #{remote} && git fetch --tags -q username && git reset -q --hard #{rev} && git clean -q -d -x -f", @source.sync(rev, dest)
117
117
  end
118
118
 
119
119
  def test_shallow_clone
@@ -138,7 +138,7 @@ class DeploySCMGitTest < Test::Unit::TestCase
138
138
  @config[:git_enable_submodules] = true
139
139
  dest = "/var/www"
140
140
  rev = 'c2d9e79'
141
- assert_equal "git clone -q -o username git@somehost.com:project.git /var/www && cd /var/www && git checkout -q -b deploy #{rev} && git submodule -q init && git submodule -q sync && git submodule -q update --recursive", @source.checkout(rev, dest)
141
+ assert_equal "git clone -q -o username git@somehost.com:project.git /var/www && cd /var/www && git checkout -q -b deploy #{rev} && git submodule -q init && git submodule -q sync && git submodule -q update --init --recursive", @source.checkout(rev, dest)
142
142
  end
143
143
 
144
144
  # Tests from base_test.rb, makin' sure we didn't break anything up there!
@@ -232,7 +232,7 @@ class DeployStrategyCopyTest < Test::Unit::TestCase
232
232
  @strategy.deploy!
233
233
  end
234
234
 
235
- def test_with_copy_cache_with_custom_cache_dir_should_use_specified_cache_dir
235
+ def test_with_copy_cache_with_custom_absolute_cache_dir_path_should_use_specified_cache_dir
236
236
  @config[:copy_cache] = "/u/caches/captest"
237
237
 
238
238
  Dir.stubs(:tmpdir).returns("/temp/dir")
@@ -250,6 +250,25 @@ class DeployStrategyCopyTest < Test::Unit::TestCase
250
250
  @strategy.deploy!
251
251
  end
252
252
 
253
+ def test_with_copy_cache_with_custom_relative_cache_dir_path_should_use_specified_cache_dir
254
+ @config[:copy_cache] = "caches/captest"
255
+
256
+ Dir.stubs(:pwd).returns("/u")
257
+ Dir.stubs(:tmpdir).returns("/temp/dir")
258
+ File.expects(:exists?).with("/u/caches/captest").returns(true)
259
+ Dir.expects(:chdir).with("/u/caches/captest").yields
260
+
261
+ @source.expects(:sync).with("154", "/u/caches/captest").returns(:local_sync)
262
+ @strategy.expects(:system).with(:local_sync)
263
+
264
+ FileUtils.expects(:mkdir_p).with("/temp/dir/1234567890")
265
+
266
+ prepare_directory_tree!("/u/caches/captest")
267
+
268
+ prepare_standard_compress_and_copy!
269
+ @strategy.deploy!
270
+ end
271
+
253
272
  def test_with_copy_cache_with_excludes_should_not_copy_excluded_files
254
273
  @config[:copy_cache] = true
255
274
  @config[:copy_exclude] = "*/bar.txt"
@@ -276,13 +295,13 @@ class DeployStrategyCopyTest < Test::Unit::TestCase
276
295
  File.expects(:directory?).with("app").returns(true)
277
296
  FileUtils.expects(:mkdir).with("/temp/dir/1234567890/app")
278
297
  File.expects(:directory?).with("foo.txt").returns(false)
279
- FileUtils.expects(:ln).with("#{cache}/foo.txt", "/temp/dir/1234567890/foo.txt")
298
+ FileUtils.expects(:ln).with("foo.txt", "/temp/dir/1234567890/foo.txt")
280
299
 
281
300
  Dir.expects(:glob).with("app/*", File::FNM_DOTMATCH).returns(["app/.", "app/..", "app/bar.txt"])
282
301
 
283
302
  unless exclude
284
303
  File.expects(:directory?).with("app/bar.txt").returns(false)
285
- FileUtils.expects(:ln).with("#{cache}/app/bar.txt", "/temp/dir/1234567890/app/bar.txt")
304
+ FileUtils.expects(:ln).with("app/bar.txt", "/temp/dir/1234567890/app/bar.txt")
286
305
  end
287
306
  end
288
307
 
metadata CHANGED
@@ -1,114 +1,130 @@
1
- --- !ruby/object:Gem::Specification
1
+ --- !ruby/object:Gem::Specification
2
2
  name: capistrano
3
- version: !ruby/object:Gem::Version
4
- version: 2.5.22
3
+ version: !ruby/object:Gem::Version
4
+ hash: 23
5
+ prerelease:
6
+ segments:
7
+ - 2
8
+ - 6
9
+ - 0
10
+ version: 2.6.0
5
11
  platform: ruby
6
- authors:
12
+ authors:
7
13
  - Jamis Buck
8
14
  - Lee Hambley
9
15
  autorequire:
10
16
  bindir: bin
11
17
  cert_chain: []
12
- date: 2011-03-22 00:00:00.000000000 Z
13
- dependencies:
14
- - !ruby/object:Gem::Dependency
18
+
19
+ date: 2011-03-22 00:00:00 +01:00
20
+ default_executable:
21
+ dependencies:
22
+ - !ruby/object:Gem::Dependency
15
23
  name: highline
16
- requirement: !ruby/object:Gem::Requirement
17
- requirements:
18
- - - ">="
19
- - !ruby/object:Gem::Version
20
- version: '0'
21
- type: :runtime
22
24
  prerelease: false
23
- version_requirements: !ruby/object:Gem::Requirement
24
- requirements:
25
- - - ">="
26
- - !ruby/object:Gem::Version
27
- version: '0'
28
- - !ruby/object:Gem::Dependency
29
- name: net-ssh
30
- requirement: !ruby/object:Gem::Requirement
31
- requirements:
25
+ requirement: &id001 !ruby/object:Gem::Requirement
26
+ none: false
27
+ requirements:
32
28
  - - ">="
33
- - !ruby/object:Gem::Version
34
- version: 2.0.14
29
+ - !ruby/object:Gem::Version
30
+ hash: 3
31
+ segments:
32
+ - 0
33
+ version: "0"
35
34
  type: :runtime
35
+ version_requirements: *id001
36
+ - !ruby/object:Gem::Dependency
37
+ name: net-ssh
36
38
  prerelease: false
37
- version_requirements: !ruby/object:Gem::Requirement
38
- requirements:
39
+ requirement: &id002 !ruby/object:Gem::Requirement
40
+ none: false
41
+ requirements:
39
42
  - - ">="
40
- - !ruby/object:Gem::Version
43
+ - !ruby/object:Gem::Version
44
+ hash: 19
45
+ segments:
46
+ - 2
47
+ - 0
48
+ - 14
41
49
  version: 2.0.14
42
- - !ruby/object:Gem::Dependency
43
- name: net-sftp
44
- requirement: !ruby/object:Gem::Requirement
45
- requirements:
46
- - - ">="
47
- - !ruby/object:Gem::Version
48
- version: 2.0.0
49
50
  type: :runtime
51
+ version_requirements: *id002
52
+ - !ruby/object:Gem::Dependency
53
+ name: net-sftp
50
54
  prerelease: false
51
- version_requirements: !ruby/object:Gem::Requirement
52
- requirements:
55
+ requirement: &id003 !ruby/object:Gem::Requirement
56
+ none: false
57
+ requirements:
53
58
  - - ">="
54
- - !ruby/object:Gem::Version
59
+ - !ruby/object:Gem::Version
60
+ hash: 15
61
+ segments:
62
+ - 2
63
+ - 0
64
+ - 0
55
65
  version: 2.0.0
56
- - !ruby/object:Gem::Dependency
57
- name: net-scp
58
- requirement: !ruby/object:Gem::Requirement
59
- requirements:
60
- - - ">="
61
- - !ruby/object:Gem::Version
62
- version: 1.0.0
63
66
  type: :runtime
67
+ version_requirements: *id003
68
+ - !ruby/object:Gem::Dependency
69
+ name: net-scp
64
70
  prerelease: false
65
- version_requirements: !ruby/object:Gem::Requirement
66
- requirements:
67
- - - ">="
68
- - !ruby/object:Gem::Version
69
- version: 1.0.0
70
- - !ruby/object:Gem::Dependency
71
- name: net-ssh-gateway
72
- requirement: !ruby/object:Gem::Requirement
73
- requirements:
71
+ requirement: &id004 !ruby/object:Gem::Requirement
72
+ none: false
73
+ requirements:
74
74
  - - ">="
75
- - !ruby/object:Gem::Version
75
+ - !ruby/object:Gem::Version
76
+ hash: 23
77
+ segments:
78
+ - 1
79
+ - 0
80
+ - 0
76
81
  version: 1.0.0
77
82
  type: :runtime
83
+ version_requirements: *id004
84
+ - !ruby/object:Gem::Dependency
85
+ name: net-ssh-gateway
78
86
  prerelease: false
79
- version_requirements: !ruby/object:Gem::Requirement
80
- requirements:
87
+ requirement: &id005 !ruby/object:Gem::Requirement
88
+ none: false
89
+ requirements:
81
90
  - - ">="
82
- - !ruby/object:Gem::Version
83
- version: 1.0.0
84
- - !ruby/object:Gem::Dependency
91
+ - !ruby/object:Gem::Version
92
+ hash: 19
93
+ segments:
94
+ - 1
95
+ - 1
96
+ - 0
97
+ version: 1.1.0
98
+ type: :runtime
99
+ version_requirements: *id005
100
+ - !ruby/object:Gem::Dependency
85
101
  name: mocha
86
- requirement: !ruby/object:Gem::Requirement
87
- requirements:
88
- - - ">="
89
- - !ruby/object:Gem::Version
90
- version: '0'
91
- type: :development
92
102
  prerelease: false
93
- version_requirements: !ruby/object:Gem::Requirement
94
- requirements:
103
+ requirement: &id006 !ruby/object:Gem::Requirement
104
+ none: false
105
+ requirements:
95
106
  - - ">="
96
- - !ruby/object:Gem::Version
97
- version: '0'
98
- description: Capistrano is a utility and framework for executing commands in parallel
99
- on multiple remote machines, via SSH.
100
- email:
107
+ - !ruby/object:Gem::Version
108
+ hash: 3
109
+ segments:
110
+ - 0
111
+ version: "0"
112
+ type: :development
113
+ version_requirements: *id006
114
+ description: Capistrano is a utility and framework for executing commands in parallel on multiple remote machines, via SSH.
115
+ email:
101
116
  - jamis@jamisbuck.org
102
117
  - lee.hambley@gmail.com
103
- executables:
118
+ executables:
104
119
  - cap
105
120
  - capify
106
121
  extensions: []
107
- extra_rdoc_files:
122
+
123
+ extra_rdoc_files:
108
124
  - README.mdown
109
- files:
110
- - ".gitignore"
111
- - ".rvmrc"
125
+ files:
126
+ - .gitignore
127
+ - .rvmrc
112
128
  - CHANGELOG
113
129
  - Gemfile
114
130
  - README.mdown
@@ -217,30 +233,41 @@ files:
217
233
  - test/task_definition_test.rb
218
234
  - test/transfer_test.rb
219
235
  - test/utils.rb
236
+ has_rdoc: true
220
237
  homepage: http://github.com/capistrano/capistrano
221
238
  licenses: []
222
- metadata: {}
239
+
223
240
  post_install_message:
224
241
  rdoc_options: []
225
- require_paths:
242
+
243
+ require_paths:
226
244
  - lib
227
- required_ruby_version: !ruby/object:Gem::Requirement
228
- requirements:
245
+ required_ruby_version: !ruby/object:Gem::Requirement
246
+ none: false
247
+ requirements:
229
248
  - - ">="
230
- - !ruby/object:Gem::Version
231
- version: '0'
232
- required_rubygems_version: !ruby/object:Gem::Requirement
233
- requirements:
249
+ - !ruby/object:Gem::Version
250
+ hash: 3
251
+ segments:
252
+ - 0
253
+ version: "0"
254
+ required_rubygems_version: !ruby/object:Gem::Requirement
255
+ none: false
256
+ requirements:
234
257
  - - ">="
235
- - !ruby/object:Gem::Version
236
- version: '0'
258
+ - !ruby/object:Gem::Version
259
+ hash: 3
260
+ segments:
261
+ - 0
262
+ version: "0"
237
263
  requirements: []
264
+
238
265
  rubyforge_project:
239
- rubygems_version: 2.6.3
266
+ rubygems_version: 1.6.2
240
267
  signing_key:
241
268
  specification_version: 3
242
269
  summary: Capistrano - Welcome to easy deployment with Ruby over SSH
243
- test_files:
270
+ test_files:
244
271
  - test/cli/execute_test.rb
245
272
  - test/cli/help_test.rb
246
273
  - test/cli/options_test.rb
checksums.yaml DELETED
@@ -1,7 +0,0 @@
1
- ---
2
- SHA1:
3
- metadata.gz: dd3e47b31f5733b124cf9106d52ce64876fce150
4
- data.tar.gz: e26eb9054ce03bca5b0b54db956d30a070b7fce7
5
- SHA512:
6
- metadata.gz: c2e3dbcfed0c70cfa919c8269eecfe54bddc14881bc5d480d934a75be37cfdc584bb45af515813bd82901bfb9bb17fb19a3fcf81e391b08029215e7e62afc50d
7
- data.tar.gz: d643fa943cb3408cb66eaf4255e44afb5c48bd98d1d9e105657b3970135c13344b22c9b3195f4bcbb8b5186f50d807a51cac53cb70acd10a97fe67c822ef4da7