EngineYard Continuous Deployment

Using Solano CI’s post-build hook, you can configure powerful continuous deployment to EngineYard, including running migrations or other tasks.

Post-Build Hook

For smooth continuous integration between your app, Solano CI and Engineyard, you’ll need to install a post-build hook that pushes into your EngineYard app and runs setup tasks as necessary.

We suggest a hook modeled on this example:

# Setup:
# 1. Take EY_API_TOKEN value from ~/.eyrc
#     Run: solano config:add suite EY_API_TOKEN xxxxxxxx
#
# 2. EY_DEPLOY_KEY value is content of authorized *private* SSH key
#      Can be: your ~/.ssh/id_rsa
#      OR: any other ssh key authorised for a given EY env
#      OR: authorize default Solano CI deploy public key in EY
#          For Solano CI default deploy public key:
#            Run: 'solano account'
#    Run: solano config:add suite EY_DEPLOY_KEY yyyyyyy
#
# 3. By default, deploys only from tracked_branch, as defined below
#
# 4. Add post_build_hook to solano.yml

require 'etc'
require 'timeout'

ENV['CI_DEPLOYMENT_ENV'] ||= 'development'
ENV['CI_DEPLOYMENT_BRANCH'] ||= 'master'

def current_branch
  `git symbolic-ref HEAD 2>/dev/null | cut -d"/" -f 3-`.strip
end

namespace :tddium do
  desc "Run post-build script"
  task :post_build_hook do
    # Print out status information
    puts "Solano CI? " + ENV.member?('TDDIUM').to_s
    puts "status " + ENV['TDDIUM_BUILD_STATUS']
    puts "on_tracked_branch? " + on_tracked_branch?.inspect
    puts "deploy? " + deploy?.inspect

    if deploy?
      Rake::Task["deploy:dev"].execute
    end
  end

  private

  def deploy?
    result = ENV.member?('TDDIUM')
    result &&= ENV['TDDIUM_BUILD_STATUS'] == 'passed'
    result &&= on_tracked_branch?
  end

  def on_tracked_branch?
    current_branch == ENV['CI_DEPLOYMENT_BRANCH']
  end
end

namespace :deploy do
  desc "Deploy master branch to dev server"
  task :dev do
    Timeout::timeout(600) do
      deploy
    end
  end

  def deploy
    home_dir = Etc.getpwuid.dir

    if ENV['TDDIUM'].present? then
      puts "We're on Solano CI: writing deployment key"
      FileUtils.mkdir_p("#{home_dir}/.ssh")
      File.open("#{home_dir}/.ssh/id_rsa.deploy", "w") do |f|
        f.write(ENV['EY_DEPLOY_KEY'])
        f.chmod(0600)
      end
      system "ssh-add #{home_dir}/.ssh/id_rsa.deploy"
    end

    puts "Writing .eyrc key"
    content = "---\napi_token: #{ENV['EY_API_TOKEN']}"
    File.open("#{home_dir}/.eyrc", "w") do |f|
      f.write(content)
      f.chmod(0600)
    end

    system "ey deploy -m -e #{ENV['CI_DEPLOYMENT_ENV']} -r #{current_branch}"
  end
end

Note

Solano CI modifies or adds certain files to ruby/rails repos to better collect results from our parallel test runners (typically config/boot.rb and various config/*.yml files). Before deploying your code, you may want to revert these changes with a command like git reset --hard $TDDIUM_CURRENT_COMMIT in a post_build setup hook.

We’re actively working on improving our EngineYard integration, and we welcome your feedback.