Initial commit
This commit is contained in:
64
core/utils.py
Normal file
64
core/utils.py
Normal file
@@ -0,0 +1,64 @@
|
||||
from typing import Dict, List, Any
|
||||
|
||||
from dns import resolver, exception
|
||||
|
||||
|
||||
def resolve_cname(hostname: str) -> List[str]:
|
||||
"""Resolve CNAME records for a hostname and return targets without trailing dots.
|
||||
|
||||
If there is no CNAME record, this returns an empty list.
|
||||
Raises dns.exception.DNSException on resolver errors.
|
||||
"""
|
||||
answers = resolver.resolve(hostname, "CNAME")
|
||||
targets: List[str] = []
|
||||
for rdata in answers:
|
||||
# rdata.target may be a Name object; to_text() yields with trailing dot
|
||||
target = getattr(rdata, "target", None)
|
||||
if target is None:
|
||||
# some dnspython versions use .to_text() directly on rdata
|
||||
text = rdata.to_text()
|
||||
else:
|
||||
text = target.to_text()
|
||||
targets.append(text.rstrip("."))
|
||||
return targets
|
||||
|
||||
|
||||
def check_cname_map(cname_map: Dict[str, str]) -> List[Dict[str, Any]]:
|
||||
"""Check a mapping of hostname -> expected CNAME target.
|
||||
|
||||
Returns a list of result dicts: {
|
||||
'hostname': str,
|
||||
'expected': str,
|
||||
'actual': List[str],
|
||||
'ok': bool,
|
||||
'error': Optional[str]
|
||||
}
|
||||
"""
|
||||
results: List[Dict[str, Any]] = []
|
||||
for hostname, expected in cname_map.items():
|
||||
expected_norm = expected.rstrip(".").lower()
|
||||
try:
|
||||
actual_targets = resolve_cname(hostname)
|
||||
actual_norm = [t.lower() for t in actual_targets]
|
||||
ok = expected_norm in actual_norm
|
||||
results.append({
|
||||
"hostname": hostname,
|
||||
"expected": expected,
|
||||
"actual": actual_targets,
|
||||
"ok": ok,
|
||||
"error": None,
|
||||
})
|
||||
except exception.DNSException as e:
|
||||
results.append({
|
||||
"hostname": hostname,
|
||||
"expected": expected,
|
||||
"actual": [],
|
||||
"ok": False,
|
||||
"error": str(e),
|
||||
})
|
||||
return results
|
||||
|
||||
|
||||
def bytes_to_gb(num_bytes: int) -> float:
|
||||
"""Convert bytes to gigabytes (GB, 1024^3)."""
|
||||
return round(num_bytes / (1024 ** 3), 3)
|
||||
Reference in New Issue
Block a user