KubernetesクラスタのDNSサーバーの構成
Kubernetes Engine (OKE)を使用して作成したKubernetesクラスタ用にDNSサーバーを構成する方法をご紹介します。
組込みDNSサーバー(kube-dns、CoreDNS)の構成
Kubernetes Engineによって作成されるクラスタには、自動的に起動される組込みKubernetesサービスとしてDNSサーバーが含まれます。各ワーカー・ノードのkubeletプロセスは、個々のコンテナをDNSサーバーに向け、DNS名をIPアドレスに変換します。
Kubernetesバージョン1.14より前のKubernetes Engineは、kube-dnsをDNSサーバーとしてクラスタを作成しました。ただし、Kubernetesバージョン1.14以降では、Kubernetes EngineはDNSサーバーとしてCoreDNSを使用してクラスタを作成します。CoreDNSは、モジュール式でプラガブルな汎用の認可DNSサーバーです。
CoreDNSのデフォルトの動作は、Corefileと呼ばれる構成ファイルによって制御されます。Corefileは、CoreDNSの動作を定義するCorefileセクションを持つKubernetes ConfigMapです。Corefileを直接変更することはできません。CoreDNSの動作をカスタマイズする必要がある場合は、独自のConfigMapを作成して適用し、Corefileの設定をオーバーライドします(このトピックで説明します)。基本的なクラスタでは、CoreDNSのデフォルト動作をカスタマイズする場合、カスタマイズはクラスタへの内部更新中に定期的に削除されることに注意してください(拡張クラスタでは、カスタマイズは削除されません)。
Kubernetes Engineによって作成されたクラスタを以前のバージョンからKubernetes 1.14以降にアップグレードすると、クラスタのkube-dnsサーバーは自動的にCoreDNSサーバーに置換されます。元のkube-dns ConfigMapを使用してkube-dnsの動作をカスタマイズした場合、それらのカスタマイズはCoreDNS ConfigMapに引き継がれないことに注意してください。CoreDNS Corefileの設定をオーバーライドするには、カスタマイズを含む新しいConfigMapを作成して適用する必要があります。
CoreDNSのカスタマイズおよびKubernetesの詳細は、KubernetesのドキュメントおよびCoreDNSのドキュメントを参照してください。
CoreDNS Corefileの設定をオーバーライドするConfigMapを作成するには:
-
yamlファイルに次の形式でConfigMapを定義します:
apiVersion: v1 kind: ConfigMap metadata: name: coredns-custom namespace: kube-system data: <customization-options>
例:
apiVersion: v1 kind: ConfigMap metadata: name: coredns-custom namespace: kube-system data: example.server: | # All custom server files must have a ".server" file extension. # Change example.com to the domain you wish to forward. example.com { # Change 1.1.1.1 to your customer DNS resolver. forward . 1.1.1.1 }
CoreDNSの動作のカスタマイズに使用するConfigMapオプションの詳細は、KubernetesのドキュメントおよびCoreDNSのドキュメントを参照してください。
-
次のように入力してConfigMapを作成します:
kubectl apply -f <filename>.yaml
-
次のように入力して、カスタマイズが適用されたことを確認します:
kubectl get configmaps --namespace=kube-system coredns-custom -o yaml
-
次のように入力して、CoreDNSでConfigMapを強制的にリロードします:
kubectl delete pod --namespace kube-system -l k8s-app=kube-dns
Oracle Cloud Infrastructure DNSを使用するためのExternalDNSの構成
ExternalDNSは、Kubernetesの外部にあるDNSプロバイダにサービスのDNSレコードを作成できるKubernetesのアドオンです。外部DNSプロバイダでDNSレコードを設定して、そのDNSプロバイダを介してKubernetesサービスを検出可能にし、DNSレコードを動的に制御できるようにします。詳細は、ExternalDNSを参照してください。
ExternalDNSをクラスタにデプロイした後、external-dns.alpha.kubernetes.io/hostname
注釈をサービスに追加することで、クラスタで実行されているサービスを公開できます。ExternalDNSは、クラスタ用に構成した外部DNSプロバイダにサービスのDNSレコードを作成します。
ExternalDNS自体は、CoreDNSのようなDNSサーバーではなく、他の外部DNSプロバイダを構成する方法です。Oracle Cloud Infrastructure DNSは、そのような外部DNSプロバイダの一種です。DNSの概要を参照してください。
便宜上、クラスタにExternalDNSを設定し、Oracle Cloud Infrastructure DNSを使用するように構成する手順を次に示します。これらの手順は、GitHubで入手可能なSetting up ExternalDNS for Oracle Cloud Infrastructure (OCI) tutorialに基づいたサマリーです。
クラスタでExternalDNSを設定し、Oracle Cloud Infrastructure DNSを使用するように構成するには:
- Oracle Cloud Infrastructure DNSに新しいDNSゾーンを作成して、ExternalDNSがクラスタ用に作成するDNSレコードを含めます。「ゾーンの作成」を参照してください。
-
まだ実行していない場合は、ステップに従って、クラスタのkubeconfig構成ファイルを設定し、(必要に応じて)そのファイルを指すようにKUBECONFIG環境変数を設定します。自分のkubeconfigファイルを設定する必要があります。別のユーザーが設定したkubeconfigファイルを使用してクラスタにアクセスすることはできません。クラスタ・アクセスの設定を参照してください。
- 作成したDNSゾーンにDNSレコードを挿入および更新するためにOracle Cloud Infrastructure APIに接続する際に使用する、ExternalDNSのOracle Cloud Infrastructureユーザー認証の詳細を含むKubernetesシークレットを作成します。
-
テキスト・エディタで、DNSゾーンへのアクセスに使用するOracle Cloud Infrastructureユーザー資格証明を含む資格証明ファイルを作成します:
auth: region: <region-identifier> tenancy: <tenancy-ocid> user: <user-ocid> key: | -----BEGIN RSA PRIVATE KEY----- <private-key> -----END RSA PRIVATE KEY----- fingerprint: <fingerprint> # Omit if there is not a password for the key passphrase: <passphrase> compartment: <compartment-ocid>
ここでは:
<region-identifer>
は、ユーザーのリージョンを識別します。たとえば、us-phoenix-1
です<tenancy-ocid>
は、ユーザーのテナンシのOCIDです。たとえば、ocid1.tenancy.oc1..aaaaaaaap...keq
です(読みやすさのために省略しています)。<user-ocid>
は、ユーザーのOCIDです。たとえば、ocid1.user.oc1..aaaaa...zutq
(読みやすさのために省略)です。<private-key>
はRSAキーで、-----BEGIN RSA PRIVATE KEY-----
で始まり、-----END RSA PRIVATE KEY-----
で終わりますpassphrase: <passphrase>
はオプションで、キーのパスフレーズを指定します(存在する場合)<compartment-ocid>
は、DNSゾーンが属するコンパートメントのOCIDです
例:auth: region: us-phoenix-1 tenancy: ocid1.tenancy.oc1..aaaaaaaap...keq user: ocid1.user.oc1..aaaaa...zutq key: | -----BEGIN RSA PRIVATE KEY----- this-is-not-a-secret_Ef8aiAk7+I0... -----END RSA PRIVATE KEY----- fingerprint: bg:92:82:9f... # Omit if there is not a password for the key passphrase: Uy2kSl... compartment: ocid1.compartment.oc1..aaaaaaaa7______ysq
- 選択した名前で資格証明ファイルを保存します(例:
oci-creds.yaml
)。 - 次のように入力して、作成した資格証明ファイルからKubernetesシークレットを作成します:
kubectl create secret generic <secret-name> --from-file=<credential-filename>
例:
kubectl create secret generic external-dns-config --from-file=oci-creds.yaml
-
- クラスタにExternalDNSをデプロイします。
- テキスト・エディタで、構成ファイル(
external-dns-deployment.yaml
など)を作成してExternalDNSデプロイメントを作成し、先ほど作成したKubernetesシークレットの名前を指定します。例:apiVersion: v1 kind: ServiceAccount metadata: name: external-dns --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRole metadata: name: external-dns rules: - apiGroups: [""] resources: ["services","endpoints","pods"] verbs: ["get","watch","list"] - apiGroups: ["extensions","networking.k8s.io"] resources: ["ingresses"] verbs: ["get","watch","list"] - apiGroups: [""] resources: ["nodes"] verbs: ["list"] --- apiVersion: rbac.authorization.k8s.io/v1 kind: ClusterRoleBinding metadata: name: external-dns-viewer roleRef: apiGroup: rbac.authorization.k8s.io kind: ClusterRole name: external-dns subjects: - kind: ServiceAccount name: external-dns namespace: default --- apiVersion: apps/v1 kind: Deployment metadata: name: external-dns spec: strategy: type: Recreate selector: matchLabels: app: external-dns template: metadata: labels: app: external-dns spec: serviceAccountName: external-dns containers: - name: external-dns image: k8s.gcr.io/external-dns/external-dns:v0.7.3 args: - --source=service - --source=ingress - --provider=oci - --policy=upsert-only # prevent ExternalDNS from deleting any records, omit to enable full synchronization - --txt-owner-id=my-identifier volumeMounts: - name: config mountPath: /etc/kubernetes/ volumes: - name: config secret: secretName: external-dns-config
- 構成ファイルを保存して閉じます。
- 次のように入力して、構成ファイルを適用し、ExternalDNSをデプロイします:
kubectl apply -f <filename>
<filename>
は、以前に作成したファイルの名前です。例:kubectl apply -f external-dns-deployment.yaml
前述のコマンドの出力により、デプロイメントが確認されます:
serviceaccount/external-dns created clusterrole.rbac.authorization.k8s.io/external-dns created clusterrolebinding.rbac.authorization.k8s.io/external-dns-viewer created deployment.apps/external-dns created
- テキスト・エディタで、構成ファイル(
- ExternalDNSが正常にデプロイされ、nginxデプロイメントおよびnginxサービスを作成して、Oracle Cloud Infrastructureで以前に作成したDNSゾーンにレコードを挿入できることを確認します:
- テキスト・エディタで、構成ファイル(
nginx-externaldns.yaml
など)を作成して、nginxデプロイメントと、external-dns.alpha.kubernetes.io/hostname
注釈を含むnginxサービスを作成します。例:apiVersion: v1 kind: Service metadata: name: nginx annotations: external-dns.alpha.kubernetes.io/hostname: example.com spec: type: LoadBalancer ports: - port: 80 name: http targetPort: 80 selector: app: nginx --- apiVersion: apps/v1 kind: Deployment metadata: name: nginx spec: selector: matchLabels: app: nginx template: metadata: labels: app: nginx spec: containers: - image: nginx name: nginx ports: - containerPort: 80 name: http
- 次のように入力して、構成ファイルを適用し、nginxサービスおよびデプロイメントを作成します:
kubectl apply -f <filename>
<filename>
は、以前に作成したファイルの名前です。例:kubectl apply -f nginx-externaldns.yaml
前述のコマンドの出力により、デプロイメントが確認されます:
service/nginx created deployment.apps/nginx created
- 数分待ってから、Oracle Cloud Infrastructure DNSゾーンでnginxサービスのDNSレコードが作成されたことを確認します(ゾーンを参照)。
- テキスト・エディタで、構成ファイル(