Delegation(委任)カテゴリで作成されたRoute 53 Resolver インバウンドエンドポイントは再帰的クエリを実行しません

Delegation(委任)カテゴリで作成されたRoute 53 Resolver インバウンドエンドポイントは再帰的クエリを実行しません

インバウンドエンドポイントをフルリゾルバとして利用したい場合はDefaultカテゴリを選択します。
Clock Icon2025.07.07

こんにちは、なおにしです。

Route 53 Resolver インバウンドエンドポイントの「Delegation」カテゴリについて確認する機会がありましたのでご紹介します。

はじめに

先日(2025/6/24)、Route 53 Resolver Endpointがプライベートホストゾーンの DNS 委任をサポートするようになりました。詳細は以下の記事およびアナウンスをご参照ください。

https://dev.classmethod.jp/articles/amazon-route-53-resolver-endpoints-dns-delegation-private-hosted-zones/

https://aws.amazon.com/jp/about-aws/whats-new/2025/06/amazon-route-53-resolver-endpoints-dns-delegation-private-hosted-zones/

プライベートホストゾーンのDNS委任がサポートされたことに伴い、追加された機能としては大きく分けると以下の2つになります。

Route 53 Resolver インバウンドエンドポイントのカテゴリに「Delegation」が追加

セルフマネージドDNSゾーン等から委任されたゾーンに対するDNS問い合わせに対して、プライベートホストゾーンに登録されているレコードに基づいて権威サーバとして応答できるようになります。
なお、現状ではエンドポイントのプロトコルとしてDo53のみがサポートされていることにはご注意ください。

20250707_naonishi_route53-resolver-inbound-endpoint-delegation-no-recursive-query_1.jpg

Route 53 Resolver アウトバウンドトラフィックのルールタイプに「Delegation」が追加

「Delegation」タイプで作成したルールを指定のVPCにアタッチすることで、当該VPCに紐づくプライベートホストゾーン に登録されている委任設定レコード(委任対象ドメインのNSレコードおよび必要に応じてそのグルーレコード)に基づき、対象となるDNS問い合わせをアウトバウンドエンドポイントを経由して外部のDNSサーバに転送することができるようになります。

20250707_naonishi_route53-resolver-inbound-endpoint-delegation-no-recursive-query_2.jpg

本記事では、前者のRoute 53 Resolver インバウンドエンドポイントのカテゴリにおける「Delegation」について少しだけ掘り下げます。

今回のアップデートに関して、エンドポイントカテゴリをDefaultにした場合とDelegationにした場合のそれぞれの挙動については、以下のドキュメントに処理の流れがまとめられています。

https://docs.aws.amazon.com/Route53/latest/DeveloperGuide/resolver-overview-forward-network-to-vpc.html

よく読むと、大きな差分としては以下の記述になります。

  • エンドポイントカテゴリDefaultの場合

      1. Resolver gets the applicable value for the domain name in the DNS query, either internally or by performing a recursive lookup against public name servers.

        (リゾルバーは、DNSクエリで指定されたドメイン名に対応する値を、内部的に取得するか、またはパブリックネームサーバーに対して再帰的クエリを実行することで取得します。)

  • エンドポイントカテゴリDelegationの場合

      1. Resolver returns the address to the AWS resource from the private hosted zone to the inbound endpoint.

        (リゾルバーは、プライベートホストゾーンからインバウンドエンドポイントに対して、AWSリソースのアドレスを返します。)

こうやって比べると、エンドポイントカテゴリDelegationの場合はパブリックネームサーバーに対して再帰的クエリを実行しないように受け取れるので、実際にどのような挙動になるのか確認してみます。

先に結論

  • エンドポイントカテゴリをDelegationに設定しているRoute 53 Resolver インバウンドエンドポイントは、対象のVPCに紐付いているプライベートホストゾーンで名前解決が可能なドメインのみ応答します
    • プライベートホストゾーンに登録されていないAWSリソースの名前解決や、その他のインターネット上のコンテンツの名前解決にもインバウンドエンドポイントを利用する場合(つまり、フルリゾルバとして利用したい場合)は、エンドポイントカテゴリをDefaultに設定する必要があります
    • プライベートホストゾーンで名前解決可能なドメインには、インターフェース VPC エンドポイントを作成し、プライベートDNS名を有効にしたAWSサービスが含まれます

やってみた

事前準備

以下の構成で検証します。

20250707_naonishi_route53-resolver-inbound-endpoint-delegation-no-recursive-query_3.png

BINDに登録しているゾーンファイルは以下のとおりです。

/var/named/parent.example.com.zone
$TTL 300
@       IN      SOA     ns1.parent.example.com. admin.parent.example.com. (
                        2024010101      ; Serial
                        3600            ; Refresh
                        1800            ; Retry
                        604800          ; Expire
                        300 )           ; Minimum TTL

; Name servers for parent zone
@       IN      NS      ns1.parent.example.com.
ns1     IN      A       10.0.1.10

; Delegation to child1 zone (VPC B)
child1  IN      NS      ns1.child1.parent.example.com.
child1  IN      NS      ns2.child1.parent.example.com.

; Glue records for child1 delegation (pointing to VPC B Resolver endpoints)
ns1.child1      IN      A       10.1.1.100
ns2.child1      IN      A       10.1.2.100

; Delegation to child2 zone (VPC C)
child2  IN      NS      ns1.child2.parent.example.com.
child2  IN      NS      ns2.child2.parent.example.com.

; Glue records for child2 delegation (pointing to VPC C Resolver endpoints)
ns1.child2      IN      A       10.2.1.100
ns2.child2      IN      A       10.2.2.100

BINDの設定ファイル(/etc/named.conf)については詳細を割愛しますが、転送設定(forwarders/forward)は適用していない状態です。

委任先のサーバとして応答できるかどうか

まず、VPC AのBINDがインストールされているEC2インスタンスで、委任したゾーン内の名前解決が可能か確認してみます。

エンドポイントカテゴリをDelegationに設定しているインバウンドエンドポイントの場合、以下のとおり問題なく応答がありました。

# dig vpcb-ec2.child1.parent.example.com @localhost

; <<>> DiG 9.18.33 <<>> vpcb-ec2.child1.parent.example.com @localhost
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 23078
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
; COOKIE: 6502a2fd3b3875c001000000686b9d2b8b5ff64b33015359 (good)
;; QUESTION SECTION:
;vpcb-ec2.child1.parent.example.com. IN A

;; ANSWER SECTION:
vpcb-ec2.child1.parent.example.com. 10 IN A     10.1.1.241

;; Query time: 1210 msec
;; SERVER: 127.0.0.1#53(localhost) (UDP)
;; WHEN: Mon Jul 07 10:10:51 UTC 2025
;; MSG SIZE  rcvd: 107

エンドポイントカテゴリをDefaultに設定しているインバウンドエンドポイントの場合、以下のとおり回答を得ることができませんでした。

# dig vpcc-ec2.child2.parent.example.com @localhost

; <<>> DiG 9.18.33 <<>> vpcc-ec2.child2.parent.example.com @localhost
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: SERVFAIL, id: 38169
;; flags: qr rd ra; QUERY: 1, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
; COOKIE: 1ae1b1a09e9fff6701000000686b9d4108389fa71a3b97ed (good)
;; QUESTION SECTION:
;vpcc-ec2.child2.parent.example.com. IN A

;; Query time: 1210 msec
;; SERVER: 127.0.0.1#53(localhost) (UDP)
;; WHEN: Mon Jul 07 10:11:13 UTC 2025
;; MSG SIZE  rcvd: 91

digに対する応答として、status: SERVFAILとなっている部分については以下のre:Postの記事に記載がある内容と一致します。(re:Postの回答は、本記事の執筆時点では2年前の更新となっていたので、エンドポイントカテゴリDelegationは存在していないタイミングの情報です)

https://repost.aws/ja/knowledge-center/route-53-fix-dns-resolution-private-zone

プライベートホストゾーンはゾーン委任をサポートしていません。委任が設定されている場合、クライアントは VPC リゾルバーから「Servfail」レスポンスコードを取得します。

BINDのログとしては以下のようなエラーが出力されました。

DNS format error from 10.2.1.100#53 resolving vpcc-ec2.child2.parent.example.com/A for 127.0.0.1#57629: server sent FORMERR
received FORMERR resolving 'vpcc-ec2.child2.parent.example.com/A/IN': 10.2.1.100#53
DNS format error from 10.2.1.100#53 resolving ns2.child2.parent.example.com/AAAA for <unknown>: server sent FORMERR
received FORMERR resolving 'ns2.child2.parent.example.com/AAAA/IN': 10.2.1.100#53

権威サーバとして応答しているかどうか

DNSにおける権威(オーソリティ)は以下のように定義されています。

https://jprs.jp/glossary/index.php?ID=0164

DNSにおいて、あるゾーンの管理権限を持っていることを表す言葉です。ルートゾーンを階層の頂点とし、親ゾーンから委任された権威サーバー(権威DNSサーバー)は、そのゾーンの完全な情報と子ゾーンへの委任情報を持ち、そのゾーンに対する「権威を持つ」と表現されます。

このため、それぞれのカテゴリのエンドポイントが権威サーバとしてDNS問い合わせに応答しているかどうかを確認してみます。

エンドポイントカテゴリをDelegationに設定しているインバウンドエンドポイントでは、以下のように応答があります。

$ dig vpcb-ec2.child1.parent.example.com @10.1.1.100 | grep flags
;; flags: qr aa rd; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1
; EDNS: version: 0, flags:; udp: 1232

エンドポイントカテゴリをDefaultに設定しているインバウンドエンドポイントでは、以下のように応答があります。

$ dig vpcc-ec2.child2.parent.example.com @10.2.1.100 | grep flags
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1
; EDNS: version: 0, flags:; udp: 1232

簡略のためにgrepで出力を制限していますが、着目する部分としてはエンドポイントカテゴリをDelegationに設定しているインバウンドエンドポイントではフラグに「aa ビット」が付与されていることです。

「aa ビット」が存在する場合、応答したネームサーバーは問い合わされたドメイン名に対する管理権限を持っていることを示します。つまり、エンドポイントカテゴリをDelegationに設定しているインバウンドエンドポイントは権威サーバとして応答しています。
一方で、エンドポイントカテゴリをDefaultに設定しているインバウンドエンドポイントは、紐付いているプライベートホストゾーンに対象レコードが存在するものの、非権威サーバ(キャッシュサーバ/フルリゾルバ)として応答しています。
DNSに関わる詳細については以下の資料もご参照ください。

https://jprs.jp/glossary/index.php?ID=0203

なお、委任先のサーバとして応答できるかどうかで確認したエラーメッセージに関しては、権威サーバからの応答ではないからFORMERR になっている、というわけではなく、純粋にエンドポイントカテゴリDefaultではゾーン委任をサポートしていない、という形で捉えていただければと思います。

AWSリソースの名前解決ができるかどうか(インターフェースエンドポイント無し)

インバウンドエンドポイントが紐付いているVPCと同じVPCに配置されているEC2インスタンスのDNS名を対象にクエリしてみます。

エンドポイントカテゴリをDefaultに設定しているインバウンドエンドポイントでは、以下のように問題なく名前解決できました。

# dig ip-10-2-1-166.ap-northeast-1.compute.internal @10.2.1.100

; <<>> DiG 9.18.33 <<>> ip-10-2-1-166.ap-northeast-1.compute.internal @10.2.1.100
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 26064
;; flags: qr rd ra; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
;; QUESTION SECTION:
;ip-10-2-1-166.ap-northeast-1.compute.internal. IN A

;; ANSWER SECTION:
ip-10-2-1-166.ap-northeast-1.compute.internal. 60 IN A 10.2.1.166

;; Query time: 0 msec
;; SERVER: 10.2.1.100#53(10.2.1.100) (UDP)
;; WHEN: Mon Jul 07 10:14:01 UTC 2025
;; MSG SIZE  rcvd: 90

エンドポイントカテゴリをDelegationに設定しているインバウンドエンドポイントでは、以下のとおり名前解決できませんでした。

# dig ip-10-1-1-241.ap-northeast-1.compute.internal @10.1.1.100

; <<>> DiG 9.18.33 <<>> ip-10-1-1-241.ap-northeast-1.compute.internal @10.1.1.100
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: REFUSED, id: 4864
;; flags: qr aa rd ad; QUERY: 0, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1
;; WARNING: recursion requested but not available

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
; COOKIE: 5d14f645f2e800b4 (echoed)
;; Query time: 0 msec
;; SERVER: 10.1.1.100#53(10.1.1.100) (UDP)
;; WHEN: Mon Jul 07 10:14:54 UTC 2025
;; MSG SIZE  rcvd: 35

まず、status: REFUSEDとなっているので、クエリを処理することが拒否されたことが分かります。また、WARNINGの内容からも再帰問い合わせが利用できないという応答があったことが分かります。

digコマンドはデフォルトの動作が再帰問い合わせなので、非再帰問い合わせで再実行した結果は以下のとおりです。

# dig ip-10-0-1-10.ap-northeast-1.compute.internal @10.1.1.100 +norecurse

; <<>> DiG 9.18.33 <<>> ip-10-0-1-10.ap-northeast-1.compute.internal @10.1.1.100 +norecurse
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: REFUSED, id: 51223
;; flags: qr aa ad; QUERY: 0, ANSWER: 0, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
; COOKIE: 49bccaf6b4a9448b (echoed)
;; Query time: 0 msec
;; SERVER: 10.1.1.100#53(10.1.1.100) (UDP)
;; WHEN: Fri Jul 04 10:15:15 UTC 2025
;; MSG SIZE  rcvd: 35

WARNINGの出力は無くなりましたがstatus: REFUSEDであることに変わりはなく、名前解決できませんでした。

AWSリソースの名前解決ができるかどうか(インターフェースエンドポイント有り)

そもそもインターフェースエンドポイントの有無で比較している背景・前提知識については、以下の記事をご参照ください。

https://dev.classmethod.jp/articles/s3-privatelink-diagram/

https://dev.classmethod.jp/articles/amazon-s3-private-connectivity-on-premises-networks/

https://dev.classmethod.jp/articles/route-53-launches-new-api-action-to-list-private-hosted-zones-associated-with-your-amazon-vpcs/

今回はVPC BにS3 インターフェースエンドポイントを設定しています。改めて各VPCに関連付けられているプライベートホストゾーンを確認してみます。

VPC Aについては、プライベートホストゾーンを作成していないので空で表示されます。

$ aws route53 list-hosted-zones-by-vpc \
--vpc-id vpc-00b66602df70fe27e \
--vpc-region ap-northeast-1
{
    "HostedZoneSummaries": [],
    "MaxItems": "100"
}

VPC BについてはS3 インターフェースエンドポイントを作成しているため、マネジメントコンソールから確認可能なプライベートホストゾーンだけではなく、"OwningService": "vpce.amazonaws.com"のプライベートホストゾーンが関連付いていることが分かります。

$ aws route53 list-hosted-zones-by-vpc \
--vpc-id vpc-0c0a8c0ac2f2d4d6f \
--vpc-region ap-northeast-1
{
    "HostedZoneSummaries": [
        {
            "HostedZoneId": "Z03731293TSIHRLZJX8H7",
            "Name": "s3-accesspoint.ap-northeast-1.amazonaws.com.",
            "Owner": {
                "OwningService": "vpce.amazonaws.com"
            }
        },
        {
            "HostedZoneId": "Z00288553KLFHH836TQUZ",
            "Name": "s3-control.ap-northeast-1.amazonaws.com.",
            "Owner": {
                "OwningService": "vpce.amazonaws.com"
            }
        },
        {
            "HostedZoneId": "Z002889913E1ENCK5B64O",
            "Name": "s3.ap-northeast-1.amazonaws.com.",
            "Owner": {
                "OwningService": "vpce.amazonaws.com"
            }
        },
        {
            "HostedZoneId": "Z00197611OGKEY18PV611",
            "Name": "child1.parent.example.com.",
            "Owner": {
                "OwningAccount": "123456789012"
            }
        }
    ],
    "MaxItems": "100"
}

VPC CについてはS3 インターフェースエンドポイントを作成していないため、マネジメントコンソールから確認可能なプライベートホストゾーンだけが関連付いていることが分かります。

$ aws route53 list-hosted-zones-by-vpc \
--vpc-id vpc-098ffd9ea2e042b96 \
--vpc-region ap-northeast-1
{
    "HostedZoneSummaries": [
        {
            "HostedZoneId": "Z03640631YHN610V85PT1",
            "Name": "child2.parent.example.com.",
            "Owner": {
                "OwningAccount": "123456789012"
            }
        }
    ],
    "MaxItems": "100"
}

つまり、インターフェースエンドポイントを作成してプライベートDNS 名を有効にしている環境であれば、対象のAWSリソースについてはプライベートホストゾーンで名前解決可能であるため、インバウンドエンドポイントのカテゴリがDelegationであっても応答できるかどうかを確認するという意図です。

まず、エンドポイントカテゴリをDefaultに設定しているインバウンドエンドポイントに対してS3バケットの名前解決を試してみます。

# dig (バケット名).s3.ap-northeast-1.amazonaws.com @10.2.1.100

; <<>> DiG 9.18.33 <<>> (バケット名).s3.ap-northeast-1.amazonaws.com @10.2.1.100
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 47041
;; flags: qr rd ra; QUERY: 1, ANSWER: 9, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
;; QUESTION SECTION:
;(バケット名).s3.ap-northeast-1.amazonaws.com. IN A

;; ANSWER SECTION:
(バケット名).s3.ap-northeast-1.amazonaws.com. 261 IN CNAME s3-r-w.ap-northeast-1.amazonaws.com.
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     3.5.154.44
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     52.219.172.54
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     52.219.199.186
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     3.5.158.160
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     3.5.157.122
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     52.219.199.18
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     3.5.156.229
s3-r-w.ap-northeast-1.amazonaws.com. 5 IN A     3.5.156.56

;; Query time: 0 msec
;; SERVER: 10.2.1.100#53(10.2.1.100) (UDP)
;; WHEN: Mon Jul 07 09:46:13 UTC 2025
;; MSG SIZE  rcvd: 227

再帰問い合わせによってS3バケットのグローバルIPアドレスが返ってきています。今回は割愛しますが、エンドポイントカテゴリをDefaultに設定しているインバウンドエンドポイントが紐付いているVPCでS3 インターフェースエンドポイントを作成してプライベートDNS 名を有効にすれば、インターフェースエンドポイントのプライベートIPアドレスが返ってくるようになります。

続いて、エンドポイントカテゴリをDelegationに設定しているインバウンドエンドポイントでも同様に確認してみます。

# dig (バケット名).s3.ap-northeast-1.amazonaws.com @10.1.1.100

; <<>> DiG 9.18.33 <<>> (バケット名).s3.ap-northeast-1.amazonaws.com @10.1.1.100
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 54592
;; flags: qr aa rd; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1
;; WARNING: recursion requested but not available

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
;; QUESTION SECTION:
;(バケット名).s3.ap-northeast-1.amazonaws.com. IN A

;; ANSWER SECTION:
(バケット名).s3.ap-northeast-1.amazonaws.com. 60 IN A 10.1.1.69

;; Query time: 0 msec
;; SERVER: 10.1.1.100#53(10.1.1.100) (UDP)
;; WHEN: Mon Jul 07 09:47:14 UTC 2025
;; MSG SIZE  rcvd: 94

インターフェースエンドポイントのプライベートIPアドレスの応答があり、名前解決可能でした。WARNINGが出力されていますが、以下のとおり明示的に非再帰問い合わせでクエリすれば表示されません。

# dig (バケット名).s3.ap-northeast-1.amazonaws.com @10.1.1.100 +norecurse

; <<>> DiG 9.18.33 <<>> (バケット名).s3.ap-northeast-1.amazonaws.com @10.1.1.100 +norecurse
;; global options: +cmd
;; Got answer:
;; ->>HEADER<<- opcode: QUERY, status: NOERROR, id: 11069
;; flags: qr aa; QUERY: 1, ANSWER: 1, AUTHORITY: 0, ADDITIONAL: 1

;; OPT PSEUDOSECTION:
; EDNS: version: 0, flags:; udp: 1232
;; QUESTION SECTION:
;(バケット名).s3.ap-northeast-1.amazonaws.com. IN A

;; ANSWER SECTION:
(バケット名).s3.ap-northeast-1.amazonaws.com. 60 IN A 10.1.1.69

;; Query time: 10 msec
;; SERVER: 10.1.1.100#53(10.1.1.100) (UDP)
;; WHEN: Mon Jul 07 10:03:14 UTC 2025
;; MSG SIZE  rcvd: 94

まとめ

Route 53 Resolver インバウンドエンドポイントの用途としては、オンプレミスのネットワークからプライベートホストゾーンに登録されているドメインの名前解決をしたいケースだけではなく、プライベートホストゾーンに登録されていないAWSリソースの名前解決や、インターネット上のコンテンツ(パブリックドメイン)を含む名前解決に活用されているケースもあるかと思います。

インバウンドエンドポイントを採用する場合は、ゾーン委任が必要なケースとそうではないケースのそれぞれで、今回追加されたDelegationカテゴリと従来のDefaultカテゴリを使い分けるように、設計時には気をつけたいと思いました。

本記事がどなたかのお役に立てれば幸いです。

Share this article

facebook logohatena logotwitter logo

© Classmethod, Inc. All rights reserved.