class OpsworksWrapper::Deployer

Public Class Methods

new(app_id) click to toggle source
# File lib/opsworks_wrapper.rb, line 6
def initialize(app_id)
  @app_id = app_id
end

Public Instance Methods

_wait_until_deployed(deployment_id, timeout) click to toggle source

Waits on the provided deployment for specified timeout (seconds)

# File lib/opsworks_wrapper.rb, line 206
def _wait_until_deployed(deployment_id, timeout)
  opsworks_client.wait_until(:deployment_successful, deployment_ids: [deployment_id]) do |w|
    w.before_attempt do |attempt|
      puts "Attempt #{attempt} to check deployment status".light_black
    end
    w.interval = 10
    w.max_attempts = timeout / w.interval
  end
end
app_id() click to toggle source
# File lib/opsworks_wrapper.rb, line 26
def app_id
  @app_id
end
create_deployment(command, instances, timeout) click to toggle source

Creates an OpsWorks deployment with specified command If @instances is not nil, the deployment will only be performed on specified instances @param [Object] command @param [Array] instances @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 173
def create_deployment(command, instances, timeout)
  instance_ids = nil
  instance_description = "all instances"

  if !instances.nil?
    instance_ids = instances.map(&:instance_id)
    instance_description = instances.map(&:hostname).join(',')
  end

  deployment_config = {
      stack_id: opsworks_app[:stack_id],
      app_id: app_id,
      instance_ids: instance_ids,
      command: command,
      comment: "Git Sha: #{current_sha}"
  }

  deployment = opsworks_client.create_deployment(deployment_config)
  print "Running command ".light_blue
  print "#{command[:name]}".light_blue.bold
  puts " on #{instance_description}".light_blue

  begin
    _wait_until_deployed(deployment[:deployment_id], timeout)
    puts "Deployment successful".green
    true
  rescue Aws::Waiters::Errors::WaiterFailed => e
    puts  "Failed to deploy: #{e.message}".red
    false
  end
end
create_deployment_exclude(command, layer_to_exclude, timeout) click to toggle source

Creates an OpsWorks deployment with specified command on all layers excluding layer_to_exclude @param [Object] command - Opsworks deployment command @param [String] layer_to_exclude @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 159
def create_deployment_exclude(command, layer_to_exclude, timeout)
  all_instances = get_instances
  excluded_instances = get_instances(layer_to_exclude)
  included_instances = all_instances - excluded_instances

  create_deployment(command, included_instances, timeout)
end
current_sha() click to toggle source
# File lib/opsworks_wrapper.rb, line 10
def current_sha
  @current_sha ||= `git rev-parse HEAD`.chomp
end
deploy(layer_name = nil, timeout = 600) click to toggle source

Run deploy command on specified layer or all layers if @layer_name is not specified (non rolling) @param [String] layer_name @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 96
def deploy(layer_name = nil, timeout = 600)
  if layer_name
    puts "Deploying on #{layer_name} layer".light_white.bold
    instances = get_instances(layer_name)
  else
    puts "Deploying on all layers".light_white.bold
    instances = nil
  end

  create_deployment({name: 'deploy'}, instances, timeout)
end
deploy_exclude(layer_name, timeout = 600) click to toggle source

Deploy to all layers except specified layer (non-rolling) @param [String] layer_name @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 149
def deploy_exclude(layer_name, timeout = 600)
  puts "Deploying to all layers except #{layer_name}".light_white.bold
  create_deployment_exclude({name: 'deploy'}, layer_name, timeout)
end
deploy_instance_rolling(instance, elb, timeout = 600) click to toggle source

Performs rolling deployment on an instance Will detach instance if elb is provided and re-attach after deployment succeeds @param [Object] instance - opsworks instance @param [Object] elb - elb instance @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 130
def deploy_instance_rolling(instance, elb, timeout = 600)
  if !elb.nil?
    elb.remove_instance(instance)
  end

  success = create_deployment({name: 'deploy'}, [instance], timeout)

  # only add instance back to elb if deployment succeeded
  if !elb.nil? && success
    success = elb.add_instance(instance)
  end

  success
end
deploy_layer_rolling(layer_name, timeout = 600) click to toggle source

Performs a rolling deploy on each instance in the layer If an elb is attached to the layer, de-registration and registration will be performed for the instance @param [String] layer_name @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 113
def deploy_layer_rolling(layer_name, timeout = 600)
  instances = get_instances(layer_name)
  elb = get_elb(layer_name)
  success = true
  instances.each do |instance|
    success = deploy_instance_rolling(instance, elb, timeout)
    break if !success
  end
  success
end
get_elb(layer_name) click to toggle source

Returns ELB instance for layer if one is attached @param [String] layer_name @return [Object?] - ELB instance

# File lib/opsworks_wrapper.rb, line 73
def get_elb(layer_name)
  layer_id = layers[layer_name].layer_id
  elbs = opsworks_client.describe_elastic_load_balancers(layer_ids:[layer_id])
  if elbs.elastic_load_balancers.size > 0
    name = elbs.elastic_load_balancers.first.elastic_load_balancer_name
    ELB.new(name)
  else
    nil
  end
end
get_instances(layer_name = nil) click to toggle source

Returns a list of OpsWorks instances for a specific layer or all layers if @layer_name is not provided @param [String] layer_name @return [List] - List of OpsWorks instances

# File lib/opsworks_wrapper.rb, line 59
def get_instances(layer_name = nil)
  if layer_name == nil
    data = opsworks_client.describe_instances(stack_id: opsworks_app[:stack_id])
  else
    layer_id = layers[layer_name].layer_id
    data = opsworks_client.describe_instances(layer_id: layer_id)
  end

  data.instances
end
get_opsworks_app() click to toggle source

Returns OpsWorks app details @return [Object]

# File lib/opsworks_wrapper.rb, line 47
def get_opsworks_app
  data = opsworks_client.describe_apps(app_ids: [app_id])
  if !(data[:apps] && data[:apps].count == 1)
    raise Error, "App #{app_id} not found.", error.backtrace
  end
  data[:apps].first
end
get_opsworks_layers() click to toggle source

Returns a dictionary for all OpsWorks layers keyed by layer name @return [Dictionary]

# File lib/opsworks_wrapper.rb, line 36
def get_opsworks_layers
  data = opsworks_client.describe_layers(stack_id: opsworks_app[:stack_id])
  layers = {}
  data.layers.each do |layer|
    layers[layer.name] = layer
  end
  layers
end
layers() click to toggle source
# File lib/opsworks_wrapper.rb, line 30
def layers
  @layers ||= get_opsworks_layers
end
load_balancer_client() click to toggle source
# File lib/opsworks_wrapper.rb, line 22
def load_balancer_client
  @client ||= Aws::ElasticLoadBalancing::Client.new
end
opsworks_app() click to toggle source
# File lib/opsworks_wrapper.rb, line 14
def opsworks_app
  @opsworks_app ||= get_opsworks_app
end
opsworks_client() click to toggle source
# File lib/opsworks_wrapper.rb, line 18
def opsworks_client
  @opsworks_client ||= Aws::OpsWorks::Client.new
end
update_cookbooks(timeout = 150) click to toggle source

Run update cookbooks on all layers @param [Number] timeout @return [Boolean]

# File lib/opsworks_wrapper.rb, line 87
def update_cookbooks(timeout = 150)
  puts 'Updating cookbooks'.light_white.bold
  create_deployment({name: 'update_custom_cookbooks'}, nil, timeout)
end