Collectors/EmailAuthDns.ps1
|
@{ Name = 'EmailAuthDns' FileName = 'emailAuthDns' ApiVersion = 'v1.0' RequiredScopes = @('Directory.Read.All') Description = 'SPF, DKIM and DMARC DNS records for every verified domain (pure DNS; Graph is only used for the domain list).' Collect = { $domains = @(Invoke-TLGraphRequest -Uri '/v1.0/domains' -All | Where-Object { $_.isVerified }) $results = foreach ($domain in $domains) { $name = [string]$domain.id Write-Verbose ("Checking e-mail authentication DNS for {0}..." -f $name) # SPF $txtRecords = @(Resolve-TLDnsRecord -Name $name -Type TXT) $spfRecord = @($txtRecords | Where-Object { $_ -match '^v=spf1' }) | Select-Object -First 1 $spfQualifier = $null if ($spfRecord) { if ($spfRecord -match '-all\s*$') { $spfQualifier = 'hardfail' } elseif ($spfRecord -match '~all\s*$') { $spfQualifier = 'softfail' } elseif ($spfRecord -match '\?all\s*$') { $spfQualifier = 'neutral' } elseif ($spfRecord -match '\+?all\s*$') { $spfQualifier = 'pass-all' } } # DKIM - Microsoft 365 publishes CNAMEs for selector1/selector2 $selector1 = @(Resolve-TLDnsRecord -Name ("selector1._domainkey.{0}" -f $name) -Type CNAME) $selector2 = @(Resolve-TLDnsRecord -Name ("selector2._domainkey.{0}" -f $name) -Type CNAME) # DMARC $dmarcRecords = @(Resolve-TLDnsRecord -Name ("_dmarc.{0}" -f $name) -Type TXT) $dmarcRecord = @($dmarcRecords | Where-Object { $_ -match '^v=DMARC1' }) | Select-Object -First 1 $dmarcPolicy = $null if ($dmarcRecord -and $dmarcRecord -match 'p\s*=\s*(none|quarantine|reject)') { $dmarcPolicy = $Matches[1].ToLowerInvariant() } [ordered]@{ domain = $name isOnMicrosoft = [bool]($name -like '*.onmicrosoft.com') isDefault = [bool]$domain.isDefault # Technical domains (SBC trunks, third-party relays) carry no # 'Email' service - rules only enforce mail domains. isMailDomain = [bool](@($domain.supportedServices) -contains 'Email') spf = [ordered]@{ present = [bool]$spfRecord record = $spfRecord qualifier = $spfQualifier } dkim = [ordered]@{ selector1 = [bool](@($selector1).Count -gt 0) selector2 = [bool](@($selector2).Count -gt 0) targets = @(@($selector1) + @($selector2)) } dmarc = [ordered]@{ present = [bool]$dmarcRecord record = $dmarcRecord policy = $dmarcPolicy } } } , @($results) } } |