Sau bài này bạn làm được: dùng dig đọc bản ghi DNS; giải thích tại sao “đổi DNS xong nhưng user vẫn vào trang cũ”; biết DNS của Kubernetes hoạt động khác DNS internet như thế nào.
DNS là gì và tại sao cần thiết
Máy tính liên lạc qua IP. Con người nhớ tên. DNS là hệ thống dịch thuật: api.example.com → 93.184.216.34.
Mọi request HTTP, SSH, hay bất kỳ kết nối TCP/UDP nào đều bắt đầu bằng một truy vấn DNS — trừ khi bạn gõ thẳng IP.
Các loại bản ghi DNS hay gặp
| Loại | Ý nghĩa | Ví dụ |
|---|---|---|
| A | Tên → IPv4 | api.example.com → 93.184.216.34 |
| AAAA | Tên → IPv6 | api.example.com → 2606:2800::1 |
| CNAME | Tên → tên khác (alias) | www.example.com → example.com |
| TXT | Chuỗi văn bản tùy ý | SPF, DKIM, ACME challenge |
| MX | Mail server | example.com → mail.example.com |
| NS | Máy chủ DNS có thẩm quyền | example.com → ns1.provider.com |
| PTR | IP → tên (reverse DNS) | 34.216.184.93.in-addr.arpa → … |
CNAME chain: www → cdn.example.net → 1.2.3.4 — resolver giải từng bước cho đến A/AAAA cuối.
TTL — bao lâu thì cache hết hạn
TTL (Time To Live) là số giây resolver được phép giữ kết quả trong cache:
dig +short A api.example.com
93.184.216.34
dig +noall +answer A api.example.com
api.example.com. 300 IN A 93.184.216.34
^^^
300 giây = 5 phút (cột thứ 2 là TTL)
+noall +answer in đúng phần ANSWER SECTION — nơi có TTL; tránh noise từ ;; QUESTION và các block khác.
Tác động với DevOps:
- TTL dài (86400s = 1 ngày): đổi IP xong, một số user vẫn trỏ IP cũ trong ~24h.
- TTL ngắn (60–300s): thay đổi lan nhanh, nhưng tăng tải DNS.
- Chiến thuật: hạ TTL xuống 60–300s trước khi migration vài tiếng/ngày, sau migration nâng lại.
Resolver chain — ai hỏi ai
[App / curl]
│ gọi getaddrinfo()
▼
[Stub resolver (OS)]
│ cache? → trả luôn
│ không có cache
▼
[Recursive resolver (8.8.8.8 / 1.1.1.1 / resolver công ty)]
│ cache? → trả luôn
│ không có cache → hỏi tiếp
▼
[Root nameserver] → "example.com do .com TLD quản lý"
▼
[TLD nameserver .com] → "example.com do ns1.provider.com quản lý"
▼
[Authoritative nameserver ns1.provider.com]
└─ trả bản ghi A/AAAA/CNAME thực sự
Split-horizon DNS: bên trong công ty, api.example.com có thể trả IP private; từ internet trả IP public. Hai kết quả khác nhau cho cùng tên — gây nhầm khi test từ máy dev.
Lệnh dig thực dụng
# Tra bản ghi A (IPv4)
dig +short A api.example.com
# Tra CNAME
dig +short CNAME www.example.com
# Xem TTL còn lại
dig A api.example.com
# Dùng resolver cụ thể (bypass /etc/resolv.conf)
dig @8.8.8.8 +short A api.example.com
# Trace từ root (debug delegation)
dig +trace api.example.com
# Reverse DNS (IP → tên)
dig -x 93.184.216.34 +short
DNS mã hoá: DoH và DoT
Truyền thống DNS dùng UDP/53 không mã hoá — ISP, mạng công cộng và MITM có thể đọc/thay đổi. Hai giao thức mã hoá đã phổ cập:
| Tên | Cổng | Transport | Đặc điểm |
|---|---|---|---|
| DoT (DNS over TLS) | 853/TCP | TLS | Dễ phát hiện và chặn (port riêng); OS/router hỗ trợ |
| DoH (DNS over HTTPS) | 443/TCP | HTTPS | Lẫn với traffic HTTPS thường; trình duyệt dùng nhiều |
Kiểm tra nhanh bằng kdig (gói knot-dnsutils) hoặc dig mới (9.18+):
# DoT
kdig @1.1.1.1 +tls api.example.com
# DoH
kdig @https://cloudflare-dns.com/dns-query api.example.com
Góc vận hành: DoH/DoT client-side bypass resolver công ty — security team thường muốn chặn DoH (danh sách IP/DoH endpoint) hoặc ép tất cả qua resolver có policy. Biết tồn tại để đoán đúng nguồn lỗi “DNS không đi qua split-horizon”.
mDNS và LLMNR — rủi ro trong LAN
mDNS (.local, UDP/5353) và LLMNR (UDP/5355) là các giao thức tự phân giải tên trong LAN không cần DNS server — dùng nhiều trong IoT, in mạng, Bonjour/Avahi.
Rủi ro: bất kỳ máy nào trong LAN có thể trả lời query mDNS/LLMNR → dễ spoof (tấn công Responder nổi tiếng trong pentest Windows domain). Khuyến nghị:
- Tắt LLMNR trên host máy chủ nếu không cần (Group Policy Windows / systemd-resolved).
- Phân tách VLAN IoT ra khỏi máy chủ quan trọng.
- Không dựa vào
.localcho service nội bộ production; đặt zone.internalriêng qua DNS authoritative.
DNSSEC — ký bảo đảm bản ghi
DNSSEC thêm chữ ký vào bản ghi để resolver xác minh không bị giả mạo trên đường đi:
# Kiểm tra zone có ký DNSSEC chưa
dig +dnssec DNSKEY example.com
# ad flag trong answer header: resolver đã validate thành công
dig example.com
# ;; flags: qr rd ra ad; ← "ad" = Authenticated Data
Thực tế 2025:
- Gốc
.và hầu hết TLD đã ký từ lâu. - Nhưng phần lớn zone người dùng vẫn không ký (ước ~20–30% tuỳ thống kê) — chi phí vận hành không nhỏ nếu rotate KSK sai.
- Resolver phổ biến (1.1.1.1, 8.8.8.8, quad9) bật validation; lỗi ký →
SERVFAIL. - Khi triển khai: bắt đầu với automated DNSSEC của provider (Route 53, Cloudflare) thay vì tự quản BIND.
Lỗi DNS thường gặp
| Lỗi | Nguyên nhân | Kiểm tra |
|---|---|---|
| NXDOMAIN | Tên không tồn tại (typo, zone chưa tạo) | dig +short A tên-nghi-ngờ |
| SERVFAIL | Nameserver lỗi, DNSSEC fail, timeout upstream | dig +short A tên @resolver-khác |
| Timeout | Resolver không trả lời (firewall UDP 53) | nc -uvz resolver-ip 53 |
| Cache cũ | TTL chưa hết dù đã đổi bản ghi | So sánh dig @authoritative vs dig @resolver |
DNS trong Kubernetes
Trong cluster, CoreDNS đóng vai resolver. Mỗi Pod có /etc/resolv.conf trỏ tới ClusterIP của CoreDNS:
nameserver 10.96.0.10
search default.svc.cluster.local svc.cluster.local cluster.local
options ndots:5
my-service→ CoreDNS tìmmy-service.default.svc.cluster.local→ ClusterIP của Service.ndots:5: nếu tên có ít hơn 5 dấu chấm, resolver thêm suffix search trước khi query public — có thể làm chậm DNS lookup external.
Debug trong Pod:
kubectl exec -it my-pod -- nslookup my-service
kubectl exec -it my-pod -- dig +short A my-service.default.svc.cluster.local
Tóm tắt
- DNS là bước đầu tiên mọi kết nối phải qua — lỗi DNS nghĩa là không ai vào được.
- TTL quyết định tốc độ lan truyền thay đổi; điều chỉnh trước migration.
digvới+short,+trace,@resolver-cụ-thểlà bộ công cụ debug cơ bản.- Kubernetes có DNS riêng (CoreDNS) — test
nslookuptrong Pod, không phải trên node.
Câu hỏi hay gặp
Đổi A record rồi mà nhiều user vẫn trỏ IP cũ — vì sao? Làm sao lần sau đỡ hơn?
Trả lời: TTL và cache ở resolver trung gian, OS, trình duyệt. Giảm TTL trước khi cutover (vài giờ đến vài ngày tùy TTL cũ), rồi đổi bản ghi; sau ổn định có thể tăng TTL lại.
dig không ra IP nhưng curl http://my-api vẫn chạy trong Pod — giải thích?
Trả lời: Tên có thể resolve qua search domain của Pod (my-api.default.svc.cluster.local), hoặc CoreDNS trả về trong khi dig không khớp query (thiếu FQDN / sai namespace). Kiểm tra /etc/resolv.conf và thử nslookup / dig đúng FQDN.
SERVFAIL từ 8.8.8.8 nhưng OK từ resolver công ty — hay gặp vì đâu?
Trả lời: Thường là DNSSEC validation fail, lỗi zone/NS chỉ lộ với một đường đi, hoặc split-horizon (public vs internal khác nhau). So sánh dig +trace và query authoritative trực tiếp.
Bài tiếp theo (Giai đoạn II): HTTP, HTTPS và HTTP/2, HTTP/3 — sau khi DNS và TCP ổn, đây là nơi request thực sự “nói chuyện”.