Add support for standard and ultra SSDs

- Breaking change on premium property in managed disks
- Add availability zone support
This commit is contained in:
Fred Park 2018-11-05 14:42:39 -08:00
Родитель 7ad6a1df05
Коммит 95dec309fe
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 3C4D545F457737EB
6 изменённых файлов: 127 добавлений и 38 удалений

Просмотреть файл

@ -1,9 +1,10 @@
remote_fs:
resource_group: my-resource-group
location: <Azure region, e.g., eastus>
zone: null
managed_disks:
resource_group: my-disk-resource-group
premium: true
sku: premium_lrs
disk_size_gb: 128
disk_names:
- p10-disk0a

Просмотреть файл

@ -64,12 +64,35 @@ def _create_managed_disk(compute_client, rfs, disk_name):
:rtype: msrestazure.azure_operation.AzureOperationPoller
:return: async operation handle
"""
account_type = (
compute_client.disks.models.StorageAccountTypes.premium_lrs
if rfs.managed_disks.premium else
compute_client.disks.models.StorageAccountTypes.standard_lrs
)
logger.info('creating managed disk: {}'.format(disk_name))
iops_rw = None
mbps_rw = None
if rfs.managed_disks.zone is not None:
zone = [rfs.managed_disks.zone]
else:
zone = None
if rfs.managed_disks.sku == 'standard_lrs':
sku = compute_client.disks.models.DiskStorageAccountTypes(
'Standard_LRS')
elif rfs.managed_disks.sku == 'premium_lrs':
sku = compute_client.disks.models.DiskStorageAccountTypes(
'Premium_LRS')
elif rfs.managed_disks.sku == 'standard_ssd_lrs':
sku = compute_client.disks.models.DiskStorageAccountTypes(
'StandardSSD_LRS')
elif rfs.managed_disks.sku == 'ultra_ssd_lrs':
sku = compute_client.disks.models.DiskStorageAccountTypes(
'UltraSSD_LRS')
if zone is None:
raise ValueError(
'Ultra SSD disks requires availabilty zones, please specify '
'zone in configuration')
iops_rw = rfs.managed_disks.disk_provisioned_perf_iops_rw
mbps_rw = rfs.managed_disks.disk_provisioned_perf_mbps_rw
logger.info(
'creating managed disk: {} size={} GB sku={} zone={} iops_rw={} '
'mbps_rw={}'.format(
disk_name, rfs.managed_disks.disk_size_gb, sku, zone,
iops_rw, mbps_rw))
return compute_client.disks.create_or_update(
resource_group_name=rfs.managed_disks.resource_group,
disk_name=disk_name,
@ -80,10 +103,13 @@ def _create_managed_disk(compute_client, rfs, disk_name):
DiskCreateOption.empty,
),
sku=compute_client.disks.models.DiskSku(
name=account_type,
name=sku,
),
os_type=compute_client.disks.models.OperatingSystemTypes.linux,
disk_size_gb=rfs.managed_disks.disk_size_gb,
zones=zone,
disk_iops_read_write=iops_rw,
disk_mbps_read_write=mbps_rw,
),
)
@ -430,7 +456,10 @@ def _create_availability_set(compute_client, rfs):
:return: msrestazure.azure_operation.AzureOperationPoller
"""
if rfs.storage_cluster.vm_count <= 1:
logger.warning('insufficient vm_count for availability set')
logger.info('insufficient vm_count for availability set')
return None
if rfs.storage_cluster.zone is not None:
logger.info('cannot create an availability set for zonal resource')
return None
as_name = settings.generate_availability_set_name(rfs.storage_cluster)
# check and fail if as exists

Просмотреть файл

@ -572,9 +572,13 @@ def create_public_ip(network_client, vm_resource, offset):
pass
else:
raise
if vm_resource.zone is not None:
zone = [vm_resource.zone]
else:
zone = None
hostname = settings.generate_hostname(vm_resource, offset)
logger.debug('creating public ip: {} with label: {}'.format(
pip_name, hostname))
logger.debug('creating public ip: {} label={} zone={}'.format(
pip_name, hostname, zone))
return network_client.public_ip_addresses.create_or_update(
resource_group_name=vm_resource.resource_group,
public_ip_address_name=pip_name,
@ -590,6 +594,7 @@ def create_public_ip(network_client, vm_resource, offset):
networkmodels.IPAllocationMethod.dynamic
),
public_ip_address_version=networkmodels.IPVersion.ipv4,
zones=zone,
),
)
@ -703,6 +708,10 @@ def create_virtual_machine(
)
)
lun += 1
if vm_resource.zone is not None:
zone = [vm_resource.zone]
else:
zone = None
# sub resource availbility set
if availset is not None:
availset = compute_client.virtual_machines.models.SubResource(
@ -717,7 +726,9 @@ def create_virtual_machine(
ResourceIdentityType.system_assigned,
)
# create vm
logger.debug('creating virtual machine: {}'.format(vm_name))
logger.debug(
'creating virtual machine: {} availset={} zone={}'.format(
vm_name, availset.id, zone))
return compute_client.virtual_machines.create_or_update(
resource_group_name=vm_resource.resource_group,
vm_name=vm_name,
@ -772,6 +783,7 @@ def create_virtual_machine(
),
),
identity=identity,
zones=zone,
),
)

Просмотреть файл

@ -354,7 +354,9 @@ FederationConstraintSettings = collections.namedtuple(
)
ManagedDisksSettings = collections.namedtuple(
'ManagedDisksSettings', [
'location', 'resource_group', 'premium', 'disk_size_gb', 'disk_names',
'location', 'resource_group', 'zone', 'sku', 'disk_size_gb',
'disk_provisioned_perf_iops_rw', 'disk_provisioned_perf_mbps_rw',
'disk_names',
]
)
VirtualNetworkSettings = collections.namedtuple(
@ -442,10 +444,10 @@ class VmResource(object):
def __init__(
self, location, resource_group, hostname_prefix, vm_size,
public_ip, virtual_network, network_security, ssh,
accelerated_networking):
accelerated_networking, zone):
# type: (VmResource, str, str, str, str, PublicIpSettings,
# VirtualNetworkSettings, NetworkSecuritySettings, SSHSettings,
# bool) -> None
# bool, int) -> None
if location is None or ' ' in location:
raise ValueError('invalid location specified')
self.location = location
@ -457,6 +459,7 @@ class VmResource(object):
self.network_security = network_security
self.ssh = ssh
self.accelerated_networking = accelerated_networking
self.zone = zone
class StorageClusterSettings(VmResource):
@ -464,14 +467,15 @@ class StorageClusterSettings(VmResource):
self, id, file_server, vm_count, fault_domains, vm_disk_map,
location, resource_group, hostname_prefix, vm_size,
public_ip, virtual_network, network_security, ssh,
accelerated_networking, prometheus):
accelerated_networking, zone, prometheus):
# type: (StorageClusterSettings, str, FileServerSettings, int, int,
# Dict, str, str, str, str, PublicIpSettings,
# VirtualNetworkSettings, NetworkSecuritySettings, SSHSettings,
# bool, PrometheusSettings) -> None
# bool, int, PrometheusSettings) -> None
super(StorageClusterSettings, self).__init__(
location, resource_group, hostname_prefix, vm_size, public_ip,
virtual_network, network_security, ssh, accelerated_networking)
virtual_network, network_security, ssh, accelerated_networking,
zone)
self.id = id
self.file_server = file_server
self.vm_count = vm_count
@ -4254,19 +4258,28 @@ def remotefs_settings(config, sc_id=None):
location = conf['location']
if util.is_none_or_empty(location):
raise ValueError('invalid location in remote_fs')
zone = _kv_read(conf, 'zone')
# managed disk settings
md_conf = conf['managed_disks']
md_rg = _kv_read_checked(md_conf, 'resource_group', resource_group)
if util.is_none_or_empty(md_rg):
raise ValueError('invalid managed_disks:resource_group in remote_fs')
md_premium = _kv_read(md_conf, 'premium', False)
md_sku = _kv_read(md_conf, 'sku')
if util.is_none_or_empty(md_sku):
raise ValueError('invalid managed_disks:sku in remote_fs')
md_disk_size_gb = _kv_read(md_conf, 'disk_size_gb')
md_disk_pp = _kv_read(md_conf, 'disk_provisioned_performance', default={})
md_disk_pp_iops = _kv_read(md_disk_pp, 'iops_read_write')
md_disk_pp_mbps = _kv_read(md_disk_pp, 'mbps_read_write')
md_disk_names = _kv_read_checked(md_conf, 'disk_names')
md = ManagedDisksSettings(
location=location,
resource_group=md_rg,
premium=md_premium,
zone=zone,
sku=md_sku,
disk_size_gb=md_disk_size_gb,
disk_provisioned_perf_iops_rw=md_disk_pp_iops,
disk_provisioned_perf_mbps_rw=md_disk_pp_mbps,
disk_names=md_disk_names,
)
if util.is_none_or_empty(sc_id):
@ -4428,17 +4441,12 @@ def remotefs_settings(config, sc_id=None):
('Number of entries in vm_disk_map {} inconsistent with '
'vm_count {}').format(len(disk_map), sc_vm_count))
return RemoteFsSettings(
managed_disks=ManagedDisksSettings(
location=location,
resource_group=md_rg,
premium=md_premium,
disk_size_gb=md_disk_size_gb,
disk_names=md_disk_names,
),
managed_disks=md,
storage_cluster=StorageClusterSettings(
id=sc_id,
location=location,
resource_group=sc_rg,
zone=zone,
virtual_network=virtual_network_settings(
sc_conf,
default_resource_group=sc_rg,
@ -4678,6 +4686,7 @@ def monitoring_settings(config):
return VmResource(
location=location,
resource_group=rg,
zone=_kv_read(conf, 'zone'),
hostname_prefix=hostname_prefix,
virtual_network=virtual_network_settings(
conf,
@ -4826,6 +4835,7 @@ def federation_settings(config):
return VmResource(
location=location,
resource_group=rg,
zone=_kv_read(conf, 'zone'),
hostname_prefix=hostname_prefix,
virtual_network=virtual_network_settings(
conf,

Просмотреть файл

@ -9,9 +9,10 @@ The remote filesystem schema is as follows:
remote_fs:
resource_group: my-resource-group
location: <Azure region, e.g., eastus>
zone: null
managed_disks:
resource_group: my-disk-resource-group
premium: true
sku: premium_lrs
disk_size_gb: 128
disk_names:
- p10-disk0a
@ -126,6 +127,13 @@ configuration blocks.
`eastus` or `northeurope`. The `location` specified must match the same
region as your Azure Batch account if linking a compute pool with a storage
cluster.
* (optional) `zone` is the availability zone to target for deployment.
This option is valid only for regions (i.e., `location`) supporting
[availability zones](https://docs.microsoft.com/azure/availability-zones/az-overview).
This option is required if using Ultra SSD disks. If a zone is specified,
automatic availability set creation for distributed/clustered file systems
will be disabled. Note that only one zone can be specified and resources
are not spread across availability zones for performance reasons.
### Managed Disks: `managed_disks`
This section defines the disks used by the file server as specified in the
@ -136,20 +144,30 @@ defined in this section.
* (optional) `resource_group` this is the resource group to use for the
disks. If this is not specified, then the `resource_group` specified in
the parent is used. At least one `resource_group` must be defined.
* (optional) `premium` defines if
[premium managed disks](https://docs.microsoft.com/azure/storage/storage-premium-storage)
should be created. Premium storage provisions a
[guaranteed level of IOPS and bandwidth](https://docs.microsoft.com/azure/storage/storage-premium-storage#premium-storage-scalability-and-performance-targets)
that scales with disk size. The default is `false` which creates
standard managed disks. Regardless of the type of storage used to back
managed disks, all data written is durable and persistent backed to Azure
Storage.
* (required) `sku` defines the
[disk storage account type](https://docs.microsoft.com/azure/virtual-machines/linux/about-disks-and-vhds#types-of-disks)
to use for the managed disks.
Valid values are `standard_lrs`, `premium_lrs`, `standard_ssd_lrs`, and
`ultra_ssd_lrs`. There is no default and this value must be specified.
If `ultra_ssd_lrs` is specified, then a `zone` must be specified in an
Availability Zone supported Azure region.
Regardless of the type of storage used to back managed disks, all data
written is durable and persistent backed to Azure Storage.
* (required) `disk_size_gb` is an integral value defining the size of the
data disks to create. Note that for managed disks, you are billed rounded
up to the nearest provisioned size. If you are unfamiliar with
how Azure prices managed disks with regard to the size of disk chosen,
please refer to
[this link](https://docs.microsoft.com/azure/storage/storage-managed-disks-overview#pricing-and-billing).
* (optional) `disk_provisioned_performance` defines provisioned performance
parameters for Ultra SSD disks. The following properties are ignored for all
`sku` types that are not `ultra_ssd_lrs`. Please see the
[Ultra SSD performance targets](https://docs.microsoft.com/azure/virtual-machines/windows/disks-ultra-ssd#scalability-and-performance-targets)
documentation for more information regarding the following values.
* (required) `iops_read_write` is the target provisioned IOPS for each
disk.
* (required) `mbps_read_write` is the target provisioned througput for
each disk in MB/s.
* (required) `disk_names` is an array of disk names to create. All disks
will be created identically with the properties defined in the `managed_disks`
section.

Просмотреть файл

@ -11,16 +11,35 @@ mapping:
location:
type: str
required: true
zone:
type: int
range:
min: 1
managed_disks:
type: map
mapping:
resource_group:
type: str
premium:
type: bool
sku:
type: str
required: true
enum: ['standard_lrs', 'premium_lrs', 'standard_ssd_lrs', 'ultra_ssd_lrs']
disk_size_gb:
type: int
required: true
disk_provisioned_performance:
type: map
mapping:
iops_read_write:
type: int
required: true
range:
min: 100
mbps_read_write:
type: int
required: true
range:
min: 1
disk_names:
type: seq
sequence: