1
0
Fork 0
mirror of https://github.com/capistrano/capistrano synced 2023-03-27 23:21:18 -04:00

deploy:cleanup should skip only the invalid releases and continue the rotation of releases (#1899)

* deploy:cleanup should skip only the invalid releases and continue the rotation
of releases

* Add cucumber tests for deploy:cleanup

* PR feedback

* rebase on master

* add ruby 2.4.1 to specs

* vagrant works with bundler 1.15.3

* remove unnecessary command
This commit is contained in:
Darwin D Wu 2017-07-22 16:15:44 -07:00 committed by Matt Brictson
parent e47b928857
commit a76b0766b0
9 changed files with 51 additions and 13 deletions

View file

@ -1,5 +1,6 @@
language: ruby language: ruby
rvm: rvm:
- 2.4.1
- 2.3.1 - 2.3.1
- 2.2 - 2.2
- 2.1 - 2.1

View file

@ -20,6 +20,8 @@ https://github.com/capistrano/capistrano/compare/v3.8.1...HEAD
* Your contribution here! * Your contribution here!
* Updated `deploy:cleanup` to continue rotating the releases and skip the invalid directory names instead of skipping the whole rotation of releases. The warning message has changed slightly due to the change of behavior.
## `3.8.2` (2017-06-16) ## `3.8.2` (2017-06-16)
https://github.com/capistrano/capistrano/compare/v3.8.1...v3.8.2 https://github.com/capistrano/capistrano/compare/v3.8.1...v3.8.2

View file

@ -28,11 +28,10 @@ Capistrano is a Ruby project, so we expect you to have a functioning Ruby enviro
Make sure to install: Make sure to install:
* [Bundler](https://bundler.io/) 1.10.5 (see note) * [Bundler](https://bundler.io/)
* [Vagrant](https://www.vagrantup.com/) * [Vagrant](https://www.vagrantup.com/)
* [VirtualBox](https://www.virtualbox.org/wiki/Downloads) (or another [Vagrant-supported](https://docs.vagrantup.com/v2/getting-started/providers.html) VM host) * [VirtualBox](https://www.virtualbox.org/wiki/Downloads) (or another [Vagrant-supported](https://docs.vagrantup.com/v2/getting-started/providers.html) VM host)
*Note: As of this writing (December 2015), Vagrant does not work with Bundler > 1.10.5. If you have multiple versions of Bundler installed, use the special underscore command-line argument to force a compatible version, like this: `bundle _1.10.5_ exec rake features`.*
### Running tests ### Running tests
@ -45,7 +44,7 @@ $ bundle install
# Run the RSpec suite # Run the RSpec suite
$ bundle exec rake spec $ bundle exec rake spec
# Run the Cucumber suite (requires Bundler 1.10.5) # Run the Cucumber suite
$ bundle exec rake features $ bundle exec rake features
# Run the Cucumber suite and leave the VM running (faster for subsequent runs) # Run the Cucumber suite and leave the VM running (faster for subsequent runs)

View file

@ -52,6 +52,14 @@ Feature: Deploy
When I run cap "deploy:symlink:release" When I run cap "deploy:symlink:release"
Then the current directory will be a symlink to the release Then the current directory will be a symlink to the release
Scenario: Cleanup
Given config stage file has line "set :keep_releases, 3"
And 5 valid existing releases
And an invalid release named "new"
When I run cap "deploy:cleanup"
Then 3 valid releases are kept
And the invalid "new" release is ignored
Scenario: Rolling Back Scenario: Rolling Back
Given I make 2 deployments Given I make 2 deployments
When I run cap "deploy:rollback" When I run cap "deploy:rollback"
@ -61,3 +69,4 @@ Feature: Deploy
Given I make 3 deployments Given I make 3 deployments
When I rollback to a specific release When I rollback to a specific release
Then the current symlink points to that specific release Then the current symlink points to that specific release

View file

@ -19,6 +19,18 @@ Then(/^the releases path is created$/) do
run_vagrant_command(test_dir_exists(TestApp.releases_path)) run_vagrant_command(test_dir_exists(TestApp.releases_path))
end end
Then(/^(\d+) valid releases are kept/) do |num|
test = %Q([ $(ls -g #{TestApp.releases_path} | grep -E '[0-9]{14}' | wc -l) == "#{num}" ])
_, _, status = vagrant_cli_command("ssh -c #{test.shellescape}")
expect(status).to be_success
end
Then(/^the invalid (.+) release is ignored$/) do |filename|
test = "ls -g #{TestApp.releases_path} | grep #{filename}"
_, _, status = vagrant_cli_command("ssh -c #{test.shellescape}")
expect(status).to be_success
end
Then(/^directories in :linked_dirs are created in shared$/) do Then(/^directories in :linked_dirs are created in shared$/) do
TestApp.linked_dirs.each do |dir| TestApp.linked_dirs.each do |dir|
run_vagrant_command(test_dir_exists(TestApp.shared_path.join(dir))) run_vagrant_command(test_dir_exists(TestApp.shared_path.join(dir)))

View file

@ -77,3 +77,16 @@ Given(/^I make (\d+) deployments$/) do |count|
stdout.strip stdout.strip
end end
end end
Given(/^(\d+) valid existing releases$/) do |num|
a_day = 86_400 # in seconds
offset = -(a_day * num.to_i)
num.to_i.times do
run_vagrant_command("mkdir -p #{TestApp.release_path(TestApp.timestamp(offset))}")
offset += a_day
end
end
Given(/^an invalid release named "(.+)"$/) do |filename|
run_vagrant_command("mkdir -p #{TestApp.release_path(filename)}")
end

View file

@ -13,7 +13,7 @@ en = {
question: "Please enter %{key}: ", question: "Please enter %{key}: ",
question_default: "Please enter %{key} (%{default_value}): ", question_default: "Please enter %{key} (%{default_value}): ",
keeping_releases: "Keeping %{keep_releases} of %{releases} deployed releases on %{host}", keeping_releases: "Keeping %{keep_releases} of %{releases} deployed releases on %{host}",
skip_cleanup: "Skipping cleanup of old releases on %{host}; unexpected foldername found (should be timestamp)", skip_cleanup: "Skipping cleanup of invalid releases on %{host}; unexpected foldername found (should be timestamp)",
no_old_releases: "No old releases (keeping newest %{keep_releases}) on %{host}", no_old_releases: "No old releases (keeping newest %{keep_releases}) on %{host}",
linked_file_does_not_exist: "linked file %{file} does not exist on %{host}", linked_file_does_not_exist: "linked file %{file} does not exist on %{host}",
cannot_rollback: "There are no older releases to rollback to", cannot_rollback: "There are no older releases to rollback to",

View file

@ -149,11 +149,13 @@ namespace :deploy do
task :cleanup do task :cleanup do
on release_roles :all do |host| on release_roles :all do |host|
releases = capture(:ls, "-x", releases_path).split releases = capture(:ls, "-x", releases_path).split
if !(releases.all? { |e| /^\d{14}$/ =~ e }) valid, invalid = releases.partition { |e| /^\d{14}$/ =~ e }
warn t(:skip_cleanup, host: host.to_s)
elsif releases.count >= fetch(:keep_releases) warn t(:skip_cleanup, host: host.to_s) if invalid.any?
info t(:keeping_releases, host: host.to_s, keep_releases: fetch(:keep_releases), releases: releases.count)
directories = (releases - releases.last(fetch(:keep_releases))) if valid.count >= fetch(:keep_releases)
info t(:keeping_releases, host: host.to_s, keep_releases: fetch(:keep_releases), releases: valid.count)
directories = (valid - valid.last(fetch(:keep_releases)))
if directories.any? if directories.any?
directories_str = directories.map do |release| directories_str = directories.map do |release|
releases_path.join(release) releases_path.join(release)

View file

@ -132,12 +132,12 @@ module TestApp
deploy_to.join("releases") deploy_to.join("releases")
end end
def release_path def release_path(t=timestamp)
releases_path.join(timestamp) releases_path.join(t)
end end
def timestamp def timestamp(offset=0)
Time.now.utc.strftime("%Y%m%d%H%M%S") (Time.now.utc + offset).strftime("%Y%m%d%H%M%S")
end end
def repo_path def repo_path