Настройка мониторинга DNS (изменения, TTL, DNSSEC)
DNS-мониторинг часто игнорируется — и напрасно. Несанкционированное изменение DNS-записи, истечение домена или поломка DNSSEC могут сделать сайт недоступным так же эффективно, как падение сервера. При этом DNS-проблемы часто не видны в серверном мониторинге.
Что мониторить в DNS
A/AAAA записи. Неожиданное изменение IP указывает на: DNS hijacking, ошибочное изменение в панели, атаку на аккаунт регистратора.
MX записи. Изменение MX — возможная атака с целью перехвата почты.
NS записи. Изменение NS-серверов — серьёзный признак компрометации.
TTL. Аномально низкий TTL (< 60 секунд) может указывать на подготовку к смене записи.
DNSSEC. Broken DNSSEC signature = полная недоступность домена для resolver'ов с DNSSEC validation.
Срок истечения домена. Истёкший домен — потеря всей DNS-конфигурации.
Мониторинг изменений записей
import dns.resolver
import dns.dnssec
import hashlib
import json
from datetime import datetime
def get_dns_records(domain: str, record_types: list = None) -> dict:
if record_types is None:
record_types = ['A', 'AAAA', 'MX', 'NS', 'TXT', 'CNAME']
records = {}
resolver = dns.resolver.Resolver()
resolver.nameservers = ['8.8.8.8', '1.1.1.1'] # Проверять через разные resolver'ы
for rtype in record_types:
try:
answers = resolver.resolve(domain, rtype)
records[rtype] = sorted([str(r) for r in answers])
except (dns.resolver.NXDOMAIN, dns.resolver.NoAnswer):
records[rtype] = []
except Exception as e:
records[rtype] = [f'ERROR: {e}']
return records
def check_dns_changes(domain: str, stored_snapshot: dict) -> list:
current = get_dns_records(domain)
changes = []
for rtype, current_values in current.items():
stored_values = stored_snapshot.get(rtype, [])
if set(current_values) != set(stored_values):
changes.append({
'record_type': rtype,
'previous': stored_values,
'current': current_values,
'detected_at': datetime.utcnow().isoformat()
})
return changes
Запускать каждые 5-15 минут. При обнаружении изменений — немедленный алерт.
Мониторинг через несколько resolver'ов
DNS-отравление или неправильная зона может распространяться неравномерно. Проверять через:
- Google (8.8.8.8)
- Cloudflare (1.1.1.1)
- OpenDNS (208.67.222.222)
- Региональные resolver'ы (для ru-домена — важно)
Если результаты разные у разных resolver'ов — признак DNS hijacking или проблем с propagation.
Prometheus Blackbox Exporter для DNS
# blackbox.yml
modules:
dns_check:
prober: dns
timeout: 5s
dns:
query_name: "example.com"
query_type: "A"
valid_rcodes:
- NOERROR
validate_answer_rrs:
fail_if_not_matches_regexp:
- "example.com.\t.*\tIN\tA\t1.2.3.4"
# Алерт: DNS не возвращает ожидаемый IP
- alert: DNSRecordChanged
expr: probe_success{job="dns_check"} == 0
for: 2m
labels:
severity: critical
annotations:
summary: "DNS check failed for {{ $labels.instance }}"
DNSSEC валидация
def check_dnssec(domain: str) -> dict:
resolver = dns.resolver.Resolver()
resolver.use_dnssec = True
resolver.nameservers = ['8.8.8.8']
try:
# Запрос с DO bit (DNSSEC OK)
answers = resolver.resolve(domain, 'A', raise_on_no_answer=False)
# Проверить наличие RRSIG
try:
rrsig = resolver.resolve(domain, 'RRSIG')
has_rrsig = len(rrsig) > 0
except:
has_rrsig = False
return {
'dnssec_valid': True,
'has_rrsig': has_rrsig,
'domain': domain
}
except dns.dnssec.ValidationFailure as e:
return {
'dnssec_valid': False,
'error': str(e),
'domain': domain
}
Инструмент для ручной проверки: dig +dnssec example.com или https://dnsviz.net/.
Мониторинг срока истечения домена
import whois
def get_domain_expiry(domain: str) -> int:
"""Возвращает количество дней до истечения"""
w = whois.whois(domain)
expiry = w.expiration_date
if isinstance(expiry, list):
expiry = expiry[0]
days = (expiry.replace(tzinfo=None) - datetime.now()).days
return days
# Алерт при < 30 дней до истечения
WHOIS не всегда надёжен — некоторые регистраторы скрывают дату. Альтернатива: мониторинг через Domainr API или уведомления регистратора.
Инструменты
- DNSCheck.tools — веб-интерфейс для ручной проверки
- Pingdom — включает DNS мониторинг в базовый план
- Zabbix с DNS-шаблонами — для on-premise мониторинга
- AWS Route 53 Health Checks — мониторинг собственных DNS-записей
Сроки настройки
- Скрипт мониторинга изменений + cron — 1-2 дня
- Blackbox Exporter + Prometheus алерты — 1 день
- DNSSEC валидация — 0.5 дня
- Мониторинг истечения домена — 0.5 дня







