Class: Chef::Provisioning::AzureDriver::Driver
- Inherits:
-
Driver
- Object
- Driver
- Chef::Provisioning::AzureDriver::Driver
- Defined in:
- lib/chef/provisioning/azure_driver/driver.rb
Overview
Provisions machines using the Azure SDK
Instance Attribute Summary collapse
-
#region ⇒ Object
readonly
Returns the value of attribute region.
-
#subscription ⇒ Object
readonly
Returns the value of attribute subscription.
Class Method Summary collapse
- .canonicalize_url(driver_url, config) ⇒ Object
-
.from_url(driver_url, config) ⇒ AzureDriver
Construct an AzureDriver object from a URL - used to parse existing URL data to hydrate a driver object.
Instance Method Summary collapse
-
#allocate_machine(action_handler, machine_spec, machine_options) ⇒ Object
Allocate a new machine with the Azure API and start it up, without blocking to wait for it.
- #destroy_machine(action_handler, machine_spec, machine_options) ⇒ Object
-
#initialize(driver_url, config) ⇒ Driver
constructor
A new instance of Driver.
- #ready_machine(action_handler, machine_spec, machine_options) ⇒ Object
Constructor Details
#initialize(driver_url, config) ⇒ Driver
Returns a new instance of Driver.
51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 51 def initialize(driver_url, config) super scheme, subscription_id = driver_url.split(':', 2) @subscription = Subscriptions.get_subscription(config, subscription_id) if !subscription raise "Driver #{driver_url} has a subscription ID, but the system has no credentials configured for it! If you have access to this subscription, you can use `azure account download` and `azure account import` in the Azure CLI to get the credentials, or set azure_subscriptions to [ { subscription_id: '...', management_credentials: ... }] in your Chef configuration." end # TODO make this instantiable so we can have multiple drivers ...... Azure.configure do |azure| # Configure these 3 properties to use Storage azure.management_certificate = subscription[:management_certificate] azure.subscription_id = subscription[:subscription_id] azure.management_endpoint = subscription[:management_endpoint] end end |
Instance Attribute Details
#region ⇒ Object (readonly)
Returns the value of attribute region.
24 25 26 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 24 def region @region end |
#subscription ⇒ Object (readonly)
Returns the value of attribute subscription.
68 69 70 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 68 def subscription @subscription end |
Class Method Details
.canonicalize_url(driver_url, config) ⇒ Object
35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 35 def self.canonicalize_url(driver_url, config) scheme, account_id = driver_url.split(':', 2) if account_id.nil? || account_id.empty? subscription = Subscriptions.default_subscription(config) if !subscription raise "Driver #{driver_url} did not specify a subscription ID, and no default subscription was found. Have you downloaded the Azure CLI and used `azure account download` and `azure account import` to set up Azure? Alternately, you can set azure_subscriptions to [ { subscription_id: '...', management_credentials: ... }] in your Chef configuration." end config = Cheffish::MergedConfig.new({ azure_subscriptions: subscription }, config) end if subscription [ "#{scheme}:#{subscription[:subscription_id]}", config ] else [ driver_url, config] end end |
.from_url(driver_url, config) ⇒ AzureDriver
Construct an AzureDriver object from a URL - used to parse existing URL data to hydrate a driver object. URL scheme: azure:subscription_id
31 32 33 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 31 def self.from_url(driver_url, config) Driver.new(driver_url, config) end |
Instance Method Details
#allocate_machine(action_handler, machine_spec, machine_options) ⇒ Object
Allocate a new machine with the Azure API and start it up, without blocking to wait for it. Creates any needed resources to get a machine up and running.
76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 76 def allocate_machine(action_handler, machine_spec, ) existing_vm = vm_for(machine_spec) # We don't need to do anything if the existing VM is found return if existing_vm = [:bootstrap_options] || {} [:vm_size] ||= 'Small' [:cloud_service_name] ||= 'chefprovisioning' [:storage_account_name] ||= 'chefprovisioning' [:location] ||= 'West US' location = [:location] machine_spec.location = { 'driver_url' => driver_url, 'driver_version' => Chef::Provisioning::AzureDriver::VERSION, 'allocated_at' => Time.now.utc.to_s, 'host_node' => action_handler.host_node, 'image_id' => [:image_id], 'location' => location, 'cloud_service' => [:cloud_service_name] } image_id = [:image_id] || default_image_for_location(location) Chef::Log.debug "Azure bootstrap options: #{.inspect}" params = { vm_name: machine_spec.name, vm_user: [:vm_user] || default_ssh_username, image: image_id, # This is only until SSH keys are added password: [:password], location: location, cloud_service_name: [:cloud_service_name] } # If the cloud service exists already, need to add a role to it - otherwise create virtual machine (including cloud service) cloud_service = azure_cloud_service_service.get_cloud_service([:cloud_service_name]) existing_deployment = azure_vm_service.list_virtual_machines([:cloud_service_name]).any? if cloud_service and existing_deployment action_handler.report_progress "Cloud Service #{[:cloud_service_name]} already exists, adding role." action_handler.report_progress "Creating #{machine_spec.name} with image #{image_id} in #{[:cloud_service_name]}..." vm = azure_vm_service.add_role(params, ) else action_handler.report_progress "Creating #{machine_spec.name} with image #{image_id} in #{location}..." vm = azure_vm_service.create_virtual_machine(params, ) end machine_spec.location['vm_name'] = vm.vm_name machine_spec.location['is_windows'] = (true if vm.os_type == 'Windows') || false action_handler.report_progress "Created #{vm.vm_name} in #{location}..." end |
#destroy_machine(action_handler, machine_spec, machine_options) ⇒ Object
154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 154 def destroy_machine(action_handler, machine_spec, ) vm = vm_for(machine_spec) vm_name = machine_spec.name cloud_service = machine_spec.location['cloud_service'] # Check if we need to proceed return if vm.nil? || vm_name.nil? || cloud_service.nil? # Skip if we don't actually need to do anything return unless action_handler.should_perform_actions # TODO: action_handler.do |block| ? action_handler.report_progress "Destroying VM #{machine_spec.name}!" azure_vm_service.delete_virtual_machine(vm_name, cloud_service) action_handler.report_progress "Destroyed VM #{machine_spec.name}!" end |
#ready_machine(action_handler, machine_spec, machine_options) ⇒ Object
133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 |
# File 'lib/chef/provisioning/azure_driver/driver.rb', line 133 def ready_machine(action_handler, machine_spec, ) vm = vm_for(machine_spec) location = machine_spec.location['location'] if vm.nil? fail "Machine #{machine_spec.name} does not have a VM associated with it, or the VM does not exist." end # TODO: Not sure if this is the right thing to check if vm.status != 'ReadyRole' action_handler.report_progress "Readying #{machine_spec.name} in #{location}..." wait_until_ready(action_handler, machine_spec) wait_for_transport(action_handler, machine_spec, ) else action_handler.report_progress "#{machine_spec.name} already ready in #{location}!" end machine_for(machine_spec, , vm) end |