开发者

Capistrano recipe to automatically run deploy:cleanup only when needed

We do over 20 deployments a day using capistrano (actually webistrano) and we have a problem where the disk space on our servers get full of old deployment folders.

Every now and again I run the deploy:cleanup task to clean out all deployments (it keeps the last :keep_releases, currently set to 30). I would like to automate the cleanup.

One solution would be to add the following to the recipe to automatically run the cleanup after every deployment:

after "deploy", "deploy:cleanup"

But, I don't want to do this after every deployment, I'd like to limit it to only when the number of previous deployments gets to a threash开发者_StackOverflow中文版old, e.g. 70. Does anyone know how I can do this?


Thoughts:

  • Does Capistrano provide a variable that holds the number of previous deployments?
    • If not, does anyone know a way to calculate it. i.e. set :num_releases, <what-can-I-put-here-to-count-previous-deployments>
  • Is there a way to pimp deploy:cleanup so it uses a minimum threshold, i.e. exit if < :max_releases previous deployments (where :max_releases is different from :keep_releases).
  • Could the except keyword be used? i.e. something like :except => { :num_releases < 70}.


Does Capistrano provide a variable that holds the number of previous deployments?

Yes, releases.length

Is there a way to pimp deploy:cleanup so it uses a minimum threshold?

Yes, here is a privately namespaced task that will trigger the normal cleanup task ONLY if a certain number of release folders have built up:

namespace :mystuff do
  task :mycleanup, :except => { :no_release => true } do
    thresh = fetch(:cleanup_threshold, 70).to_i
    if releases.length > thresh
      logger.info "Threshold of #{thresh} releases reached, runing deploy:cleanup."
      deploy.cleanup
    end
  end
end

To have this run automatically after a deploy, put this at the top of the recipe:

after "deploy", "mystuff:mycleanup"

The good thing about this is that, before and after directives set on deploy:cleanup are executed as normal. For example we require the following:

before 'deploy:cleanup', 'mystuff:prepare_cleanup_permissions'
after 'deploy:cleanup', 'mystuff:restore_cleanup_permissions'


A quick and dirty approach using the current capistrano code:

Change the cleanup task in https://github.com/capistrano/capistrano/blob/master/lib/capistrano/recipes/deploy.rb#L405 into this:

  task :cleanup, :except => { :no_release => true } do
    thresh = fetch(:cleanup_threshold, 70).to_i
    count = fetch(:keep_releases, 5).to_i
    if thresh >= releases.length
      logger.important "no old releases to clean up"
    else
      logger.info "threshold of #{thresh} releases reached, keeping #{count} of #{releases.length} deployed releases"

      directories = (releases - releases.last(count)).map { |release|
        File.join(releases_path, release) }.join(" ")

      try_sudo "rm -rf #{directories}"
    end
  end

and then you will be able to add

set :cleanup_threshold, 70

to your deployment recipe.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜