capistrano 3.6.0 → 3.7.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/.github/issue_template.md +19 -0
- data/.github/pull_request_template.md +26 -0
- data/.gitignore +1 -0
- data/.travis.yml +10 -2
- data/CHANGELOG.md +63 -1
- data/DEVELOPMENT.md +7 -1
- data/Dangerfile +54 -0
- data/README.md +4 -5
- data/capistrano.gemspec +3 -2
- data/features/support/vagrant_helpers.rb +3 -5
- data/lib/capistrano/all.rb +1 -0
- data/lib/capistrano/configuration/host_filter.rb +1 -1
- data/lib/capistrano/configuration/plugin_installer.rb +20 -2
- data/lib/capistrano/configuration/role_filter.rb +1 -1
- data/lib/capistrano/configuration/scm_resolver.rb +144 -0
- data/lib/capistrano/configuration/validated_variables.rb +48 -13
- data/lib/capistrano/configuration/variables.rb +0 -8
- data/lib/capistrano/configuration.rb +30 -3
- data/lib/capistrano/defaults.rb +3 -1
- data/lib/capistrano/doctor/variables_doctor.rb +1 -1
- data/lib/capistrano/dsl/env.rb +2 -9
- data/lib/capistrano/dsl/paths.rb +1 -1
- data/lib/capistrano/dsl/task_enhancements.rb +0 -8
- data/lib/capistrano/dsl.rb +2 -1
- data/lib/capistrano/i18n.rb +1 -0
- data/lib/capistrano/scm/git.rb +73 -0
- data/lib/capistrano/scm/hg.rb +48 -0
- data/lib/capistrano/scm/plugin.rb +13 -0
- data/lib/capistrano/scm/svn.rb +47 -0
- data/lib/capistrano/{tasks → scm/tasks}/git.rake +9 -24
- data/lib/capistrano/{tasks → scm/tasks}/hg.rake +11 -10
- data/lib/capistrano/{tasks → scm/tasks}/svn.rake +11 -10
- data/lib/capistrano/setup.rb +1 -1
- data/lib/capistrano/tasks/deploy.rake +4 -5
- data/lib/capistrano/templates/Capfile +18 -7
- data/lib/capistrano/templates/deploy.rb.erb +7 -10
- data/lib/capistrano/templates/stage.rb.erb +8 -8
- data/lib/capistrano/version.rb +1 -1
- data/lib/capistrano/version_validator.rb +2 -5
- data/spec/lib/capistrano/configuration/host_filter_spec.rb +5 -0
- data/spec/lib/capistrano/configuration/plugin_installer_spec.rb +98 -0
- data/spec/lib/capistrano/configuration/role_filter_spec.rb +17 -1
- data/spec/lib/capistrano/configuration_spec.rb +61 -2
- data/spec/lib/capistrano/doctor/variables_doctor_spec.rb +0 -7
- data/spec/lib/capistrano/dsl/task_enhancements_spec.rb +0 -15
- data/spec/lib/capistrano/scm/git_spec.rb +131 -0
- data/spec/lib/capistrano/scm/hg_spec.rb +104 -0
- data/spec/lib/capistrano/scm/svn_spec.rb +116 -0
- data/spec/lib/capistrano/scm_spec.rb +1 -1
- metadata +37 -19
- data/features/remote_file_task.feature +0 -14
- data/issue_template.md +0 -21
- data/lib/capistrano/git.rb +0 -54
- data/lib/capistrano/hg.rb +0 -43
- data/lib/capistrano/svn.rb +0 -42
- data/spec/lib/capistrano/git_spec.rb +0 -109
- data/spec/lib/capistrano/hg_spec.rb +0 -90
- data/spec/lib/capistrano/svn_spec.rb +0 -105
@@ -102,12 +102,33 @@ module Capistrano
|
|
102
102
|
end
|
103
103
|
end
|
104
104
|
|
105
|
+
def configure_scm
|
106
|
+
Capistrano::Configuration::SCMResolver.new.resolve
|
107
|
+
end
|
108
|
+
|
105
109
|
def timestamp
|
106
110
|
@timestamp ||= Time.now.utc
|
107
111
|
end
|
108
112
|
|
113
|
+
def add_filter(filter=nil, &block)
|
114
|
+
if block
|
115
|
+
raise ArgumentError, "Both a block and an object were given" if filter
|
116
|
+
|
117
|
+
filter = Object.new
|
118
|
+
def filter.filter(servers)
|
119
|
+
block.call(servers)
|
120
|
+
end
|
121
|
+
elsif !filter.respond_to? :filter
|
122
|
+
raise TypeError, "Provided custom filter <#{filter.inspect}> does " \
|
123
|
+
"not have a public 'filter' method"
|
124
|
+
end
|
125
|
+
@custom_filters ||= []
|
126
|
+
@custom_filters << filter
|
127
|
+
end
|
128
|
+
|
109
129
|
def setup_filters
|
110
|
-
@filters = cmdline_filters
|
130
|
+
@filters = cmdline_filters
|
131
|
+
@filters += @custom_filters if @custom_filters
|
111
132
|
@filters << Filter.new(:role, ENV["ROLES"]) if ENV["ROLES"]
|
112
133
|
@filters << Filter.new(:host, ENV["HOSTS"]) if ENV["HOSTS"]
|
113
134
|
fh = fetch_for(:filter, {}) || {}
|
@@ -130,8 +151,14 @@ module Capistrano
|
|
130
151
|
fetch(:sshkit_backend) == SSHKit::Backend::Printer
|
131
152
|
end
|
132
153
|
|
133
|
-
def install_plugin(plugin, load_hooks: true)
|
134
|
-
installer.install(plugin,
|
154
|
+
def install_plugin(plugin, load_hooks: true, load_immediately: false)
|
155
|
+
installer.install(plugin,
|
156
|
+
load_hooks: load_hooks,
|
157
|
+
load_immediately: load_immediately)
|
158
|
+
end
|
159
|
+
|
160
|
+
def scm_plugin_installed?
|
161
|
+
installer.scm_installed?
|
135
162
|
end
|
136
163
|
|
137
164
|
def servers
|
data/lib/capistrano/defaults.rb
CHANGED
@@ -18,7 +18,9 @@ end
|
|
18
18
|
end
|
19
19
|
end
|
20
20
|
|
21
|
-
|
21
|
+
# We use a special :_default_git value so that SCMResolver can tell whether the
|
22
|
+
# default has been replaced by the user via `set`.
|
23
|
+
set_if_empty :scm, Capistrano::Configuration::SCMResolver::DEFAULT_GIT
|
22
24
|
set_if_empty :branch, "master"
|
23
25
|
set_if_empty :deploy_to, -> { "/var/www/#{fetch(:application)}" }
|
24
26
|
set_if_empty :tmp_dir, "/tmp"
|
@@ -7,7 +7,7 @@ module Capistrano
|
|
7
7
|
class VariablesDoctor
|
8
8
|
# These are keys that have no default values in Capistrano, but are
|
9
9
|
# nonetheless expected to be set.
|
10
|
-
WHITELIST = [:application, :repo_url
|
10
|
+
WHITELIST = [:application, :repo_url].freeze
|
11
11
|
private_constant :WHITELIST
|
12
12
|
|
13
13
|
include Capistrano::Doctor::OutputHelpers
|
data/lib/capistrano/dsl/env.rb
CHANGED
@@ -7,15 +7,8 @@ module Capistrano
|
|
7
7
|
def_delegators :env,
|
8
8
|
:configure_backend, :fetch, :set, :set_if_empty, :delete,
|
9
9
|
:ask, :role, :server, :primary, :validate, :append,
|
10
|
-
:remove, :dry_run?, :install_plugin
|
11
|
-
|
12
|
-
def is_question?(key)
|
13
|
-
env.is_question?(key)
|
14
|
-
end
|
15
|
-
|
16
|
-
def any?(key)
|
17
|
-
env.any?(key)
|
18
|
-
end
|
10
|
+
:remove, :dry_run?, :install_plugin, :any?, :is_question?,
|
11
|
+
:configure_scm, :scm_plugin_installed?
|
19
12
|
|
20
13
|
def roles(*names)
|
21
14
|
env.roles_for(names.flatten)
|
data/lib/capistrano/dsl/paths.rb
CHANGED
@@ -17,14 +17,6 @@ module Capistrano
|
|
17
17
|
end
|
18
18
|
end
|
19
19
|
|
20
|
-
def remote_file(task)
|
21
|
-
warn("[Deprecation Warning] `remote_file` is deprecated and will be "\
|
22
|
-
"removed in Capistrano 3.7.0")
|
23
|
-
|
24
|
-
target_roles = task.delete(:roles) { :all }
|
25
|
-
define_remote_file_task(task, target_roles)
|
26
|
-
end
|
27
|
-
|
28
20
|
def define_remote_file_task(task, target_roles)
|
29
21
|
Capistrano::UploadTask.define_task(task) do |t|
|
30
22
|
prerequisite_file = t.prerequisites.first
|
data/lib/capistrano/dsl.rb
CHANGED
@@ -13,7 +13,8 @@ module Capistrano
|
|
13
13
|
|
14
14
|
def invoke(task_name, *args)
|
15
15
|
task = Rake::Task[task_name]
|
16
|
-
|
16
|
+
# NOTE: We access instance variable since the accessor was only added recently. Once Capistrano depends on rake 11+, we can revert the following line
|
17
|
+
if task && task.instance_variable_get(:@already_invoked)
|
17
18
|
file, line, = caller.first.split(":")
|
18
19
|
colors = SSHKit::Color.new($stderr)
|
19
20
|
$stderr.puts colors.colorize("Skipping task `#{task_name}'.", :yellow)
|
data/lib/capistrano/i18n.rb
CHANGED
@@ -12,6 +12,7 @@ en = {
|
|
12
12
|
written_file: "create %{file}",
|
13
13
|
question: "Please enter %{key} (%{default_value}): ",
|
14
14
|
keeping_releases: "Keeping %{keep_releases} of %{releases} deployed releases on %{host}",
|
15
|
+
skip_cleanup: "Skipping cleanup of old releases on %{host}; unexpected foldername found (should be timestamp)",
|
15
16
|
no_old_releases: "No old releases (keeping newest %{keep_releases}) on %{host}",
|
16
17
|
linked_file_does_not_exist: "linked file %{file} does not exist on %{host}",
|
17
18
|
cannot_rollback: "There are no older releases to rollback to",
|
@@ -0,0 +1,73 @@
|
|
1
|
+
require "capistrano/scm/plugin"
|
2
|
+
|
3
|
+
class Capistrano::SCM::Git < Capistrano::SCM::Plugin
|
4
|
+
def set_defaults
|
5
|
+
set_if_empty :git_shallow_clone, false
|
6
|
+
set_if_empty :git_wrapper_path, lambda {
|
7
|
+
# Try to avoid permissions issues when multiple users deploy the same app
|
8
|
+
# by using different file names in the same dir for each deployer and stage.
|
9
|
+
suffix = [:application, :stage, :local_user].map { |key| fetch(key).to_s }.join("-").gsub(/\s+/, "-")
|
10
|
+
"#{fetch(:tmp_dir)}/git-ssh-#{suffix}.sh"
|
11
|
+
}
|
12
|
+
set_if_empty :git_environmental_variables, lambda {
|
13
|
+
{
|
14
|
+
git_askpass: "/bin/echo",
|
15
|
+
git_ssh: fetch(:git_wrapper_path)
|
16
|
+
}
|
17
|
+
}
|
18
|
+
end
|
19
|
+
|
20
|
+
def register_hooks
|
21
|
+
after "deploy:new_release_path", "git:create_release"
|
22
|
+
before "deploy:check", "git:check"
|
23
|
+
before "deploy:set_current_revision", "git:set_current_revision"
|
24
|
+
end
|
25
|
+
|
26
|
+
def define_tasks
|
27
|
+
eval_rakefile File.expand_path("../tasks/git.rake", __FILE__)
|
28
|
+
end
|
29
|
+
|
30
|
+
def repo_mirror_exists?
|
31
|
+
backend.test " [ -f #{repo_path}/HEAD ] "
|
32
|
+
end
|
33
|
+
|
34
|
+
def check_repo_is_reachable
|
35
|
+
git :'ls-remote --heads', repo_url
|
36
|
+
end
|
37
|
+
|
38
|
+
def clone_repo
|
39
|
+
if (depth = fetch(:git_shallow_clone))
|
40
|
+
git :clone, "--mirror", "--depth", depth, "--no-single-branch", repo_url, repo_path.to_s
|
41
|
+
else
|
42
|
+
git :clone, "--mirror", repo_url, repo_path.to_s
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
def update_mirror
|
47
|
+
# Note: Requires git version 1.9 or greater
|
48
|
+
if (depth = fetch(:git_shallow_clone))
|
49
|
+
git :fetch, "--depth", depth, "origin", fetch(:branch)
|
50
|
+
else
|
51
|
+
git :remote, :update, "--prune"
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
def archive_to_release_path
|
56
|
+
if (tree = fetch(:repo_tree))
|
57
|
+
tree = tree.slice %r#^/?(.*?)/?$#, 1
|
58
|
+
components = tree.split("/").size
|
59
|
+
git :archive, fetch(:branch), tree, "| #{SSHKit.config.command_map[:tar]} -x --strip-components #{components} -f - -C", release_path
|
60
|
+
else
|
61
|
+
git :archive, fetch(:branch), "| #{SSHKit.config.command_map[:tar]} -x -f - -C", release_path
|
62
|
+
end
|
63
|
+
end
|
64
|
+
|
65
|
+
def fetch_revision
|
66
|
+
backend.capture(:git, "rev-list --max-count=1 #{fetch(:branch)}")
|
67
|
+
end
|
68
|
+
|
69
|
+
def git(*args)
|
70
|
+
args.unshift :git
|
71
|
+
backend.execute(*args)
|
72
|
+
end
|
73
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require "capistrano/scm/plugin"
|
2
|
+
|
3
|
+
class Capistrano::SCM::Hg < Capistrano::SCM::Plugin
|
4
|
+
def register_hooks
|
5
|
+
after "deploy:new_release_path", "hg:create_release"
|
6
|
+
before "deploy:check", "hg:check"
|
7
|
+
before "deploy:set_current_revision", "hg:set_current_revision"
|
8
|
+
end
|
9
|
+
|
10
|
+
def define_tasks
|
11
|
+
eval_rakefile File.expand_path("../tasks/hg.rake", __FILE__)
|
12
|
+
end
|
13
|
+
|
14
|
+
def hg(*args)
|
15
|
+
args.unshift(:hg)
|
16
|
+
backend.execute(*args)
|
17
|
+
end
|
18
|
+
|
19
|
+
def repo_mirror_exists?
|
20
|
+
backend.test " [ -d #{repo_path}/.hg ] "
|
21
|
+
end
|
22
|
+
|
23
|
+
def check_repo_is_reachable
|
24
|
+
hg "id", repo_url
|
25
|
+
end
|
26
|
+
|
27
|
+
def clone_repo
|
28
|
+
hg "clone", "--noupdate", repo_url, repo_path.to_s
|
29
|
+
end
|
30
|
+
|
31
|
+
def update_mirror
|
32
|
+
hg "pull"
|
33
|
+
end
|
34
|
+
|
35
|
+
def archive_to_release_path
|
36
|
+
if (tree = fetch(:repo_tree))
|
37
|
+
tree = tree.slice %r#^/?(.*?)/?$#, 1
|
38
|
+
components = tree.split("/").size
|
39
|
+
hg "archive --type tgz -p . -I", tree, "--rev", fetch(:branch), "| tar -x --strip-components #{components} -f - -C", release_path
|
40
|
+
else
|
41
|
+
hg "archive", release_path, "--rev", fetch(:branch)
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
def fetch_revision
|
46
|
+
backend.capture(:hg, "log --rev #{fetch(:branch)} --template \"{node}\n\"")
|
47
|
+
end
|
48
|
+
end
|
@@ -0,0 +1,13 @@
|
|
1
|
+
require "capistrano/plugin"
|
2
|
+
require "capistrano/scm"
|
3
|
+
|
4
|
+
# Base class for all built-in and third-party SCM plugins. Notice that this
|
5
|
+
# class doesn't really do anything other than provide an `scm?` predicate. This
|
6
|
+
# tells Capistrano that the plugin provides SCM functionality. All other plugin
|
7
|
+
# features are inherited from Capistrano::Plugin.
|
8
|
+
#
|
9
|
+
class Capistrano::SCM::Plugin < Capistrano::Plugin
|
10
|
+
def scm?
|
11
|
+
true
|
12
|
+
end
|
13
|
+
end
|
@@ -0,0 +1,47 @@
|
|
1
|
+
require "capistrano/scm/plugin"
|
2
|
+
|
3
|
+
class Capistrano::SCM::Svn < Capistrano::SCM::Plugin
|
4
|
+
def register_hooks
|
5
|
+
after "deploy:new_release_path", "svn:create_release"
|
6
|
+
before "deploy:check", "svn:check"
|
7
|
+
before "deploy:set_current_revision", "svn:set_current_revision"
|
8
|
+
end
|
9
|
+
|
10
|
+
def define_tasks
|
11
|
+
eval_rakefile File.expand_path("../tasks/svn.rake", __FILE__)
|
12
|
+
end
|
13
|
+
|
14
|
+
def svn(*args)
|
15
|
+
args.unshift(:svn)
|
16
|
+
args.push "--username #{fetch(:svn_username)}" if fetch(:svn_username)
|
17
|
+
args.push "--password #{fetch(:svn_password)}" if fetch(:svn_password)
|
18
|
+
args.push "--revision #{fetch(:svn_revision)}" if fetch(:svn_revision)
|
19
|
+
backend.execute(*args)
|
20
|
+
end
|
21
|
+
|
22
|
+
def repo_mirror_exists?
|
23
|
+
backend.test " [ -d #{repo_path}/.svn ] "
|
24
|
+
end
|
25
|
+
|
26
|
+
def check_repo_is_reachable
|
27
|
+
svn_username = fetch(:svn_username) ? "--username #{fetch(:svn_username)}" : ""
|
28
|
+
svn_password = fetch(:svn_password) ? "--password #{fetch(:svn_password)}" : ""
|
29
|
+
backend.test :svn, :info, repo_url, svn_username, svn_password
|
30
|
+
end
|
31
|
+
|
32
|
+
def clone_repo
|
33
|
+
svn :checkout, repo_url, repo_path.to_s
|
34
|
+
end
|
35
|
+
|
36
|
+
def update_mirror
|
37
|
+
svn :update
|
38
|
+
end
|
39
|
+
|
40
|
+
def archive_to_release_path
|
41
|
+
svn :export, "--force", ".", release_path
|
42
|
+
end
|
43
|
+
|
44
|
+
def fetch_revision
|
45
|
+
backend.capture(:svnversion, repo_path.to_s)
|
46
|
+
end
|
47
|
+
end
|
@@ -1,22 +1,7 @@
|
|
1
|
-
|
2
|
-
|
3
|
-
@strategy ||= Capistrano::Git.new(self, fetch(:git_strategy, Capistrano::Git::DefaultStrategy))
|
4
|
-
end
|
5
|
-
|
6
|
-
set :git_wrapper_path, lambda {
|
7
|
-
# Try to avoid permissions issues when multiple users deploy the same app
|
8
|
-
# by using different file names in the same dir for each deployer and stage.
|
9
|
-
suffix = [:application, :stage, :local_user].map { |key| fetch(key).to_s }.join("-")
|
10
|
-
"#{fetch(:tmp_dir)}/git-ssh-#{suffix}.sh"
|
11
|
-
}
|
12
|
-
|
13
|
-
set :git_environmental_variables, lambda {
|
14
|
-
{
|
15
|
-
git_askpass: "/bin/echo",
|
16
|
-
git_ssh: fetch(:git_wrapper_path)
|
17
|
-
}
|
18
|
-
}
|
1
|
+
# This trick lets us access the Git plugin within `on` blocks.
|
2
|
+
git_plugin = self
|
19
3
|
|
4
|
+
namespace :git do
|
20
5
|
desc "Upload the git wrapper script, this script guarantees that we can script git without getting an interactive prompt"
|
21
6
|
task :wrapper do
|
22
7
|
on release_roles :all do
|
@@ -31,7 +16,7 @@ namespace :git do
|
|
31
16
|
fetch(:branch)
|
32
17
|
on release_roles :all do
|
33
18
|
with fetch(:git_environmental_variables) do
|
34
|
-
|
19
|
+
git_plugin.check_repo_is_reachable
|
35
20
|
end
|
36
21
|
end
|
37
22
|
end
|
@@ -39,12 +24,12 @@ namespace :git do
|
|
39
24
|
desc "Clone the repo to the cache"
|
40
25
|
task clone: :'git:wrapper' do
|
41
26
|
on release_roles :all do
|
42
|
-
if
|
27
|
+
if git_plugin.repo_mirror_exists?
|
43
28
|
info t(:mirror_exists, at: repo_path)
|
44
29
|
else
|
45
30
|
within deploy_path do
|
46
31
|
with fetch(:git_environmental_variables) do
|
47
|
-
|
32
|
+
git_plugin.clone_repo
|
48
33
|
end
|
49
34
|
end
|
50
35
|
end
|
@@ -56,7 +41,7 @@ namespace :git do
|
|
56
41
|
on release_roles :all do
|
57
42
|
within repo_path do
|
58
43
|
with fetch(:git_environmental_variables) do
|
59
|
-
|
44
|
+
git_plugin.update_mirror
|
60
45
|
end
|
61
46
|
end
|
62
47
|
end
|
@@ -68,7 +53,7 @@ namespace :git do
|
|
68
53
|
with fetch(:git_environmental_variables) do
|
69
54
|
within repo_path do
|
70
55
|
execute :mkdir, "-p", release_path
|
71
|
-
|
56
|
+
git_plugin.archive_to_release_path
|
72
57
|
end
|
73
58
|
end
|
74
59
|
end
|
@@ -79,7 +64,7 @@ namespace :git do
|
|
79
64
|
on release_roles :all do
|
80
65
|
within repo_path do
|
81
66
|
with fetch(:git_environmental_variables) do
|
82
|
-
set :current_revision,
|
67
|
+
set :current_revision, git_plugin.fetch_revision
|
83
68
|
end
|
84
69
|
end
|
85
70
|
end
|
@@ -1,23 +1,24 @@
|
|
1
|
-
|
2
|
-
def strategy
|
3
|
-
@strategy ||= Capistrano::Hg.new(self, fetch(:hg_strategy, Capistrano::Hg::DefaultStrategy))
|
4
|
-
end
|
1
|
+
# TODO: this is nearly identical to git.rake. DRY up?
|
5
2
|
|
3
|
+
# This trick lets us access the Hg plugin within `on` blocks.
|
4
|
+
hg_plugin = self
|
5
|
+
|
6
|
+
namespace :hg do
|
6
7
|
desc "Check that the repo is reachable"
|
7
8
|
task :check do
|
8
9
|
on release_roles :all do
|
9
|
-
|
10
|
+
hg_plugin.check_repo_is_reachable
|
10
11
|
end
|
11
12
|
end
|
12
13
|
|
13
14
|
desc "Clone the repo to the cache"
|
14
15
|
task :clone do
|
15
16
|
on release_roles :all do
|
16
|
-
if
|
17
|
+
if hg_plugin.repo_mirror_exists?
|
17
18
|
info t(:mirror_exists, at: repo_path)
|
18
19
|
else
|
19
20
|
within deploy_path do
|
20
|
-
|
21
|
+
hg_plugin.clone_repo
|
21
22
|
end
|
22
23
|
end
|
23
24
|
end
|
@@ -27,7 +28,7 @@ namespace :hg do
|
|
27
28
|
task update: :'hg:clone' do
|
28
29
|
on release_roles :all do
|
29
30
|
within repo_path do
|
30
|
-
|
31
|
+
hr.update_mirror
|
31
32
|
end
|
32
33
|
end
|
33
34
|
end
|
@@ -36,7 +37,7 @@ namespace :hg do
|
|
36
37
|
task create_release: :'hg:update' do
|
37
38
|
on release_roles :all do
|
38
39
|
within repo_path do
|
39
|
-
|
40
|
+
hg_plugin.archive_to_release_path
|
40
41
|
end
|
41
42
|
end
|
42
43
|
end
|
@@ -45,7 +46,7 @@ namespace :hg do
|
|
45
46
|
task :set_current_revision do
|
46
47
|
on release_roles :all do
|
47
48
|
within repo_path do
|
48
|
-
set :current_revision,
|
49
|
+
set :current_revision, hg_plugin.fetch_revision
|
49
50
|
end
|
50
51
|
end
|
51
52
|
end
|
@@ -1,23 +1,24 @@
|
|
1
|
-
|
2
|
-
def strategy
|
3
|
-
@strategy ||= Capistrano::Svn.new(self, fetch(:svn_strategy, Capistrano::Svn::DefaultStrategy))
|
4
|
-
end
|
1
|
+
# TODO: this is nearly identical to git.rake. DRY up?
|
5
2
|
|
3
|
+
# This trick lets us access the Svn plugin within `on` blocks.
|
4
|
+
svn_plugin = self
|
5
|
+
|
6
|
+
namespace :svn do
|
6
7
|
desc "Check that the repo is reachable"
|
7
8
|
task :check do
|
8
9
|
on release_roles :all do
|
9
|
-
|
10
|
+
svn_plugin.check_repo_is_reachable
|
10
11
|
end
|
11
12
|
end
|
12
13
|
|
13
14
|
desc "Clone the repo to the cache"
|
14
15
|
task :clone do
|
15
16
|
on release_roles :all do
|
16
|
-
if
|
17
|
+
if svn_plugin.repo_mirror_exists?
|
17
18
|
info t(:mirror_exists, at: repo_path)
|
18
19
|
else
|
19
20
|
within deploy_path do
|
20
|
-
|
21
|
+
svn_plugin.clone_repo
|
21
22
|
end
|
22
23
|
end
|
23
24
|
end
|
@@ -27,7 +28,7 @@ namespace :svn do
|
|
27
28
|
task update: :'svn:clone' do
|
28
29
|
on release_roles :all do
|
29
30
|
within repo_path do
|
30
|
-
|
31
|
+
svn_plugin.update_mirror
|
31
32
|
end
|
32
33
|
end
|
33
34
|
end
|
@@ -36,7 +37,7 @@ namespace :svn do
|
|
36
37
|
task create_release: :'svn:update' do
|
37
38
|
on release_roles :all do
|
38
39
|
within repo_path do
|
39
|
-
|
40
|
+
svn_plugin.archive_to_release_path
|
40
41
|
end
|
41
42
|
end
|
42
43
|
end
|
@@ -45,7 +46,7 @@ namespace :svn do
|
|
45
46
|
task :set_current_revision do
|
46
47
|
on release_roles :all do
|
47
48
|
within repo_path do
|
48
|
-
set :current_revision,
|
49
|
+
set :current_revision, svn_plugin.fetch_revision
|
49
50
|
end
|
50
51
|
end
|
51
52
|
end
|
data/lib/capistrano/setup.rb
CHANGED
@@ -26,7 +26,6 @@ namespace :deploy do
|
|
26
26
|
end
|
27
27
|
|
28
28
|
task updating: :new_release_path do
|
29
|
-
invoke "#{scm}:create_release"
|
30
29
|
invoke "deploy:set_current_revision"
|
31
30
|
invoke "deploy:symlink:shared"
|
32
31
|
end
|
@@ -53,7 +52,6 @@ namespace :deploy do
|
|
53
52
|
|
54
53
|
desc "Check required files and directories exist"
|
55
54
|
task :check do
|
56
|
-
invoke "#{scm}:check"
|
57
55
|
invoke "deploy:check:directories"
|
58
56
|
invoke "deploy:check:linked_dirs"
|
59
57
|
invoke "deploy:check:make_linked_dirs"
|
@@ -150,8 +148,10 @@ namespace :deploy do
|
|
150
148
|
desc "Clean up old releases"
|
151
149
|
task :cleanup do
|
152
150
|
on release_roles :all do |host|
|
153
|
-
releases = capture(:ls, "-
|
154
|
-
if releases.
|
151
|
+
releases = capture(:ls, "-x", releases_path).split
|
152
|
+
if !(releases.all? { |e| /^\d{14}$/ =~ e })
|
153
|
+
warn t(:skip_cleanup, host: host.to_s)
|
154
|
+
elsif releases.count >= fetch(:keep_releases)
|
155
155
|
info t(:keeping_releases, host: host.to_s, keep_releases: fetch(:keep_releases), releases: releases.count)
|
156
156
|
directories = (releases - releases.last(fetch(:keep_releases)))
|
157
157
|
if directories.any?
|
@@ -225,7 +225,6 @@ namespace :deploy do
|
|
225
225
|
|
226
226
|
desc "Place a REVISION file with the current revision SHA in the current release path"
|
227
227
|
task :set_current_revision do
|
228
|
-
invoke "#{scm}:set_current_revision"
|
229
228
|
on release_roles(:all) do
|
230
229
|
within release_path do
|
231
230
|
execute :echo, "\"#{fetch(:current_revision)}\" >> REVISION"
|
@@ -4,6 +4,17 @@ require "capistrano/setup"
|
|
4
4
|
# Include default deployment tasks
|
5
5
|
require "capistrano/deploy"
|
6
6
|
|
7
|
+
# Load the SCM plugin appropriate to your project:
|
8
|
+
#
|
9
|
+
# require "capistrano/scm/hg"
|
10
|
+
# install_plugin Capistrano::SCM::Hg
|
11
|
+
# or
|
12
|
+
# require "capistrano/scm/svn"
|
13
|
+
# install_plugin Capistrano::SCM::Svn
|
14
|
+
# or
|
15
|
+
require "capistrano/scm/git"
|
16
|
+
install_plugin Capistrano::SCM::Git
|
17
|
+
|
7
18
|
# Include tasks from other gems included in your Gemfile
|
8
19
|
#
|
9
20
|
# For documentation on these, see for example:
|
@@ -15,13 +26,13 @@ require "capistrano/deploy"
|
|
15
26
|
# https://github.com/capistrano/rails
|
16
27
|
# https://github.com/capistrano/passenger
|
17
28
|
#
|
18
|
-
# require
|
19
|
-
# require
|
20
|
-
# require
|
21
|
-
# require
|
22
|
-
# require
|
23
|
-
# require
|
24
|
-
# require
|
29
|
+
# require "capistrano/rvm"
|
30
|
+
# require "capistrano/rbenv"
|
31
|
+
# require "capistrano/chruby"
|
32
|
+
# require "capistrano/bundler"
|
33
|
+
# require "capistrano/rails/assets"
|
34
|
+
# require "capistrano/rails/migrations"
|
35
|
+
# require "capistrano/passenger"
|
25
36
|
|
26
37
|
# Load custom tasks from `lib/capistrano/tasks` if you have any defined
|
27
38
|
Dir.glob("lib/capistrano/tasks/*.rake").each { |r| import r }
|
@@ -1,33 +1,30 @@
|
|
1
1
|
# config valid only for current version of Capistrano
|
2
|
-
lock
|
2
|
+
lock "<%= Capistrano::VERSION %>"
|
3
3
|
|
4
|
-
set :application,
|
5
|
-
set :repo_url,
|
4
|
+
set :application, "my_app_name"
|
5
|
+
set :repo_url, "git@example.com:me/my_repo.git"
|
6
6
|
|
7
7
|
# Default branch is :master
|
8
8
|
# ask :branch, `git rev-parse --abbrev-ref HEAD`.chomp
|
9
9
|
|
10
10
|
# Default deploy_to directory is /var/www/my_app_name
|
11
|
-
# set :deploy_to,
|
12
|
-
|
13
|
-
# Default value for :scm is :git
|
14
|
-
# set :scm, :git
|
11
|
+
# set :deploy_to, "/var/www/my_app_name"
|
15
12
|
|
16
13
|
# Default value for :format is :airbrussh.
|
17
14
|
# set :format, :airbrussh
|
18
15
|
|
19
16
|
# You can configure the Airbrussh format using :format_options.
|
20
17
|
# These are the defaults.
|
21
|
-
# set :format_options, command_output: true, log_file:
|
18
|
+
# set :format_options, command_output: true, log_file: "log/capistrano.log", color: :auto, truncate: :auto
|
22
19
|
|
23
20
|
# Default value for :pty is false
|
24
21
|
# set :pty, true
|
25
22
|
|
26
23
|
# Default value for :linked_files is []
|
27
|
-
# append :linked_files,
|
24
|
+
# append :linked_files, "config/database.yml", "config/secrets.yml"
|
28
25
|
|
29
26
|
# Default value for linked_dirs is []
|
30
|
-
# append :linked_dirs,
|
27
|
+
# append :linked_dirs, "log", "tmp/pids", "tmp/cache", "tmp/sockets", "public/system"
|
31
28
|
|
32
29
|
# Default value for default_env is {}
|
33
30
|
# set :default_env, { path: "/opt/ruby/bin:$PATH" }
|