[MS] Adding support for VMSS Data Disks using Managed Disk feature (#14608)
* Added support for data disks with managed disks feature * Updated docs with VMSS Data Disks changes
This commit is contained in:
parent
399af7710d
commit
5884d518e7
|
@ -343,6 +343,47 @@ func resourceArmVirtualMachineScaleSet() *schema.Resource {
|
|||
Set: resourceArmVirtualMachineScaleSetStorageProfileOsDiskHash,
|
||||
},
|
||||
|
||||
"storage_profile_data_disk": {
|
||||
Type: schema.TypeList,
|
||||
Optional: true,
|
||||
Elem: &schema.Resource{
|
||||
Schema: map[string]*schema.Schema{
|
||||
"lun": {
|
||||
Type: schema.TypeInt,
|
||||
Required: true,
|
||||
},
|
||||
|
||||
"create_option": {
|
||||
Type: schema.TypeString,
|
||||
Required: true,
|
||||
},
|
||||
|
||||
"caching": {
|
||||
Type: schema.TypeString,
|
||||
Optional: true,
|
||||
Computed: true,
|
||||
},
|
||||
|
||||
"disk_size_gb": {
|
||||
Type: schema.TypeInt,
|
||||
Optional: true,
|
||||
Computed: true,
|
||||
ValidateFunc: validateDiskSizeGB,
|
||||
},
|
||||
|
||||
"managed_disk_type": {
|
||||
Type: schema.TypeString,
|
||||
Optional: true,
|
||||
Computed: true,
|
||||
ValidateFunc: validation.StringInSlice([]string{
|
||||
string(compute.PremiumLRS),
|
||||
string(compute.StandardLRS),
|
||||
}, true),
|
||||
},
|
||||
},
|
||||
},
|
||||
},
|
||||
|
||||
"storage_profile_image_reference": {
|
||||
Type: schema.TypeSet,
|
||||
Optional: true,
|
||||
|
@ -450,6 +491,15 @@ func resourceArmVirtualMachineScaleSetCreate(d *schema.ResourceData, meta interf
|
|||
return err
|
||||
}
|
||||
storageProfile.OsDisk = osDisk
|
||||
|
||||
if _, ok := d.GetOk("storage_profile_data_disk"); ok {
|
||||
dataDisks, err := expandAzureRMVirtualMachineScaleSetsStorageProfileDataDisk(d)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
storageProfile.DataDisks = &dataDisks
|
||||
}
|
||||
|
||||
if _, ok := d.GetOk("storage_profile_image_reference"); ok {
|
||||
imageRef, err := expandAzureRmVirtualMachineScaleSetStorageProfileImageReference(d)
|
||||
if err != nil {
|
||||
|
@ -586,6 +636,12 @@ func resourceArmVirtualMachineScaleSetRead(d *schema.ResourceData, meta interfac
|
|||
return fmt.Errorf("[DEBUG] Error setting Virtual Machine Scale Set Storage Profile OS Disk error: %#v", err)
|
||||
}
|
||||
|
||||
if resp.VirtualMachineProfile.StorageProfile.DataDisks != nil {
|
||||
if err := d.Set("storage_profile_data_disk", flattenAzureRmVirtualMachineScaleSetStorageProfileDataDisk(properties.VirtualMachineProfile.StorageProfile.DataDisks)); err != nil {
|
||||
return fmt.Errorf("[DEBUG] Error setting Virtual Machine Scale Set Storage Profile Data Disk error: %#v", err)
|
||||
}
|
||||
}
|
||||
|
||||
if properties.VirtualMachineProfile.ExtensionProfile != nil {
|
||||
extension, err := flattenAzureRmVirtualMachineScaleSetExtensionProfile(properties.VirtualMachineProfile.ExtensionProfile)
|
||||
if err != nil {
|
||||
|
@ -802,6 +858,26 @@ func flattenAzureRmVirtualMachineScaleSetStorageProfileOSDisk(profile *compute.V
|
|||
return []interface{}{result}
|
||||
}
|
||||
|
||||
func flattenAzureRmVirtualMachineScaleSetStorageProfileDataDisk(disks *[]compute.VirtualMachineScaleSetDataDisk) interface{} {
|
||||
result := make([]interface{}, len(*disks))
|
||||
for i, disk := range *disks {
|
||||
l := make(map[string]interface{})
|
||||
if disk.ManagedDisk != nil {
|
||||
l["managed_disk_type"] = string(disk.ManagedDisk.StorageAccountType)
|
||||
}
|
||||
|
||||
l["create_option"] = disk.CreateOption
|
||||
l["caching"] = string(disk.Caching)
|
||||
if disk.DiskSizeGB != nil {
|
||||
l["disk_size_gb"] = *disk.DiskSizeGB
|
||||
}
|
||||
l["lun"] = *disk.Lun
|
||||
|
||||
result[i] = l
|
||||
}
|
||||
return result
|
||||
}
|
||||
|
||||
func flattenAzureRmVirtualMachineScaleSetStorageProfileImageReference(profile *compute.ImageReference) []interface{} {
|
||||
result := make(map[string]interface{})
|
||||
result["publisher"] = *profile.Publisher
|
||||
|
@ -1149,6 +1225,46 @@ func expandAzureRMVirtualMachineScaleSetsStorageProfileOsDisk(d *schema.Resource
|
|||
return osDisk, nil
|
||||
}
|
||||
|
||||
func expandAzureRMVirtualMachineScaleSetsStorageProfileDataDisk(d *schema.ResourceData) ([]compute.VirtualMachineScaleSetDataDisk, error) {
|
||||
disks := d.Get("storage_profile_data_disk").([]interface{})
|
||||
dataDisks := make([]compute.VirtualMachineScaleSetDataDisk, 0, len(disks))
|
||||
for _, diskConfig := range disks {
|
||||
config := diskConfig.(map[string]interface{})
|
||||
|
||||
createOption := config["create_option"].(string)
|
||||
managedDiskType := config["managed_disk_type"].(string)
|
||||
lun := int32(config["lun"].(int))
|
||||
|
||||
dataDisk := compute.VirtualMachineScaleSetDataDisk{
|
||||
Lun: &lun,
|
||||
CreateOption: compute.DiskCreateOptionTypes(createOption),
|
||||
}
|
||||
|
||||
managedDiskVMSS := &compute.VirtualMachineScaleSetManagedDiskParameters{}
|
||||
|
||||
if managedDiskType != "" {
|
||||
managedDiskVMSS.StorageAccountType = compute.StorageAccountTypes(managedDiskType)
|
||||
} else {
|
||||
managedDiskVMSS.StorageAccountType = compute.StorageAccountTypes(compute.StandardLRS)
|
||||
}
|
||||
|
||||
//assume that data disks in VMSS can only be Managed Disks
|
||||
dataDisk.ManagedDisk = managedDiskVMSS
|
||||
if v := config["caching"].(string); v != "" {
|
||||
dataDisk.Caching = compute.CachingTypes(v)
|
||||
}
|
||||
|
||||
if v := config["disk_size_gb"]; v != nil {
|
||||
diskSize := int32(config["disk_size_gb"].(int))
|
||||
dataDisk.DiskSizeGB = &diskSize
|
||||
}
|
||||
|
||||
dataDisks = append(dataDisks, dataDisk)
|
||||
}
|
||||
|
||||
return dataDisks, nil
|
||||
}
|
||||
|
||||
func expandAzureRmVirtualMachineScaleSetStorageProfileImageReference(d *schema.ResourceData) (*compute.ImageReference, error) {
|
||||
storageImageRefs := d.Get("storage_profile_image_reference").(*schema.Set).List()
|
||||
|
||||
|
|
|
@ -136,6 +136,25 @@ func TestAccAzureRMVirtualMachineScaleSet_loadBalancer(t *testing.T) {
|
|||
})
|
||||
}
|
||||
|
||||
func TestAccAzureRMVirtualMachineScaleSet_loadBalancerManagedDataDisks(t *testing.T) {
|
||||
ri := acctest.RandInt()
|
||||
config := fmt.Sprintf(testAccAzureRMVirtualMachineScaleSetLoadbalancerTemplateManagedDataDisks, ri, ri, ri, ri, ri, ri)
|
||||
resource.Test(t, resource.TestCase{
|
||||
PreCheck: func() { testAccPreCheck(t) },
|
||||
Providers: testAccProviders,
|
||||
CheckDestroy: testCheckAzureRMVirtualMachineScaleSetDestroy,
|
||||
Steps: []resource.TestStep{
|
||||
{
|
||||
Config: config,
|
||||
Check: resource.ComposeTestCheckFunc(
|
||||
testCheckAzureRMVirtualMachineScaleSetExists("azurerm_virtual_machine_scale_set.test"),
|
||||
testCheckAzureRMVirtualMachineScaleSetHasDataDisks("azurerm_virtual_machine_scale_set.test"),
|
||||
),
|
||||
},
|
||||
},
|
||||
})
|
||||
}
|
||||
|
||||
func TestAccAzureRMVirtualMachineScaleSet_overprovision(t *testing.T) {
|
||||
ri := acctest.RandInt()
|
||||
config := fmt.Sprintf(testAccAzureRMVirtualMachineScaleSetOverprovisionTemplate, ri, ri, ri, ri, ri, ri)
|
||||
|
@ -369,6 +388,39 @@ func testCheckAzureRMVirtualMachineScaleSetExtension(name string) resource.TestC
|
|||
}
|
||||
}
|
||||
|
||||
func testCheckAzureRMVirtualMachineScaleSetHasDataDisks(name string) resource.TestCheckFunc {
|
||||
return func(s *terraform.State) error {
|
||||
// Ensure we have enough information in state to look up in API
|
||||
rs, ok := s.RootModule().Resources[name]
|
||||
if !ok {
|
||||
return fmt.Errorf("Not found: %s", name)
|
||||
}
|
||||
|
||||
name := rs.Primary.Attributes["name"]
|
||||
resourceGroup, hasResourceGroup := rs.Primary.Attributes["resource_group_name"]
|
||||
if !hasResourceGroup {
|
||||
return fmt.Errorf("Bad: no resource group found in state for virtual machine: scale set %s", name)
|
||||
}
|
||||
|
||||
conn := testAccProvider.Meta().(*ArmClient).vmScaleSetClient
|
||||
resp, err := conn.Get(resourceGroup, name)
|
||||
if err != nil {
|
||||
return fmt.Errorf("Bad: Get on vmScaleSetClient: %s", err)
|
||||
}
|
||||
|
||||
if resp.StatusCode == http.StatusNotFound {
|
||||
return fmt.Errorf("Bad: VirtualMachineScaleSet %q (resource group: %q) does not exist", name, resourceGroup)
|
||||
}
|
||||
|
||||
storageProfile := resp.VirtualMachineProfile.StorageProfile.DataDisks
|
||||
if storageProfile == nil || len(*storageProfile) == 0 {
|
||||
return fmt.Errorf("Bad: Could not get data disks configurations for scale set %v", name)
|
||||
}
|
||||
|
||||
return nil
|
||||
}
|
||||
}
|
||||
|
||||
var testAccAzureRMVirtualMachineScaleSet_basic = `
|
||||
resource "azurerm_resource_group" "test" {
|
||||
name = "acctestRG-%d"
|
||||
|
@ -1286,3 +1338,84 @@ resource "azurerm_virtual_machine_scale_set" "test" {
|
|||
}
|
||||
}
|
||||
`
|
||||
|
||||
var testAccAzureRMVirtualMachineScaleSetLoadbalancerTemplateManagedDataDisks = `
|
||||
resource "azurerm_resource_group" "test" {
|
||||
name = "acctestrg-%d"
|
||||
location = "southcentralus"
|
||||
}
|
||||
resource "azurerm_virtual_network" "test" {
|
||||
name = "acctvn-%d"
|
||||
address_space = ["10.0.0.0/16"]
|
||||
location = "southcentralus"
|
||||
resource_group_name = "${azurerm_resource_group.test.name}"
|
||||
}
|
||||
resource "azurerm_subnet" "test" {
|
||||
name = "acctsub-%d"
|
||||
resource_group_name = "${azurerm_resource_group.test.name}"
|
||||
virtual_network_name = "${azurerm_virtual_network.test.name}"
|
||||
address_prefix = "10.0.2.0/24"
|
||||
}
|
||||
resource "azurerm_lb" "test" {
|
||||
name = "acctestlb-%d"
|
||||
location = "southcentralus"
|
||||
resource_group_name = "${azurerm_resource_group.test.name}"
|
||||
frontend_ip_configuration {
|
||||
name = "default"
|
||||
subnet_id = "${azurerm_subnet.test.id}"
|
||||
private_ip_address_allocation = "Dynamic"
|
||||
}
|
||||
}
|
||||
resource "azurerm_lb_backend_address_pool" "test" {
|
||||
name = "test"
|
||||
resource_group_name = "${azurerm_resource_group.test.name}"
|
||||
loadbalancer_id = "${azurerm_lb.test.id}"
|
||||
}
|
||||
resource "azurerm_virtual_machine_scale_set" "test" {
|
||||
name = "acctvmss-%d"
|
||||
location = "southcentralus"
|
||||
resource_group_name = "${azurerm_resource_group.test.name}"
|
||||
upgrade_policy_mode = "Manual"
|
||||
sku {
|
||||
name = "Standard_A0"
|
||||
tier = "Standard"
|
||||
capacity = 1
|
||||
}
|
||||
os_profile {
|
||||
computer_name_prefix = "testvm-%d"
|
||||
admin_username = "myadmin"
|
||||
admin_password = "Passwword1234"
|
||||
}
|
||||
network_profile {
|
||||
name = "TestNetworkProfile"
|
||||
primary = true
|
||||
ip_configuration {
|
||||
name = "TestIPConfiguration"
|
||||
subnet_id = "${azurerm_subnet.test.id}"
|
||||
load_balancer_backend_address_pool_ids = [ "${azurerm_lb_backend_address_pool.test.id}" ]
|
||||
}
|
||||
}
|
||||
|
||||
storage_profile_os_disk {
|
||||
name = ""
|
||||
caching = "ReadWrite"
|
||||
create_option = "FromImage"
|
||||
managed_disk_type = "Standard_LRS"
|
||||
}
|
||||
|
||||
storage_profile_data_disk {
|
||||
lun = 0
|
||||
caching = "ReadWrite"
|
||||
create_option = "Empty"
|
||||
disk_size_gb = 10
|
||||
managed_disk_type = "Standard_LRS"
|
||||
}
|
||||
|
||||
storage_profile_image_reference {
|
||||
publisher = "Canonical"
|
||||
offer = "UbuntuServer"
|
||||
sku = "16.04.0-LTS"
|
||||
version = "latest"
|
||||
}
|
||||
}
|
||||
`
|
||||
|
|
|
@ -195,6 +195,13 @@ resource "azurerm_virtual_machine_scale_set" "test" {
|
|||
managed_disk_type = "Standard_LRS"
|
||||
}
|
||||
|
||||
storage_profile_data_disk {
|
||||
lun = 0
|
||||
caching = "ReadWrite"
|
||||
create_option = "Empty"
|
||||
disk_size_gb = 10
|
||||
}
|
||||
|
||||
os_profile {
|
||||
computer_name_prefix = "testvm"
|
||||
admin_username = "myadmin"
|
||||
|
@ -248,6 +255,7 @@ The following arguments are supported:
|
|||
* `os_profile_linux_config` - (Required, when a linux machine) A Linux config block as documented below.
|
||||
* `network_profile` - (Required) A collection of network profile block as documented below.
|
||||
* `storage_profile_os_disk` - (Required) A storage profile os disk block as documented below
|
||||
* `storage_profile_data_disk` - (Optional) A storage profile data disk block as documented below
|
||||
* `storage_profile_image_reference` - (Optional) A storage profile image reference block as documented below.
|
||||
* `extension` - (Optional) Can be specified multiple times to add extension profiles to the scale set. Each `extension` block supports the fields documented below.
|
||||
* `tags` - (Optional) A mapping of tags to assign to the resource.
|
||||
|
@ -329,6 +337,15 @@ The following arguments are supported:
|
|||
When setting this field `os_type` needs to be specified. Cannot be used when `vhd_containers`, `managed_disk_type` or `storage_profile_image_reference ` are specified.
|
||||
* `os_type` - (Optional) Specifies the operating system Type, valid values are windows, linux.
|
||||
|
||||
`storage_profile_data_disk` supports the following:
|
||||
|
||||
* `lun` - (Required) Specifies the Logical Unit Number of the disk in each virtual machine in the scale set.
|
||||
`Premium_LRS`.
|
||||
* `create_option` - (Optional) Specifies how the data disk should be created. The only possible options are `FromImage` and `Empty`.
|
||||
* `caching` - (Optional) Specifies the caching requirements. Possible values include: `None` (default), `ReadOnly`, `ReadWrite`.
|
||||
* `disk_size_gb` - (Optional) Specifies the size of the disk in GB. This element is required when creating an empty disk.
|
||||
* `managed_disk_type` - (Optional) Specifies the type of managed disk to create. Value must be either `Standard_LRS` or
|
||||
|
||||
`storage_profile_image_reference` supports the following:
|
||||
|
||||
* `publisher` - (Required) Specifies the publisher of the image used to create the virtual machines
|
||||
|
|
Loading…
Reference in New Issue