Class: HybridPlatformsConductor::HpcPlugins::Provisioner::Proxmox
- Inherits:
-
Provisioner
- Object
- Plugin
- Provisioner
- HybridPlatformsConductor::HpcPlugins::Provisioner::Proxmox
- Defined in:
- lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb
Overview
Provision Proxmox containers
Constant Summary collapse
- MAX_PROXMOX_HOSTNAME_SIZE =
Maximum size in chars of hostnames set in Proxmox
64
Constants included from LoggerHelpers
LoggerHelpers::LEVELS_MODIFIERS, LoggerHelpers::LEVELS_TO_STDERR
Class Attribute Summary collapse
-
.proxmox_waiter_files_mutex ⇒ Object
Returns the value of attribute proxmox_waiter_files_mutex.
Instance Method Summary collapse
-
#create ⇒ Object
Create an instance.
-
#default_timeout ⇒ Object
Return the default timeout to apply when waiting for an instance to be started/stopped…
-
#destroy ⇒ Object
Destroy an instance Prerequisite: create has been called before [API] - This method is mandatory.
-
#ip ⇒ Object
Return the IP address of an instance.
-
#start ⇒ Object
Start an instance Prerequisite: create has been called before [API] - This method is mandatory.
-
#state ⇒ Object
Return the state of an instance [API] - This method is mandatory.
-
#stop ⇒ Object
Stop an instance Prerequisite: create has been called before [API] - This method is mandatory.
Methods inherited from Provisioner
#initialize, #wait_for_port, #wait_for_port!, #wait_for_state, #wait_for_state!, #with_running_instance
Methods included from LoggerHelpers
#err, #init_loggers, #log_component=, #log_debug?, #log_level=, #out, #section, #set_loggers_format, #stderr_device, #stderr_device=, #stderr_displayed?, #stdout_device, #stdout_device=, #stdout_displayed?, #stdouts_to_s, #with_progress_bar
Methods inherited from Plugin
extend_config_dsl_with, #initialize, valid?
Constructor Details
This class inherits a constructor from HybridPlatformsConductor::Provisioner
Class Attribute Details
.proxmox_waiter_files_mutex ⇒ Object
Returns the value of attribute proxmox_waiter_files_mutex.
71 72 73 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 71 def proxmox_waiter_files_mutex @proxmox_waiter_files_mutex end |
Instance Method Details
#create ⇒ Object
Create an instance. Reuse an existing one if it already exists.
- API
-
This method is mandatory
-
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 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 81 def create # First check if we already have a test container that corresponds to this node and environment @lxc_details = nil with_proxmox do |proxmox| proxmox_get(proxmox, 'nodes').each do |node_info| if proxmox_test_info[:test_config][:pve_nodes].include?(node_info['node']) && node_info['status'] == 'online' proxmox_get(proxmox, "nodes/#{node_info['node']}/lxc").each do |lxc_info| vm_id = Integer(lxc_info['vmid']) if vm_id.between?(*proxmox_test_info[:test_config][:vm_ids_range]) # Check if the description contains our ID lxc_config = proxmox_get(proxmox, "nodes/#{node_info['node']}/lxc/#{vm_id}/config") vm_description_lines = (lxc_config['description'] || '').split("\n") hpc_marker_idx = vm_description_lines.index('===== HPC info =====') unless hpc_marker_idx.nil? # Get the HPC info associated to this VM # Hash<Symbol,String> vm_hpc_info = Hash[vm_description_lines[hpc_marker_idx + 1..-1].map do |line| property, value = line.split(': ') [property.to_sym, value] end] if vm_hpc_info[:node] == @node && vm_hpc_info[:environment] == @environment # Found it # Get back the IP ip_found = nil lxc_config['net0'].split(',').each do |net_info| property, value = net_info.split('=') if property == 'ip' ip_found = value.split('/').first break end end raise "[ #{@node}/#{@environment} ] - Unable to get IP back from LXC container nodes/#{node_info['node']}/lxc/#{vm_id}/config" if ip_found.nil? @lxc_details = { pve_node: node_info['node'], vm_id: vm_id, vm_ip: ip_found } break end end end end break if @lxc_details end end end unless @lxc_details # We couldn't find an existing LXC container for this node/environment. # We have to create one. # Get the image name for this node image = @nodes_handler.get_image_of(@node).to_sym # Find if we have such an image registered if @config.known_os_images.include?(image) proxmox_conf = "#{@config.os_image_dir(image)}/proxmox.json" if File.exist?(proxmox_conf) pve_template = JSON.parse(File.read(proxmox_conf)).dig 'template' if pve_template # Query the inventory to know about minimum resources needed to deploy the node. # Provide default values if they are not part of the metadata. min_resources_to_deploy = { cpus: 2, ram_mb: 1024, disk_gb: 10 }.merge(@nodes_handler.get_deploy_resources_min_of(@node) || {}) # Create the Proxmox container from the sync node. vm_config = proxmox_test_info[:vm_config] # Hostname in Proxmox is capped at 65 chars. # Make sure we don't get over it, but still use a unique one. hostname = "#{@node}.#{@environment}.hpc-test.com" if hostname.size > MAX_PROXMOX_HOSTNAME_SIZE # Truncate it, but add a unique ID in it. # In the end the hostname looks like: # <truncated_node_environment>.<unique_id>.hpc-test.com hostname = "-#{Digest::MD5.hexdigest(hostname)[0..7]}.hpc-test.com" hostname = "#{@node}.#{@environment}"[0..MAX_PROXMOX_HOSTNAME_SIZE - hostname.size - 1] + hostname end @lxc_details = request_lxc_creation_for({ ostemplate: pve_template, hostname: hostname.gsub('_', '-'), cores: min_resources_to_deploy[:cpus], cpulimit: min_resources_to_deploy[:cpus], memory: min_resources_to_deploy[:ram_mb], rootfs: "local-lvm:#{min_resources_to_deploy[:disk_gb]}", nameserver: vm_config[:vm_dns_servers].join(' '), searchdomain: vm_config[:vm_search_domain], net0: "name=eth0,bridge=vmbr0,gw=#{vm_config[:vm_gateway]}", password: 'root_pwd', description: <<~EOS ===== HPC info ===== node: #{@node} environment: #{@environment} debug: #{log_debug? ? 'true' : 'false'} EOS }) else raise "[ #{@node}/#{@environment} ] - No template found in #{proxmox_conf}" end else raise "[ #{@node}/#{@environment} ] - No Proxmox configuration found at #{proxmox_conf}" end else raise "[ #{@node}/#{@environment} ] - Unknown OS image #{image} defined for node #{@node}" end end end |
#default_timeout ⇒ Object
Return the default timeout to apply when waiting for an instance to be started/stopped…
- API
-
This method is optional
-
- Result
-
Integer: The timeout in seconds
262 263 264 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 262 def default_timeout proxmox_test_info[:default_timeout] || 3600 end |
#destroy ⇒ Object
Destroy an instance Prerequisite: create has been called before
- API
-
This method is mandatory
-
210 211 212 213 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 210 def destroy log_debug "[ #{@node}/#{@environment} ] - Delete Proxmox LXC Container ..." release_lxc_container(@lxc_details[:vm_id]) end |
#ip ⇒ Object
Return the IP address of an instance. Prerequisite: create has been called before.
- API
-
This method is optional
-
- Result
-
String or nil: The instance IP address, or nil if this information is not relevant
253 254 255 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 253 def ip @lxc_details[:vm_ip] end |
#start ⇒ Object
Start an instance Prerequisite: create has been called before
- API
-
This method is mandatory
-
190 191 192 193 194 195 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 190 def start log_debug "[ #{@node}/#{@environment} ] - Start Proxmox LXC Container ..." with_proxmox do |proxmox| run_proxmox_task(proxmox, :post, @lxc_details[:pve_node], "lxc/#{@lxc_details[:vm_id]}/status/start") end end |
#state ⇒ Object
Return the state of an instance
- API
-
This method is mandatory
-
- Result
-
Symbol: The state the instance is in. Possible values are:
-
:missing: The instance does not exist
-
:created: The instance has been created but is not running
-
:running: The instance is running
-
:exited: The instance has run and is now stopped
-
:error: The instance is in error
-
225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 225 def state if @lxc_details.nil? :missing else status = nil with_proxmox do |proxmox| vm_id_str = @lxc_details[:vm_id].to_s status = if proxmox_get(proxmox, "nodes/#{@lxc_details[:pve_node]}/lxc").any? { |data_info| data_info['vmid'] == vm_id_str } status_info = proxmox_get(proxmox, "nodes/#{@lxc_details[:pve_node]}/lxc/#{@lxc_details[:vm_id]}/status/current") # Careful that it is possible that somebody destroyed the VM and so its status is missing status = status_info.key?('status') ? status_info['status'].to_sym : :missing status = :exited if status == :stopped status else :missing end end status end end |
#stop ⇒ Object
Stop an instance Prerequisite: create has been called before
- API
-
This method is mandatory
-
200 201 202 203 204 205 |
# File 'lib/hybrid_platforms_conductor/hpc_plugins/provisioner/proxmox.rb', line 200 def stop log_debug "[ #{@node}/#{@environment} ] - Stop Proxmox LXC Container ..." with_proxmox do |proxmox| run_proxmox_task(proxmox, :post, @lxc_details[:pve_node], "lxc/#{@lxc_details[:vm_id]}/status/stop") end end |