コンセプト

Edit This Page

ServiceとPodに対するDNS

このページではKubernetesによるDNSサポートについて概観します。

イントロダクション

KubernetesのDNSはクラスター上でDNS PodとServiceをスケジュールし、DNSの名前解決をするために各コンテナに対してDNS ServiceのIPを使うようにKubeletを設定します。

何がDNS名を取得するか

クラスター内(DNSサーバーそれ自体も含む)で定義された全てのServiceはDNS名を割り当てられます。デフォルトでは、クライアントPodのDNSサーチリストはPod自身のネームスペースと、クラスターのデフォルトドメインを含みます。
下記の例でこの仕組みを説明します。

Kubernetesのbarというネームスペース内でfooという名前のServiceがあると仮定します。barネームスペース内で稼働しているPodは、fooに対してDNSクエリを実行するだけでこのServiceを探すことができます。barとは別のquuxネームスペース内で稼働しているPodは、foo.barに対してDNSクエリを実行するだけでこのServiceを探すことができます。

下記のセクションでは、サポートされているレコードタイプとレイアウトについて詳しくまとめています。 うまく機能する他のレイアウト、名前、またはクエリーは、実装の詳細を考慮し、警告なしに変更されることがあります。
最新の仕様に関する詳細は、KubernetesにおけるDNSベースのServiceディスカバリを参照ください。

Service

Aレコード

“通常の”(Headlessでない)Serviceは、my-svc.my-namespace.svc.cluster.localという形式のDNS Aレコードを割り当てられます。このAレコードはそのServiceのClusterIPへと名前解決されます。

“Headless”(ClusterIPなしの)Serviceもまたmy-svc.my-namespace.svc.cluster.localという形式のDNS Aレコードを割り当てられます。通常のServiceとは異なり、このAレコードはServiceによって選択されたPodのIPの一覧へと名前解決されます。クライアントはこの一覧のIPを使うか、その一覧から標準のラウンドロビン方式によって選択されたIPを使います…

SRVレコード

SRVレコードは、通常のServiceもしくはHeadless Servicesの一部である名前付きポート向けに作成されます。それぞれの名前付きポートに対して、そのSRVレコードは_my-port-name._my-port-protocol.my-svc.my-namespace.svc.cluster.localという形式となります。
通常のServiceに対しては、このSRVレコードはmy-svc.my-namespace.svc.cluster.localという形式のドメイン名とポート番号へ名前解決します。
Headless Serviceに対しては、このSRVレコードは複数の結果を返します。それはServiceの背後にある各Podの1つを返すのと、auto-generated-name.my-svc.my-namespace.svc.cluster.localという形式のPodのドメイン名とポート番号を含んだ結果を返します。

Pod

Aレコード

DNSが有効なとき、Podは”pod-ip-address.my-namespace.pod.cluster.local“という形式のAレコードを割り当てられます。

例えば、defaultネームスペース内でcluster.localというDNS名を持ち、1.2.3.4というIPを持ったPodは次の形式のエントリーを持ちます。: 1-2-3-4.default.pod.cluster.local

Podのhostnameとsubdomainフィールド

現在、Podが作成されたとき、そのPodのホスト名はPodのmetadata.nameフィールドの値となります。

Pod Specは、オプションであるhostnameフィールドを持ち、Podのホスト名を指定するために使うことができます。hostnameが指定されたとき、hostnameはそのPodの名前よりも優先されます。例えば、hostnameフィールドが”my-host“にセットされたPodを考えると、Podはそのhostnameが”my-host“に設定されます。

Pod Specはまた、オプションであるsubdomainフィールドも持ち、Podのサブドメイン名を指定するために使うことができます。例えば、”my-namespace“というネームスペース内でhostnamefooとセットされていて、subdomainbarとセットされているPodの場合、そのPodは”foo.bar.my-namespace.svc.cluster.local“という名前の完全修飾ドメイン名(FQDN)を持つことになります。

例:

apiVersion: v1
kind: Service
metadata:
  name: default-subdomain
spec:
  selector:
    name: busybox
  clusterIP: None
  ports:
  - name: foo # 実際は、portは必要ありません。
    port: 1234
    targetPort: 1234
---
apiVersion: v1
kind: Pod
metadata:
  name: busybox1
  labels:
    name: busybox
spec:
  hostname: busybox-1
  subdomain: default-subdomain
  containers:
  - image: busybox:1.28
    command:
      - sleep
      - "3600"
    name: busybox
---
apiVersion: v1
kind: Pod
metadata:
  name: busybox2
  labels:
    name: busybox
spec:
  hostname: busybox-2
  subdomain: default-subdomain
  containers:
  - image: busybox:1.28
    command:
      - sleep
      - "3600"
    name: busybox

もしそのPodと同じネームスペース内で、同じサブドメインを持ったHeadless Serviceが存在していた場合、クラスターのKubeDNSサーバーもまた、そのPodの完全修飾ドメイン名(FQDN)に対するAレコードを返します。 例えば、”busybox-1“というホスト名で、”default-subdomain“というサブドメインを持ったPodと、そのPodと同じネームスペース内にある”default-subdomain“という名前のHeadless Serviceがあると考えると、そのPodは自身の完全修飾ドメイン名(FQDN)を”busybox-1.default-subdomain.my-namespace.svc.cluster.local“として扱います。DNSはそのPodのIPを指し示すAレコードを返します。”busybox1“と”busybox2“の両方のPodはそれぞれ独立したAレコードを持ちます。

そのエンドポイントオブジェクトはそのIPに加えてhostnameを任意のエンドポイントアドレスに対して指定できます。

備考: AレコードはPodの名前に対して作成されないため、hostnameはPodのAレコードが作成されるために必須となります。hostnameを持たないがsubdomainを持つようなPodは、そのPodのIPアドレスを指し示すHeadless Service(default-subdomain.my-namespace.svc.cluster.local)に対するAレコードのみ作成します。

PodのDNSポリシー

DNSポリシーはPod毎に設定できます。現在のKubernetesでは次のようなPod固有のDNSポリシーをサポートしています。これらのポリシーはPod SpecのdnsPolicyフィールドで指定されます。

備考: “Default”は、デフォルトのDNSポリシーではありません。もしdnsPolicyが明示的に指定されていない場合、”ClusterFirst”が使用されます。

下記の例では、hostNetworkフィールドがtrueにセットされているため、dnsPolicyが”ClusterFirstWithHostNet“とセットされているPodを示します。

apiVersion: v1
kind: Pod
metadata:
  name: busybox
  namespace: default
spec:
  containers:
  - image: busybox:1.28
    command:
      - sleep
      - "3600"
    imagePullPolicy: IfNotPresent
    name: busybox
  restartPolicy: Always
  hostNetwork: true
  dnsPolicy: ClusterFirstWithHostNet

PodのDNS設定

PodのDNS設定は、ユーザーがPodに対してそのDNS設定上でさらに制御するための手段を提供します。

dnsConfigフィールドはオプションで、どのような設定のdnsPolicyでも共に機能することができます。しかし、PodのdnsPolicyが”None“にセットされていたとき、dnsConfigフィールドは必ず指定されなくてはなりません。

下記の項目は、ユーザーがdnsConfigフィールドに指定可能なプロパティーとなります。

下記のファイルはカスタムDNS設定を持ったPodの例です。

service/networking/custom-dns.yaml
apiVersion: v1
kind: Pod
metadata:
  namespace: default
  name: dns-example
spec:
  containers:
    - name: test
      image: nginx
  dnsPolicy: "None"
  dnsConfig:
    nameservers:
      - 1.2.3.4
    searches:
      - ns1.svc.cluster.local
      - my.dns.search.suffix
    options:
      - name: ndots
        value: "2"
      - name: edns0

上記のPodが作成されたとき、testコンテナは、コンテナ内の/etc/resolv.confファイル内にある下記の内容を取得します。

nameserver 1.2.3.4
search ns1.svc.cluster.local my.dns.search.suffix
options ndots:2 edns0

IPv6用のセットアップのためには、サーチパスとname serverは下記のようにセットアップするべきです。

$ kubectl exec -it dns-example -- cat /etc/resolv.conf
nameserver fd00:79:30::a
search default.svc.cluster.local svc.cluster.local cluster.local
options ndots:5

DNS機能を利用可用なバージョン

PodのDNS設定と”None“というDNSポリシーの利用可能なバージョンに関しては下記の通りです。

k8s versionFeature support
1.14ステーブル
1.10β版 (デフォルトで有効)
1.9α版

次の項目

DNS設定の管理方法に関しては、DNS Serviceの設定 を確認してください。

フィードバック