lib/bosh/cli/commands/02_create_cf.rb
$:.unshift(File.expand_path("../../../..", __FILE__))
require "yaml"
require "bosh/cloudfoundry"
module Bosh::Cli::Command
class CloudFoundry < Base
include FileUtils
include Bosh::Cli::Validation
include Bosh::Cloudfoundry
usage "create cf"
desc "create a deployment file for Cloud Foundry and deploy it"
option "--dns mycloud.com", "Primary domain"
option "--ip 1.2.3.4,1.2.3.5", Array, "Public IPs; one per router node"
option "--name cf-<timestamp>", "Unique bosh deployment name"
option "--disk 4096", Integer, "Size of persistent disk (Mb)"
option "--security-group default", String, "Security group to assign to provisioned VMs"
option "--deployment-size medium", String, "Size of deployment - medium or large"
option "--skip-dns-validation", "Skip DNS validation"
def create_cf
auth_required
bosh_status # preload
setup_deployment_attributes
ip_addresses = options[:ip]
err("USAGE: bosh create cf --ip 1.2.3.4 -- please provide one IP address that will be bound to router.") if ip_addresses.blank?
err("Only one IP address is supported currently. Please create an issue to mention you need more.") if ip_addresses.size > 1
attrs.set(:ip_addresses, ip_addresses)
attrs.set_unless_nil(:name, options[:name])
attrs.set_unless_nil(:dns, options[:dns])
attrs.set_unless_nil(:persistent_disk, options[:disk])
attrs.set_unless_nil(:security_group, options[:security_group])
attrs.set_unless_nil(:common_password, options[:common_password])
attrs.set_unless_nil(:deployment_size, options[:deployment_size])
attrs.set_unless_nil(:skip_dns_validation, options[:skip_dns_validation])
release_version = ReleaseVersion.latest_version_number
@release_version_cpi_size =
ReleaseVersionCpiSize.new(@release_version_cpi, attrs.deployment_size)
nl
say "CPI: #{bosh_cpi.make_green}"
say "DNS mapping: #{attrs.validated_color(:dns)} --> #{attrs.validated_color(:ip_addresses)}"
say "Deployment name: #{attrs.validated_color(:name)}"
say "Deployment size: #{attrs.validated_color(:deployment_size)}"
say "Persistent disk: #{attrs.validated_color(:persistent_disk)}"
say "Security group: #{attrs.validated_color(:security_group)}"
nl
validate_deployment_attributes
unless confirmed?("Security group #{attrs.validated_color(:security_group)} exists with ports #{attrs.required_ports.join(", ")}")
cancel_deployment
end
unless confirmed?("Creating Cloud Foundry")
cancel_deployment
end
raise Bosh::Cli::ValidationHalted unless errors.empty?
@deployment_file = DeploymentFile.new(@release_version_cpi_size, attrs, bosh_status)
perform_deploy(options)
rescue Bosh::Cli::ValidationHalted
errors.each do |error|
say error.make_red
end
exit 1
end
usage "show cf attributes"
desc "display the deployment attributes, indicate which are changable"
def show_cf_attributes
setup_deployment_attributes
reconstruct_deployment_file
nl
say "Immutable attributes:"
attrs.immutable_attributes.each do |attr_name|
say "#{attr_name}: #{attrs.validated_color(attr_name.to_sym)}"
end
nl
say "Mutable (changable) attributes:"
attrs.mutable_attributes.each do |attr_name|
say "#{attr_name}: #{attrs.validated_color(attr_name.to_sym)}"
end
end
usage "change cf attributes"
desc "change deployment attributes and perform bosh deploy"
def change_cf_attributes(*attribute_values)
setup_deployment_attributes
reconstruct_deployment_file
# TODO fail if setting immutable attributes
attribute_values.each do |attr_value|
# FIXME check that correct format of input: xyz=123 and give feedback
attr_name, value = attr_value.split(/=/)
previous_value = attrs.validated_color(attr_name)
step("Checking '#{attr_name}' is a valid mutable attribute",
"Attribute '#{attr_name}' is not a valid mutable attribute (see 'bosh show cf attributes')", :non_fatal) do
attrs.mutable_attribute?(attr_name)
end
attrs.set_mutable(attr_name, value)
end
validate_deployment_attributes
# TODO show validated attributes like "create cf"
raise Bosh::Cli::ValidationHalted unless errors.empty?
perform_deploy(options)
rescue Bosh::Cli::ValidationHalted
errors.each do |error|
say error.make_red
end
exit 1
end
protected
def setup_deployment_attributes
@release_version_cpi = ReleaseVersionCpi.latest_for_cpi(bosh_cpi)
@deployment_attributes = DeploymentAttributes.new(director, bosh_status, @release_version_cpi)
end
def attrs
@deployment_attributes
end
# After a deployment is created, the input properties/attributes are stored within the generated
# deployment file. Therefore, to update a deployment, first we must load in the attributes.
def reconstruct_deployment_file
@deployment_file = DeploymentFile.reconstruct_from_deployment_file(deployment, director, bosh_status)
@deployment_attributes = @deployment_file.deployment_attributes
@release_version_cpi_size = @deployment_file.release_version_cpi_size
end
def perform_deploy(deploy_options={})
@deployment_file.perform(deploy_options)
end
def bosh_status
@bosh_status ||= begin
step("Fetching bosh information", "Cannot fetch bosh information", :fatal) do
@bosh_status = director.get_status
end
@bosh_status
end
end
def bosh_cpi
bosh_status["cpi"]
end
def validate_deployment_attributes
attrs.validate_deployment_size
attrs.validate_dns_mapping
end
end
end