def create_private_dns_zone(self, zone: str, link_vnets: List[Tuple[str, str]] = [], rsg: str = None) -> None: """Create private DNS zone in Azure Args: zone (str): domain name of the zone """ self.logger.info(f"Creating private DNS zone: {zone}") dns = self.client( PrivateDnsManagementClient).private_zones.create_or_update( self.rsg if not rsg else rsg, zone, PrivateZone(location="global")) dns = dns.result() for vnet_rsg, vnet_name in link_vnets: self.private_dns_link_to_vnet( rsg, zone, vnet_rsg, vnet_name, ) self.logger.info("Private DNS Zone created, VNETs linked")
def _ensure_ase_private_dns_zone(cli_ctx, resource_group_name, name, inbound_vnet_id, inbound_ip_address): # Private DNS Zone private_dns_client = _get_private_dns_client_factory(cli_ctx) zone_name = '{}.appserviceenvironment.net'.format(name) zone = PrivateZone(location='global', tags=None) poller = private_dns_client.private_zones.begin_create_or_update( resource_group_name, zone_name, zone) LongRunningOperation(cli_ctx)(poller) link_name = '{}_link'.format(name) link = VirtualNetworkLink(location='global', tags=None) link.virtual_network = SubResource(id=inbound_vnet_id) link.registration_enabled = False private_dns_client.virtual_network_links.begin_create_or_update( resource_group_name, zone_name, link_name, link, if_none_match='*') ase_record = ARecord(ipv4_address=inbound_ip_address) record_set = RecordSet(ttl=3600) record_set.a_records = [ase_record] private_dns_client.record_sets.create_or_update(resource_group_name, zone_name, 'a', '*', record_set) private_dns_client.record_sets.create_or_update(resource_group_name, zone_name, 'a', '@', record_set) private_dns_client.record_sets.create_or_update(resource_group_name, zone_name, 'a', '*.scm', record_set)
def create_privatedns_zone(cmd, resource_group_name, private_zone_name, tags=None): from azure.mgmt.privatedns import PrivateDnsManagementClient from azure.mgmt.privatedns.models import PrivateZone client = get_mgmt_service_client(cmd.cli_ctx, PrivateDnsManagementClient).private_zones if private_zone_name.endswith(".local"): logger.warning(("Please be aware that DNS names ending with .local are reserved for use with multicast DNS " "and may not work as expected with some operating systems. For details refer to your operating systems documentation.")) zone = PrivateZone(location='global', tags=tags) return client.begin_create_or_update(resource_group_name, private_zone_name, zone, if_none_match='*')
def prepare_private_dns_zone(db_context, database_engine, resource_group, server_name, private_dns_zone, subnet_id, location, yes): cmd = db_context.cmd dns_suffix_client = db_context.cf_private_dns_zone_suffix(cmd.cli_ctx, '_') private_dns_zone_suffix = dns_suffix_client.execute() if db_context.command_group == 'mysql': private_dns_zone_suffix = private_dns_zone_suffix.private_dns_zone_suffix # suffix should start with . if private_dns_zone_suffix[0] != '.': private_dns_zone_suffix = '.' + private_dns_zone_suffix # Get Vnet Components vnet_subscription, vnet_rg, vnet_name, _ = get_id_components(subnet_id) nw_client = network_client_factory(cmd.cli_ctx, subscription_id=vnet_subscription) vnet_id = resource_id(subscription=vnet_subscription, resource_group=vnet_rg, namespace='Microsoft.Network', type='virtualNetworks', name=vnet_name) vnet = nw_client.virtual_networks.get(vnet_rg, vnet_name) # Process private dns zone (no input or Id input) dns_rg = None dns_subscription = vnet_subscription if private_dns_zone is None: if 'private' in private_dns_zone_suffix: private_dns_zone = server_name + private_dns_zone_suffix else: private_dns_zone = server_name + '.private' + private_dns_zone_suffix elif not _is_resource_name(private_dns_zone) and is_valid_resource_id( private_dns_zone): dns_subscription, dns_rg, private_dns_zone, _ = get_id_components( private_dns_zone) validate_private_dns_zone(db_context, server_name=server_name, private_dns_zone=private_dns_zone, private_dns_zone_suffix=private_dns_zone_suffix) server_sub_resource_client = resource_client_factory( cmd.cli_ctx, subscription_id=get_subscription_id(cmd.cli_ctx)) vnet_sub_resource_client = resource_client_factory( cmd.cli_ctx, subscription_id=vnet_subscription) dns_sub_resource_client = resource_client_factory( cmd.cli_ctx, subscription_id=dns_subscription) # check existence DNS zone and change resource group if dns_rg is not None: _create_and_verify_resource_group(dns_sub_resource_client, dns_rg, location, yes) # decide which resource group the dns zone provision zone_exist_flag = False if dns_rg is not None and check_existence( dns_sub_resource_client, private_dns_zone, dns_rg, 'Microsoft.Network', 'privateDnsZones'): zone_exist_flag = True elif dns_rg is None and check_existence( server_sub_resource_client, private_dns_zone, resource_group, 'Microsoft.Network', 'privateDnsZones'): zone_exist_flag = True dns_rg = resource_group dns_subscription = get_subscription_id(cmd.cli_ctx) elif dns_rg is None and check_existence( vnet_sub_resource_client, private_dns_zone, vnet_rg, 'Microsoft.Network', 'privateDnsZones'): zone_exist_flag = True dns_subscription = vnet_subscription dns_rg = vnet_rg elif dns_rg is None: zone_exist_flag = False dns_subscription = vnet_subscription dns_rg = vnet_rg private_dns_client = private_dns_client_factory( cmd.cli_ctx, subscription_id=dns_subscription) private_dns_link_client = private_dns_link_client_factory( cmd.cli_ctx, subscription_id=dns_subscription) link = VirtualNetworkLink(location='global', virtual_network=SubResource(id=vnet.id)) link.registration_enabled = False # create DNS zone if not exist if not zone_exist_flag: user_confirmation( "Do you want to create a new private DNS zone {0} in resource group {1}" .format(private_dns_zone, dns_rg), yes=yes) logger.warning('Creating a private dns zone %s in resource group "%s"', private_dns_zone, dns_rg) private_zone = private_dns_client.begin_create_or_update( resource_group_name=dns_rg, private_zone_name=private_dns_zone, parameters=PrivateZone(location='global'), if_none_match='*').result() private_dns_link_client.begin_create_or_update( resource_group_name=dns_rg, private_zone_name=private_dns_zone, virtual_network_link_name=vnet_name + '-link', parameters=link, if_none_match='*').result() else: logger.warning( 'Using the existing private dns zone %s in resource group "%s"', private_dns_zone, dns_rg) private_zone = private_dns_client.get( resource_group_name=dns_rg, private_zone_name=private_dns_zone) virtual_links = private_dns_link_client.list( resource_group_name=dns_rg, private_zone_name=private_dns_zone) link_exist_flag = False for virtual_link in virtual_links: if virtual_link.virtual_network.id == vnet_id: link_exist_flag = True break if not link_exist_flag: private_dns_link_client.begin_create_or_update( resource_group_name=dns_rg, private_zone_name=private_dns_zone, virtual_network_link_name=vnet_name + '-link', parameters=link, if_none_match='*').result() return private_zone.id
def import_zone(cmd, resource_group_name, private_zone_name, file_name): from azure.cli.core.util import read_file_content import sys from azure.mgmt.privatedns.models import RecordSet file_text = read_file_content(file_name) zone_obj = parse_zone_file(file_text, private_zone_name) origin = private_zone_name record_sets = {} for record_set_name in zone_obj: for record_set_type in zone_obj[record_set_name]: record_set_obj = zone_obj[record_set_name][record_set_type] if record_set_type == 'soa': origin = record_set_name.rstrip('.') if not isinstance(record_set_obj, list): record_set_obj = [record_set_obj] for entry in record_set_obj: record_set_ttl = entry['ttl'] record_set_key = '{}{}'.format(record_set_name.lower(), record_set_type) record = _build_record(cmd, entry) if not record: logger.warning( 'Cannot import %s. RecordType is not found. Skipping...', entry['delim'].lower()) continue record_set = record_sets.get(record_set_key, None) if not record_set: # Workaround for issue #2824 relative_record_set_name = record_set_name.rstrip('.') if not relative_record_set_name.endswith(origin): logger.warning( 'Cannot import %s. Only records relative to origin may be ' 'imported at this time. Skipping...', relative_record_set_name) continue record_set = RecordSet(ttl=record_set_ttl) record_sets[record_set_key] = record_set _privatedns_add_record(record_set, record, record_set_type, is_list=record_set_type.lower() not in ['soa', 'cname']) total_records = 0 for key, rs in record_sets.items(): rs_name, rs_type = key.lower().rsplit('.', 1) rs_name = rs_name[:-(len(origin) + 1)] if rs_name != origin else '@' try: record_count = len( getattr(rs, _privatedns_type_to_property_name(rs_type))) except TypeError: record_count = 1 total_records += record_count cum_records = 0 from azure.mgmt.privatedns import PrivateDnsManagementClient from azure.mgmt.privatedns.models import PrivateZone client = get_mgmt_service_client(cmd.cli_ctx, PrivateDnsManagementClient) print('== BEGINNING ZONE IMPORT: {} ==\n'.format(private_zone_name), file=sys.stderr) if private_zone_name.endswith(".local"): logger.warning(( "Please be aware that DNS names ending with .local are reserved for use with multicast DNS " "and may not work as expected with some operating systems. For details refer to your operating systems documentation." )) zone = PrivateZone(location='global') result = LongRunningOperation(cmd.cli_ctx)( client.private_zones.create_or_update(resource_group_name, private_zone_name, zone)) if result.provisioning_state != 'Succeeded': raise CLIError( 'Error occured while creating or updating private dns zone.') for key, rs in record_sets.items(): rs_name, rs_type = key.lower().rsplit('.', 1) rs_name = '@' if rs_name == origin else rs_name if rs_name.endswith(origin): rs_name = rs_name[:-(len(origin) + 1)] try: record_count = len( getattr(rs, _privatedns_type_to_property_name(rs_type))) except TypeError: record_count = 1 if rs_name == '@' and rs_type == 'soa': root_soa = client.record_sets.get(resource_group_name, private_zone_name, 'soa', '@') rs.soa_record.host = root_soa.soa_record.host rs_name = '@' try: client.record_sets.create_or_update(resource_group_name, private_zone_name, rs_type, rs_name, rs) cum_records += record_count print("({}/{}) Imported {} records of type '{}' and name '{}'". format(cum_records, total_records, record_count, rs_type, rs_name), file=sys.stderr) except CloudError as ex: logger.error(ex) print("\n== {}/{} RECORDS IMPORTED SUCCESSFULLY: '{}' ==".format( cum_records, total_records, private_zone_name), file=sys.stderr)
def prepare_private_dns_zone(cmd, database_engine, resource_group, server_name, private_dns_zone, subnet_id, location): from azure.mgmt.privatedns.models import SubResource dns_suffix_client = cf_postgres_flexible_private_dns_zone_suffix_operations( cmd.cli_ctx, '_') private_dns_zone_suffix = dns_suffix_client.execute(database_engine) vnet_sub, vnet_rg, vnet_name, _ = get_id_components(subnet_id) private_dns_client = private_dns_client_factory(cmd.cli_ctx) private_dns_link_client = private_dns_link_client_factory(cmd.cli_ctx) resource_client = resource_client_factory(cmd.cli_ctx) vnet_id = resource_id(subscription=vnet_sub, resource_group=vnet_rg, namespace='Microsoft.Network', type='virtualNetworks', name=vnet_name) nw_client = network_client_factory(cmd.cli_ctx, subscription_id=vnet_sub) vnet = nw_client.virtual_networks.get(vnet_rg, vnet_name) from azure.mgmt.privatedns.models import VirtualNetworkLink if private_dns_zone is None: private_dns_zone = server_name + '.' + private_dns_zone_suffix elif not _check_if_resource_name( private_dns_zone) and is_valid_resource_id(private_dns_zone): subscription, resource_group, private_dns_zone, _ = get_id_components( private_dns_zone) if private_dns_zone[-len(private_dns_zone_suffix ):] != private_dns_zone_suffix: raise ValidationError( 'The suffix for the private DNS zone should be "{}"'.format( private_dns_zone_suffix)) if subscription != get_subscription_id(cmd.cli_ctx): logger.warning( 'The provided private DNS zone ID is in different subscription from the server' ) resource_client = resource_client_factory( cmd.cli_ctx, subscription_id=subscription) private_dns_client = private_dns_client_factory( cmd.cli_ctx, subscription_id=subscription) private_dns_link_client = private_dns_link_client_factory( cmd.cli_ctx, subscription_id=subscription) _resource_group_verify_and_create(resource_client, resource_group, location) elif _check_if_resource_name(private_dns_zone) and not is_valid_resource_name(private_dns_zone) \ or not _check_if_resource_name(private_dns_zone) and not is_valid_resource_id(private_dns_zone): raise ValidationError( "Check if the private dns zone name or id is in correct format.") elif _check_if_resource_name(private_dns_zone) and private_dns_zone[ -len(private_dns_zone_suffix):] != private_dns_zone_suffix: raise ValidationError( 'The suffix for the private DNS zone should be "{}"'.format( private_dns_zone_suffix)) link = VirtualNetworkLink(location='global', virtual_network=SubResource(id=vnet.id)) link.registration_enabled = True if not check_existence(resource_client, private_dns_zone, resource_group, 'Microsoft.Network', 'privateDnsZones'): logger.warning('Creating a private dns zone %s..', private_dns_zone) from azure.mgmt.privatedns.models import PrivateZone private_zone = private_dns_client.create_or_update( resource_group_name=resource_group, private_zone_name=private_dns_zone, parameters=PrivateZone(location='global'), if_none_match='*').result() private_dns_link_client.create_or_update( resource_group_name=resource_group, private_zone_name=private_dns_zone, virtual_network_link_name=vnet_name + '-link', parameters=link, if_none_match='*').result() else: logger.warning('Using the existing private dns zone %s', private_dns_zone) private_zone = private_dns_client.get( resource_group_name=resource_group, private_zone_name=private_dns_zone) # private dns zone link list virtual_links = private_dns_link_client.list( resource_group_name=resource_group, private_zone_name=private_dns_zone) link_exist_flag = False for virtual_link in virtual_links: if virtual_link.virtual_network.id == vnet_id: link_exist_flag = True break if not link_exist_flag: private_dns_link_client.create_or_update( resource_group_name=resource_group, private_zone_name=private_dns_zone, virtual_network_link_name=vnet_name + '-link', parameters=link, if_none_match='*').result() return private_zone.id
def prepare_private_dns_zone(cmd, database_engine, resource_group, server_name, private_dns_zone, subnet_id, location): dns_suffix_client = cf_postgres_flexible_private_dns_zone_suffix_operations( cmd.cli_ctx, '_') private_dns_zone_suffix = dns_suffix_client.execute(database_engine) vnet_sub, vnet_rg, vnet_name, _ = get_id_components(subnet_id) private_dns_client = private_dns_client_factory(cmd.cli_ctx) private_dns_link_client = private_dns_link_client_factory(cmd.cli_ctx) resource_client = resource_client_factory(cmd.cli_ctx) vnet_id = resource_id(subscription=vnet_sub, resource_group=vnet_rg, namespace='Microsoft.Network', type='virtualNetworks', name=vnet_name) nw_client = network_client_factory(cmd.cli_ctx, subscription_id=vnet_sub) vnet = nw_client.virtual_networks.get(vnet_rg, vnet_name) dns_rg = None if private_dns_zone is None: if 'private' in private_dns_zone_suffix: private_dns_zone = server_name + '.' + private_dns_zone_suffix else: private_dns_zone = server_name + '.private.' + private_dns_zone_suffix # resource ID input => check subscription and change client elif not _check_if_resource_name( private_dns_zone) and is_valid_resource_id(private_dns_zone): subscription, dns_rg, private_dns_zone, _ = get_id_components( private_dns_zone) if private_dns_zone[-len(private_dns_zone_suffix ):] != private_dns_zone_suffix: raise ValidationError( 'The suffix of the private DNS zone should be "{}"'.format( private_dns_zone_suffix)) if subscription != get_subscription_id(cmd.cli_ctx): logger.warning( 'The provided private DNS zone ID is in different subscription from the server' ) resource_client = resource_client_factory( cmd.cli_ctx, subscription_id=subscription) private_dns_client = private_dns_client_factory( cmd.cli_ctx, subscription_id=subscription) private_dns_link_client = private_dns_link_client_factory( cmd.cli_ctx, subscription_id=subscription) _resource_group_verify_and_create(resource_client, dns_rg, location) # check Invalid resource ID or Name format elif _check_if_resource_name(private_dns_zone) and not is_valid_resource_name(private_dns_zone) \ or not _check_if_resource_name(private_dns_zone) and not is_valid_resource_id(private_dns_zone): raise ValidationError( "Check if the private dns zone name or Id is in correct format.") # Invalid resource name suffix check elif _check_if_resource_name(private_dns_zone) and private_dns_zone[ -len(private_dns_zone_suffix):] != private_dns_zone_suffix: raise ValidationError( 'The suffix of the private DNS zone should be in "{}" format'. format(private_dns_zone_suffix)) validate_private_dns_zone(cmd, server_name=server_name, private_dns_zone=private_dns_zone) link = VirtualNetworkLink(location='global', virtual_network=SubResource(id=vnet.id)) link.registration_enabled = False # check existence DNS zone and change resource group zone_exist_flag = False if dns_rg is not None and check_existence( resource_client, private_dns_zone, dns_rg, 'Microsoft.Network', 'privateDnsZones'): zone_exist_flag = True elif dns_rg is None and check_existence( resource_client, private_dns_zone, resource_group, 'Microsoft.Network', 'privateDnsZones'): zone_exist_flag = True dns_rg = resource_group elif dns_rg is None and check_existence(resource_client, private_dns_zone, vnet_rg, 'Microsoft.Network', 'privateDnsZones'): zone_exist_flag = True dns_rg = vnet_rg else: dns_rg = vnet_rg # create DNS zone if not exist if not zone_exist_flag: logger.warning('Creating a private dns zone %s in resource group "%s"', private_dns_zone, dns_rg) private_zone = private_dns_client.begin_create_or_update( resource_group_name=dns_rg, private_zone_name=private_dns_zone, parameters=PrivateZone(location='global'), if_none_match='*').result() private_dns_link_client.begin_create_or_update( resource_group_name=dns_rg, private_zone_name=private_dns_zone, virtual_network_link_name=vnet_name + '-link', parameters=link, if_none_match='*').result() else: logger.warning( 'Using the existing private dns zone %s in resource group "%s"', private_dns_zone, dns_rg) private_zone = private_dns_client.get( resource_group_name=dns_rg, private_zone_name=private_dns_zone) virtual_links = private_dns_link_client.list( resource_group_name=dns_rg, private_zone_name=private_dns_zone) link_exist_flag = False for virtual_link in virtual_links: if virtual_link.virtual_network.id == vnet_id: link_exist_flag = True break if not link_exist_flag: private_dns_link_client.begin_create_or_update( resource_group_name=dns_rg, private_zone_name=private_dns_zone, virtual_network_link_name=vnet_name + '-link', parameters=link, if_none_match='*').result() return private_zone.id