====== DNS ====== Par cet exemple du DNS, je souhaite remontrer la différence entre une chaîne de caractères et un objet. ===== Demande initiale ===== Supposons que vous ayez à faire énormément de modifications DNS à cause d'un fournisseur qui change de serveur. On vous donne une liste d'enregistrements DNS de type A et il faut les modifier. Comme vous avez les bons réflexes, vous vous lancez dans deux opérations: - Vérifier les données fournies par le demandeur: la confiance n'exclut jamais le contrôle. - Fournir le rapport preCheck à votre commanditaire. Pour l'exemple, partons de fichier initial suivant: A_Record,Provider google.ca,p1 google.com,p1 google.fr,p2 google.toto,p3 ===== Le piège ===== Si on décide d'aborder le défi en utilisant powershell, alors bien des gens seraient tenter de partir ainsi en utilisant nslookup: Import-Csv -Path input_dns.csv | foreach { nslookup $_.A_Record 8.8.8.8 } On obtient des choses horribles. nslookup : Non-authoritative answer: At line:1 char:1 + nslookup google.ca 8.8.8.8 + ~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : NotSpecified: (Non-authoritative answer::String) [], RemoteException + FullyQualifiedErrorId : NativeCommandError Server: dns.google Address: 8.8.8.8 Name: google.ca Addresses: 2607:f8b0:4020:805::2003 172.217.13.131 Cela pose les problèmes suivants: - Les résultats s'affichent sur l'écran mais c'est très dur d'en extraire les informations. - nslookup n'est pas une commande Powershell alors on n'obtient pas d'objet adapté à notre requête DNS - Impossible d'utiliser les résultats pour créer notre fichier de preCheck ===== Le bon outil ===== Nous allons donc utiliser la commande DNS PowerShell: Resolve-Dns Import-Csv -Path input_dns.csv | foreach { Resolve-DnsName $_.A_Record -Type A -Server 8.8.8.8 } Cette fois-ci on obtient quelque chose de beaucoup plus sympa avec des objets que nous allons pouvoir manipuler. Name Type TTL Section IPAddress ---- ---- --- ------- --------- google.ca A 49 Answer 172.217.13.131 google.com A 299 Answer 172.217.13.110 google.fr A 299 Answer 172.217.13.163 Resolve-DnsName : google.toto : DNS name does not exist At line:2 char:7 + Resolve-DnsName $_.A_Record -Type A -Server 8.8.8.8 + ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ + CategoryInfo : ResourceUnavailable: (google.toto:String) [Resolve-DnsName], Win32Exception + FullyQualifiedErrorId : DNS_ERROR_RCODE_NAME_ERROR,Microsoft.DnsClient.Commands.ResolveDnsName On obtient toujours une exception pour l'enregistrement qui n'existe pas, mais avec un bloc "try" et une redirection de sortie d'erreurs, on va s'en sortir. Import-Csv -Path input_dns.csv | foreach { $currentLine = $_ $record = $currentLine.A_Record try { $result = Resolve-DnsName $record -Type A -Server 8.8.8.8 2> $null Write-Host $result.getType().fullname } catch { Write-Host ("Error with record: {0}" -f $record) } } On obtient des objets que nous allons pouvoir manipuler et exporter. Microsoft.DnsClient.Commands.DnsRecord_A Microsoft.DnsClient.Commands.DnsRecord_A Microsoft.DnsClient.Commands.DnsRecord_A Error with record: google.toto Name Type TTL Section IPAddress ---- ---- --- ------- --------- google.ca A 299 Answer 172.217.13.131 google.com A 299 Answer 172.217.13.110 google.fr A 299 Answer 172.217.13.163 ===== Script final ===== On se rappelle ce que l'on souhaite: prendre tous les enregistrements DNS A demandés et s'assurer qu'il n'y a pas d'erreurs dans la demande du client. $results = @() Import-Csv -Path input_dns.csv | foreach { $currentLine = $_ $record = $currentLine.A_Record try { $result = Resolve-DnsName $record -Type A -Server 8.8.8.8 2> $null Write-Host $result.getType().fullname $exportLine = $result | Select-Object -Property Name,Type,IPAddress $exportLine | Add-Member -MemberType NoteProperty -Name "Status" -Value "ok" } catch { Write-Host ("Error with record: {0}" -f $record) $exportLine = New-Object psobject -Property @{ 'Name' = $record; 'Type' = 'A'; 'IPAddress' = ''; 'Status' = 'ko'; } } $results += $exportLine } $results | Export-Csv -Path dnsPreCheck.csv -Delimiter "," -Encoding UTF8 -NoTypeInformation Le résultat permet de mettre en valeur un domaine qui n'a pas d'entrée A connue. C'est ce que l'on souhaitait découvrir. "Name","Type","IPAddress","Status" "google.ca","A","172.217.13.131","ok" "google.com","A","172.217.13.110","ok" "google.fr","A","172.217.13.163","ok" "google.toto","A","","ko"