mirror of
https://github.com/hashicorp/vagrant.git
synced 2026-02-13 15:54:02 -05:00
Remove customized require behaviors and modify the bin executable to check for missing tools that Vagrant expects to exist when running outside of an installer.
224 lines
6.7 KiB
Ruby
224 lines
6.7 KiB
Ruby
# Copyright (c) HashiCorp, Inc.
|
|
# SPDX-License-Identifier: BUSL-1.1
|
|
|
|
require "log4r"
|
|
require "securerandom"
|
|
|
|
require "vagrant/util/numeric"
|
|
|
|
module VagrantPlugins
|
|
module Kernel_V2
|
|
class VagrantConfigDisk < Vagrant.plugin("2", :config)
|
|
#-------------------------------------------------------------------
|
|
# Config class for a given Disk
|
|
#-------------------------------------------------------------------
|
|
|
|
DEFAULT_DISK_TYPES = [:disk, :dvd, :floppy].freeze
|
|
|
|
FILE_CHAR_REGEX = /[^-a-z0-9_]/i.freeze
|
|
|
|
# Note: This value is for internal use only
|
|
#
|
|
# @return [String]
|
|
attr_reader :id
|
|
|
|
# File name for the given disk. Defaults to a generated name that is:
|
|
#
|
|
# vagrant_<disk_type>_<short_uuid>
|
|
#
|
|
# @return [String]
|
|
attr_accessor :name
|
|
|
|
# Type of disk to create. Defaults to `:disk`
|
|
#
|
|
# @return [Symbol]
|
|
attr_accessor :type
|
|
|
|
# Type of disk extension to create. Defaults to `vdi`
|
|
#
|
|
# @return [String]
|
|
attr_accessor :disk_ext
|
|
|
|
# Size of disk to create
|
|
#
|
|
# @return [Integer,String]
|
|
attr_accessor :size
|
|
|
|
# Path to the location of the disk file (Optional for `:disk` type,
|
|
# required for `:dvd` type.)
|
|
#
|
|
# @return [String]
|
|
attr_accessor :file
|
|
|
|
# Determines if this disk is the _main_ disk, or an attachment.
|
|
# Defaults to true.
|
|
#
|
|
# @return [Boolean]
|
|
attr_accessor :primary
|
|
|
|
# Provider specific options
|
|
#
|
|
# @return [Hash]
|
|
attr_accessor :provider_config
|
|
|
|
def initialize(type)
|
|
@logger = Log4r::Logger.new("vagrant::config::vm::disk")
|
|
|
|
@type = type
|
|
@provider_config = {}
|
|
|
|
@name = UNSET_VALUE
|
|
@provider_type = UNSET_VALUE
|
|
@size = UNSET_VALUE
|
|
@primary = UNSET_VALUE
|
|
@file = UNSET_VALUE
|
|
@disk_ext = UNSET_VALUE
|
|
|
|
# Internal options
|
|
@id = SecureRandom.uuid
|
|
end
|
|
|
|
# Helper method for storing provider specific config options
|
|
#
|
|
# Expected format is:
|
|
#
|
|
# - `provider__diskoption: value`
|
|
# - `{provider: {diskoption: value, otherdiskoption: value, ...}`
|
|
#
|
|
# Duplicates will be overriden
|
|
#
|
|
# @param [Hash] options
|
|
def add_provider_config(**options, &block)
|
|
current = {}
|
|
options.each do |k,v|
|
|
opts = k.to_s.split("__")
|
|
|
|
if opts.size == 2
|
|
current[opts[0].to_sym] = {opts[1].to_sym => v}
|
|
elsif v.is_a?(Hash)
|
|
current[k] = v
|
|
else
|
|
@logger.warn("Disk option '#{k}' found that does not match expected provider disk config schema.")
|
|
end
|
|
end
|
|
|
|
current = @provider_config.merge(current) if !@provider_config.empty?
|
|
if current
|
|
@provider_config = current
|
|
else
|
|
@provider_config = {}
|
|
end
|
|
end
|
|
|
|
def finalize!
|
|
# Ensure all config options are set to nil or default value if untouched
|
|
# by user
|
|
@type = :disk if @type == UNSET_VALUE
|
|
@size = nil if @size == UNSET_VALUE
|
|
@file = nil if @file == UNSET_VALUE
|
|
|
|
if @primary == UNSET_VALUE
|
|
@primary = false
|
|
end
|
|
|
|
if @name.is_a?(String) && @name.match(FILE_CHAR_REGEX)
|
|
@logger.warn("Vagrant will remove detected invalid characters in '#{@name}' and convert the disk name into something usable for a file")
|
|
@name.gsub!(FILE_CHAR_REGEX, "_")
|
|
elsif @name == UNSET_VALUE
|
|
if @primary
|
|
@name = "vagrant_primary"
|
|
else
|
|
@name = nil
|
|
end
|
|
end
|
|
end
|
|
|
|
# @return [Array] array of strings of error messages from config option validation
|
|
def validate(machine)
|
|
errors = _detected_errors
|
|
# validate type with list of known disk types
|
|
|
|
if !DEFAULT_DISK_TYPES.include?(@type)
|
|
errors << I18n.t("vagrant.config.disk.invalid_type", type: @type,
|
|
types: DEFAULT_DISK_TYPES.join(', '))
|
|
end
|
|
|
|
if @disk_ext == UNSET_VALUE
|
|
if machine.provider.capability?(:set_default_disk_ext)
|
|
@disk_ext = machine.provider.capability(:set_default_disk_ext)
|
|
else
|
|
@logger.warn("No provider capability defined to set default 'disk_ext' type. Will use 'vdi' for disk extension.")
|
|
@disk_ext = "vdi"
|
|
end
|
|
elsif @disk_ext
|
|
@disk_ext = @disk_ext.downcase
|
|
|
|
if machine.provider.capability?(:validate_disk_ext)
|
|
if !machine.provider.capability(:validate_disk_ext, @disk_ext)
|
|
if machine.provider.capability?(:default_disk_exts)
|
|
disk_exts = machine.provider.capability(:default_disk_exts).join(', ')
|
|
else
|
|
disk_exts = "not found"
|
|
end
|
|
errors << I18n.t("vagrant.config.disk.invalid_ext", ext: @disk_ext,
|
|
name: @name,
|
|
exts: disk_exts)
|
|
end
|
|
else
|
|
@logger.warn("No provider capability defined to validate 'disk_ext' type")
|
|
end
|
|
end
|
|
|
|
if @size && !@size.is_a?(Integer)
|
|
if @size.is_a?(String)
|
|
@size = Vagrant::Util::Numeric.string_to_bytes(@size)
|
|
end
|
|
end
|
|
|
|
if !@size && type == :disk
|
|
errors << I18n.t("vagrant.config.disk.invalid_size", name: @name, machine: machine.name)
|
|
end
|
|
|
|
if @type == :dvd && !@file
|
|
errors << I18n.t("vagrant.config.disk.dvd_type_file_required", name: @name, machine: machine.name)
|
|
end
|
|
|
|
if @type == :dvd && @primary
|
|
errors << I18n.t("vagrant.config.disk.dvd_type_primary", name: @name, machine: machine.name)
|
|
end
|
|
|
|
if @file
|
|
if !@file.is_a?(String)
|
|
errors << I18n.t("vagrant.config.disk.invalid_file_type", file: @file, machine: machine.name)
|
|
elsif !File.file?(@file)
|
|
errors << I18n.t("vagrant.config.disk.missing_file", file_path: @file,
|
|
name: @name, machine: machine.name)
|
|
end
|
|
end
|
|
|
|
if @provider_config
|
|
if !@provider_config.empty?
|
|
if !@provider_config.key?(machine.provider_name)
|
|
machine.env.ui.warn(I18n.t("vagrant.config.disk.missing_provider",
|
|
machine: machine.name,
|
|
provider_name: machine.provider_name))
|
|
end
|
|
end
|
|
end
|
|
|
|
if !@name
|
|
errors << I18n.t("vagrant.config.disk.no_name_set", machine: machine.name)
|
|
end
|
|
|
|
errors
|
|
end
|
|
|
|
# The String representation of this Disk.
|
|
#
|
|
# @return [String]
|
|
def to_s
|
|
"disk config"
|
|
end
|
|
end
|
|
end
|
|
end
|