require 'fingercap/recipes' require 'fingercap/persistant_directory' Capistrano::Configuration.instance(:must_exist).load do def _instances if ENV['INSTANCE'] [ENV['INSTANCE']] elsif ENV['INSTANCES'] ENV['INSTANCES'].split(' ') elsif variables[:instances_file] File.read(File.expand_path(variables[:instances_file], __FILE__)).split(/\s/).map { |i| i.strip } else puts "[!] Please set an :instances_file or pass the instances to operate on through INSTANCE or INSTANCES." exit -1 end end def install_from_secure(path, remote_file_name, options={}) sudo "scp #{remote_ssh_options} deploy@secure.callrecord.me:/home/deploy/#{path} #{remote_file_name}" end set :instances, _instances set :primary_instance, instances.first default_run_options[:pty] = true set :runner, 'app' set :user, 'deploy' set :deploy_to, "/var/www/#{application}" set :domain, primary_instance role :app, *instances role :web, *instances role :db, primary_instance, :primary => true role :master, primary_instance set :remote_secure_key_file, '/home/deploy/.ssh/secure.key' set :remote_ssh_options, "-o 'StrictHostKeyChecking no' -i #{remote_secure_key_file}" if variables[:deploy_key_file] if File.exist?(deploy_key_file) ssh_options[:keys] = [deploy_key_file] else puts "[!] Can't read `#{deploy_key_file}', maybe certain volumes aren't mounted?" exit -1 end else puts "[!] Please set :ssh_key_file with a path to a valid SSH key for the deploy user." end namespace :key do desc "Push the secure SSH key to the instance" task :push do remote_secure_key_dir = File.dirname(remote_secure_key_file) sudo "mkdir -p #{remote_secure_key_dir}" sudo "chown -R deploy:deploy #{remote_secure_key_dir}" sudo "rm -f #{remote_secure_key_file}" upload(secure_key_file, remote_secure_key_file) sudo "chmod 400 #{remote_secure_key_file}" end desc "Remove the secure SSH key from the instance" task :remove do sudo "rm -f #{remote_secure_key_file}" end end namespace :configure do desc "Set permissions on the application install directories" task :set_permissions do try_sudo "chown -R #{user}:wheel #{deploy_to}" try_sudo "chown -R #{fetch(:runner, "app")}:wheel #{shared_path}" end desc "Create persistant directories" task :create_persistant_directories do raise "Overwrite this task for the specific application" end desc "Symlink persistant directories" task :symlink_persistant_directories do raise "Overwrite this task for the specific application" end desc "Copy credentials from the secure instance to the shared directory" task :install_credentials do end desc "Copy server certificates from the secure instance to /etc" task :install_certificates do # TODO: permissions install_from_secure 'etc/ssl/private/callrecord.pem', '/etc/ssl/private/callrecord.pem' install_from_secure 'etc/ssl/certs/robin.crt', '/etc/ssl/certs/robin.crt' end desc "Install all gems needed by the application" task :install_gems do sudo "gem install libxml-ruby --no-rdoc --no-ri" run "if [ -f #{current_path}/Rakefile ]; then cd #{current_path}; sudo rake gems:install RAILS_ENV=production; fi" end desc "Setup additional networking" task :networking do end end namespace :monit do desc "Restart services" task :restart do sudo "/usr/sbin/monit -c /etc/monitrc restart all" end end namespace :sphinx do desc "Stop Sphinx" task :stop, :roles => :master do config_file = "#{current_path}/config/production.sphinx.conf" sudo "touch #{config_file}" sudo "chown app:app #{config_file}" sudo "chown app:app #{current_path}/log" run "if [ -f #{current_path}/Rakefile ]; then cd #{current_path}; sudo -u app rake thinking_sphinx:stop RAILS_ENV=production; fi" end desc "Perform additional configuration for the search daemon" task :configure, :roles => :master do config_file = "#{current_path}/config/environments/production.rb" new_config_file = "#{current_path}/config/environments/production.rb.tmp" run "cat #{config_file} | sed 's/ThinkingSphinx\..*//' > #{new_config_file}" run "mv #{new_config_file} #{config_file}" config_file = "#{current_path}/config/sphinx.yml" new_config_file = "#{current_path}/config/sphinx.yml.tmp" run "cat #{config_file} | sed 's/address:.*/address: 0.0.0.0/' > #{new_config_file}" run "mv #{new_config_file} #{config_file}" end desc "Start the search daemon" task :start, :roles => :master do config_file = "#{current_path}/config/production.sphinx.conf" sudo "touch #{config_file}" sudo "chown app:app #{config_file}" sudo "chown app:app #{current_path}/log" run "if [ -f #{current_path}/Rakefile ]; then cd #{current_path}; sudo -u app rake thinking_sphinx:configure RAILS_ENV=production; fi" run "if [ -f #{current_path}/Rakefile ]; then cd #{current_path}; sudo -u app rake thinking_sphinx:start RAILS_ENV=production; fi" end end namespace :tunnel do PID_FILE = '/var/run/ssh-tunnel.pid' START_STOP_DAEMON = '/sbin/start-stop-daemon' SSH = '/usr/bin/ssh' desc "Setup SSH tunnels to the secure instance" task :setup do args = "#{remote_ssh_options} -L 35553:localhost:35553 deploy@depot.callrecord.me -N" sudo "#{START_STOP_DAEMON} --make-pidfile --pidfile #{PID_FILE} --exec #{SSH} --background --start -- #{args} " end desc "Tear SSH tunnels to the secure instance down" task :teardown do sudo "echo" run "if [ -f #{PID_FILE} ]; then sudo #{START_STOP_DAEMON} --pidfile #{PID_FILE} --stop; fi" end desc "Stop and start the tunnel" task :restart do tunnel.teardown tunnel.setup end desc "Clean out the pidfile left by a crashed SSH tunnel" task :cleanup do sudo "rm -f #{PID_FILE}" end end namespace :deploy do desc "Stop the application (empty operation)" task :stop do end desc "Start the application" task :start do apache.restart end desc "Restart the application" task :restart do passenger.restart end desc "Configure the instance for this application and install it" task :install do setup configure.set_permissions check configure.create_persistant_directories key.push configure.install_credentials configure.install_certificates configure.networking key.remove update configure.install_gems end desc "Set the server into maintenance mode" task :start_maintenance do sudo "a2enmod rewrite" sudo "a2dissite storage mobile device" sudo "a2ensite maintenance" sudo "/etc/init.d/apache2 reload" end desc "Take the server out of maintenance mode" task :stop_maintenance do sudo "a2dismod rewrite" sudo "a2dissite maintenance" sudo "a2ensite storage mobile device" sudo "/etc/init.d/apache2 reload" end end after 'deploy:symlink', 'configure:symlink_persistant_directories' if variables[:prepare_tasks] before "deploy", *prepare_tasks before "deploy:migrations", *prepare_tasks end if variables[:finalize_tasks] after "deploy", *finalize_tasks after "deploy:migrations", *finalize_tasks end end