dns について
システム設計者向けに、DNSレコード、トラフィックルーティング、フェイルオーバーを検討するスキルです。遅延、地域、重み、ヘルス状態に応じた入口の選択と、TTLによる伝播・復旧時間を扱います。
主な機能
- 01DNSレコードタイプの選択
- 02重み・遅延・地理ルーティングの設定
- 03プライマリ・セカンダリのフェイルオーバー計画
- 04TTLとヘルスチェックの設定
- 05クエリ負荷と伝播時間の見積もり
活用シーン
- 01サービスの安定したホスト名の設定
- 02マルチリージョンのトラフィック入口設計
- 03リージョン障害後のDNS切り替え計画
インストール
コマンドをコピーしてターミナルで実行します。
npx skills add https:/ / github.com/ proyecto26/ system-design-skills --skill dnsインストール後、Claude Code で/dnsを入力して読み込まれたか確認します。
同梱ファイル
SKILL.md と一緒にインストールされる参考資料やスクリプト。
references/deep-dive.mdreferences/providers/aws.mdazure.mdgcp.mdgeneric.md詳細
DNS
DNS はグローバルな玄関口です。名前(api.example.com)をアドレスに変換する処理は、リクエストがサーバーに届く前に行われます。また、DNS はルーティングレイヤーでもあり、同じ検索でも、地域、レイテンシ、健全性、重みに応じて、クライアントごとに異なる応答を返せます。設定を誤ると、クライアントが停止中のリージョンに到達したり、フェイルオーバーに数秒ではなく数分かかったり、不適切な応答が数時間キャッシュされたりします。DNS はロードバランサーでも CDN でもありません。DNS が決めるのは、クライアントにどのエンドポイントを使うよう伝えるかであり、そのエンドポイント内でバイト列をどのように分散するかではありません。
これを選ぶ場面
安定したホスト名でサービスにアクセスできるようにする場合、最も近い、または最も健全なリージョン/データセンターへトラフィックを誘導する必要がある場合、あるいはエンドポイントの IP が変わる可能性があり(新しいロードバランサー、フェイルオーバーサイトなど)、コードを変更せずにクライアントを追従させる必要がある場合に使います。マルチリージョンやマルチデータセンターの設計では、DNS で接続先を選ぶ必要があります。シングルリージョンの設計でも、安定して変更可能な名前を用意するために必要です。
選ばない場面
1 つのリージョン内のルーティングには向きません。これはロードバランサーの役割(→ load-balancing)であり、TTL に縛られて数分かかるのではなく、ミリ秒単位で反応します。リクエストごと、またはセッションを考慮した細かな振り分けにも向きません。DNS は検索ごとに応答しますが、その後クライアントがキャッシュするためです。サブ秒で復旧する高速なフェイルオーバーにも向きません。DNS のフェイルオーバーは TTL とリゾルバーのキャッシュに左右されるため、名前のレイヤーで即時切り替えができるとは約束しないでください。また、ユーザーが複数リージョンに分散しているという数値が示される前に、複雑なルーティングポリシーを選ばないでください(YAGNI)。1 つのリージョンなら、単一の A/ALIAS レコードが適切なデフォルトです。
まず確認すること
- 地理的な分散 — 1 つのリージョンですか、それとも複数ですか?ユーザーはどこにいますか?(→
requirements-scoping) - フェイルオーバー先 — リージョンを失った場合の目標復旧時間は、数秒ですか、それとも「数分なら問題ありません」ですか?
- エンドポイントの動的な度合い — IP は固定ですか、それとも変更される LB のホスト名ですか?(
AとCNAME/ALIASの選択に影響します) - 誘導の目的 — レイテンシが最も低い接続先、ユーザーの地理的位置、重み(カナリア/A/B)、それとも単純なラウンドロビンのどれですか?
- マッピングの古さに対する許容度 — クライアントが古い応答を保持できる時間はどのくらいですか?(TTL を決めます →
back-of-the-envelope)
選択肢
レコードタイプ(名前が返すもの)
A/AAAA— 名前 → IPv4/IPv6。エンドポイントの IP が安定している場合に使います。CNAME— 名前 → 別の名前。プロバイダーのホスト名にエイリアスする場合に使います。ゾーン頂点(example.com)では使えません。ALIAS/ANAME(プロバイダー固有)— ゾーン頂点からホスト名へのエイリアス。example.comを LB/CDN のホスト名に向ける場合に使います。NS/MX/TXT— 委任、メール、検証に使います。ドメインの要件に応じて使うもので、トラフィックの振り分けには使いません。
ルーティングポリシー(クライアントが受け取る応答)
- Simple — 全員に 1 つの応答を返します。単一のエンドポイントに使います。
- Weighted — 割合に応じて振り分けます。カナリア、A/B、クラスター間の移行に使います。
- Latency-based — リゾルバーまでの測定レイテンシが最も低いリージョンを返します。ラウンドトリップを最小化する場合に使います。
- Geolocation/GeoDNS — クライアントの位置に応じて応答します(データレジデンシー、ローカライズされたコンテンツなど)。レイテンシではなく地理的位置で決める必要がある場合に使います。
- Failover — プライマリが健全な間はプライマリを返し、健全でなくなったらセカンダリを返します。アクティブ/パッシブ型の DR に使います。
- Multivalue — 健全な IP を複数返し、クライアントが選択します。健全性チェックによる除外を行いつつ、クライアント側で手軽に分散させる場合に使います。
到達性
- Anycast — 多数の拠点から同じ IP をアドバタイズし、ネットワークが最も近い拠点へルーティングします。リゾルバー/CDN のフロントエンドと DDoS 耐性に使います(概念については
content-deliveryを参照してください)。
トレードオフ
| オプション | 解決すること | 悪化すること | 切り替えるタイミング |
|---|---|---|---|
シンプルな A/ALIAS | 単純で、安定した名前を 1 つ使えます | 誘導もフェイルオーバーもできず、IP が停止すると単一障害点になります | トラフィックが複数のリージョンにまたがる、または DR が必要な場合 → 重み付け/レイテンシー/フェイルオーバー |
| 重み付け | 段階的な切り替え、カナリアリリース、クラスターの負荷分散 | 手動で時間がかかり、ヘルスチェックと組み合わせない限り正常性を認識しません | 自動で近い場所に誘導したい場合 → レイテンシーベース、自動で切り替えたい場合 → フェイルオーバー |
| レイテンシーベース | ユーザーごとに最小 RTT の接続先へ自動で誘導します | ユーザーではなく リゾルバー の場所に基づいてルーティングし、リージョンごとのエンドポイントが必要です | 速度よりデータレジデンシーが重要な場合 → ジオロケーション |
| ジオロケーション | コンプライアンス、地域に応じた応答 | VPN/フォワーディングリゾルバー経由で誤った場所に誘導され、地図の精度も粗いです | 地理的位置より速度が重要な場合 → レイテンシーベース |
| フェイルオーバー | アクティブ/パッシブ構成で自動的に切り替えます | 復旧時間は TTL とキャッシュに左右され、コールドスタンバイのリスクがあります | RTO を 1 秒未満にする必要がある場合 → DNS ではなくリージョン内の LB |
| Anycast | 最寄りの接続ポイントを提供し、DDoS を吸収します | 運用の負荷が高く(BGP)、経路変更時にフラップします | サイトが 1 つしかない場合 → 導入する価値はありません |
負荷時の挙動
DNS の障害は、広範囲にわたりゆっくりと影響します。不正な応答や権威サーバーの停止は、 次に名前を解決するすべてのユーザー に影響し、TTL が許す限りその影響が続きます。
- TTL キャッシュが復旧と伝播を遅らせます。 リゾルバーや OS/ブラウザーの キャッシュは TTL の間、応答を保持します。一部の ISP は過剰にキャッシュします。フェイルオーバーや IP の変更が 有効になるのは古いエントリーの期限が切れてからです。実効的な 復旧時間はゼロではなく、TTL に残存するキャッシュの時間を加えたものです。
- 権威 DNS が単一障害点になります。 権威サーバー(または単一の 管理対象ゾーン)が停止すると、サーバーが正常でも 何も 解決できません。 多数のサイトにまたがる Anycast を使用しているプロバイダーを選び、セカンダリー DNS プロバイダーの導入も検討してください。
- ヘルスチェックの集中/フラッピング。 多数のエンドポイントに対する積極的なヘルスチェックは
接続先に過大な負荷をかける可能性があり、チェックがフラップすると応答が頻繁に切り替わり、
クライアントが分散します。間隔、失敗しきい値を調整し、N 回連続で失敗した場合に限るよう設定してください(→
resilience-failureがヘルスチェックの調整を担当します)。 - 低 TTL による負荷。 高速なフェイルオーバーのために TTL を数秒に下げると、権威サーバーへの検索 QPS が 増大し、攻撃時にキャッシュによる緩衝効果がなくなります。
- リゾルバー層への DDoS。 DNS は典型的な増幅型 DDoS の標的です。リゾルバーが過負荷になると、サービス全体にアクセスできなくなります。
監視対象: 名前解決のレイテンシーとエラー/SERVFAIL 率、レコードごとのクエリ QPS、 エンドポイントごとのヘルスチェック状態、変更後の伝播時間、各リージョン/応答が実際に受け取るトラフィックの割合。
適用方法
- 入力を明確にする — 地理的な分散、リージョン喪失時の RTO、エンドポイントの安定性、振り分けの目的、マッピングの古さを確認します(最初に確認することを参照)。固定の入口を持つ単一リージョンなら、シンプルなレコードだけで十分です。そこで止めます。
- トレードオフ表からポリシーを選ぶ — レコードタイプ(アペックスで LB/CDN のホスト名を指す
ALIASが一般的な既定値)と、振り分けの目的に応じたルーティングポリシーを選びます。カナリアには加重、速度にはレイテンシー、データの保管場所の要件には地理、アクティブ/パッシブ DR にはフェイルオーバーを選びます。 - 主要な設定値を決める — TTL(迅速なフェイルオーバーとルックアップ負荷および伝播のバランス)、ヘルスチェックの間隔と失敗しきい値、フェイルオーバー先を設定します。セカンダリ DNS/エニーキャストの方針も事前に決めます。
- 選択をストレステストする — ストレス下での動作を確認します。TTL によって許容可能な実効復旧時間が得られること、権威 DNS 層が SPOF でないこと、ヘルスチェックが頻繁に状態変化を繰り返したり、リクエストが殺到したりしないことを確かめます。
- 数値を使って規模を見積もる — 選択した TTL でのルックアップ QPS と、変更によって生じる伝播時間を見積もります(→ 重要な数値)。
- プロバイダーを選ぶ — 既定では一般的なレシピを使い、ユーザーがクラウドを指定した場合にのみプロバイダーファイルを開きます(プロバイダーの選択を参照)。
- 回答でトレードオフを示す — ここで行った選択ごとに 1 行を設けた
決定 | 解決する問題 | 悪化する点 | 変更するタイミング…の表を提示します(例:オプション、ストア、障害時ポリシー)。最後の列には具体的なトリガー(数値または観測可能なシグナル)を記載します。その後、最初に何が壊れるかを示します。
推奨事項と避けるべきこと
推奨事項
- リージョン間の選択は DNS で振り分け、リージョン内の負荷分散は LB に任せます。
- アペックスで LB/CDN のホスト名を指す
ALIAS/ANAMEを使い、IP が変わってもレコードの編集が不要なようにします。 - ルーティングポリシーとヘルスチェックを組み合わせ、停止したリージョンが振り分け先にならないようにします。
- 多数のサイトにまたがるエニーキャストで権威 DNS を運用し、セカンダリプロバイダーも検討します。
- TTL は意図を持って設定します。RTO に間に合うほど短く、負荷に耐えられるほど長くします。
避けるべきこと
- DNS フェイルオーバーが即時に行われると期待しないでください。TTL とリゾルバーのキャッシュによって時間がかかります。
- ゾーンアペックスに
CNAMEを設定しないでください。無効なため、ALIAS/ANAMEを使います。 - セキュリティや厳密な配置にジオロケーションを頼らないでください(VPN やフォワーダーによって位置情報が不正確になることがあります)。
- それ以外はマルチリージョン構成なのに、権威 DNS ゾーンを 1 つだけ運用して SPOF にしないでください。
- 「念のため」と TTL をどこでも数秒に設定しないでください。クエリ負荷が増大します。
重要な数値
見積もる量は、伝播時間と実効フェイルオーバー時間の両方を左右するTTL(TTL が 60 秒なら、即時ではなく最大で約 60 秒以上の古さが残ることがあります)、TTL によって権威サーバーに発生するルックアップ QPS(TTL が短いほどクエリ数が増加)、そして名前解決のレイテンシー予算(追加のラウンドトリップが 1 回発生しますが、大部分はキャッシュによって隠されます)です。これらは、back-of-the-envelopeの経験則とピーク倍率の計算を使って判断します。ここの表を繰り返し記載しないでください。
インターフェースの概要
DNS レコードは契約です。名前(api.example.com)、タイプ(A/AAAA/CNAME/ALIAS)、値(IP またはターゲットホスト名)、TTL(秒)、および任意のルーティングポリシー+ヘルスチェックで構成されます。ゾーンファイルの行の例:
api.example.com. 60 IN A 203.0.113.10 ; latency-policy, region us-east, health-check id hc-1
レコードごとに、どのポリシーで選択するか、どのヘルスチェックで制御するか、古さの上限を定める TTL を決めます。
プロバイダーの選択
既定では上記の一般的なレシピを使います。ユーザーがクラウドを指定した場合は、マネージドサービスへの対応付け、クォータ/制限、プロバイダー固有のトレードオフについて、references/providers/<provider>.mdを参照します。そのプロバイダーのファイルが存在しない場合は、一般的なレシピを回答として使います。
図
名前解決の経路(クライアント → 再帰リゾルバー → ルート/TLD/権威 DNS → 応答)や、地理/レイテンシーに基づいて振り分けるマルチリージョンのフロントドアを図示するには、プラグイン内のarchitecture-diagramスキルを使います。簡単なインライン図:
クライアント → リゾルバー → 権威 DNS(ポリシー:レイテンシー)→ リージョン A | リージョン B。
関連する構成要素
load-balancing— これを補完します。DNS はリージョン/エンドポイント間でトラフィックを分散し、ロードバランサーはリージョン内でリクエストを分散して、ミリ秒単位で対応します。content-delivery— これと組み合わせて使います。CDN はエニーキャストと DNS を使ってユーザーをエッジ POP にルーティングし、エニーキャスト/エッジキャッシュの概念はそちらで扱われます。resilience-failure— これにつながります。ヘルスチェックの調整、フェイルオーバー、縮退パターン(およびレート制限)はそちらで扱われ、DNS フェイルオーバーの前提となります。back-of-the-envelope— これにつながります。レコードセットと伝播時間枠の規模を決めるための TTL/QPS/レイテンシの計算を提供します。system-design— オーケストレーターで扱われる概念です。推論ループ、トレードオフの手法、10 個の障害モードが含まれます。
参考資料
references/deep-dive.md— 名前解決の階層(再帰問い合わせと権威問い合わせ、ルート/TLD)、すべてのレコードタイプ、TTL/伝播の実際の動作、エニーキャストの仕組み、ヘルスチェック付きフェイルオーバーの内部構造を説明します。DNS レイヤーを詳細に設計する際に参照してください。references/providers/{generic,aws,azure,gcp}.md— 環境ごとのサービス対応、制限事項、注意点。