Nuclear Rooster

7Sep/070

Overriding Capistrano

Capistrano rocks for deployment, but I found myself wanting to override some spefic parts of the gem. I realize that I am a little late on the scene, as Capistrano 2.0 is out and about, but this solved some of my problems.

Specifically, I wanted to customize the SVN checkout to use sudo, have sudo default to specific user, and add a deployment message to the revisions log. This is all easy to do without editing the capistrano gem. I looked around the gem source and found the code that I wanted to override, and then pulled it out and tweaked it.

In deploy.rb

class ::Capistrano::SCM::Subversion
  alias_method :non_sudo_checkout, :checkout
  def checkout(actor)
    op = 'export'
    command = "sudo -u USER #{svn} #{op} -q --config-dir /home/USER/.subversion -r#{configuration.revision} #{configuration.repository} #{actor.release_path} &&"
   run_checkout(actor, command, &svn_stream_handler(actor))
  end
end

class ::Capistrano::Actor
  alias_method :sudo_with_optional_user, :sudo
  def sudo(command, options={}, &block)
    sudo_with_optional_user(command, {:as =>; 'SUDO_USER'}.merge(options), &block)
  end
end

class ::Capistrano::SCM::Base
  alias_method :logging_commands_without_message, :logging_commands
  def logging_commands(directory = nil)
    log = "#{configuration.deploy_to}/revisions.log"
    "(test -e #{log} || (touch #{log} && chmod 666 #{log})) && " +
    "echo `date +\"%Y-%m-%d %H:%M:%S\"` $USER #{configuration.revision} #{directory} '#{configuration.message}' >> #{log};"
  end
end