virtual-kubeletをAWS Fargateで試してみた
現在開催中のJapan Container Days 1812の基調講演でvirtual-kubeletなるプロダクトを聞いたので、サクッと試してみました。
virtual-kubeletとは
Kubernetesにおけるkubeletの実装の一つで、podの作成先を他のプラットフォームのAPIに依頼することができるとのこと。これによって、AzureのACIやAWSのFargateなどのサーバレスフレームワークをKubernetesと連携、Kubernetes側で操作できるようになります。
今回の前提条件
以下の環境を前提に解説します。
- AWS Fargateクラスタ
- 最低でもMasterノードをデプロイしたKubernetesクラスタ
- virtual-kubeletを動作させるためのVM (OS: CentOS7)
Get Started!
まず、virtual-kubeletを動作させるVMにGoとawscliを導入します。この導入手順は割愛します。
次にvirtual-kubeletのバイナリをビルドします。
mkdir -p $GOPATH/src/github.com/virtual-kubelet cd $GOPATH/src/github.com/virtual-kubelet git clone https://github.com/virtual-kubelet/virtual-kubelet cd virtual-kubelet make build
ビルドしたら、バイナリをパスの通るところに置きます。
mv bin/virtual-kubelet /usr/bin/
続いてvirtual-kubeletのprovider設定ファイルを作ります。
mkdir -p /etc/kubernetes/ cp providers/aws/fargate.toml /etc/kubernetes/ cat <<EOF > /etc/kubernetes/fargate.toml Region = "<Fargateクラスタのあるリージョン>" ClusterName = "<Fargateクラスタの名前>" Subnets = [<Fargateクラスタの所属するサブネットのカンマ区切りのリスト>] SecurityGroups = ["<タスクにアタッチしたいSG>"] AssignPublicIPv4Address = true ExecutionRoleArn = "" CloudWatchLogGroupName = "" PlatformVersion = "LATEST" OperatingSystem = "Linux" CPU = "20" Memory = "40Gi" Pods = "20" EOF
virtual-kubeletがKubernetesのマスターに接続するためのkubeconfigをここで作成します。
cat <<EOF > /etc/kubernetes/virtual-kubelet.conf <kubeconfigの中身> EOF
最後にsystemdのunitファイルと環境変数ファイルを作ります。
cat <<EOF > /etc/sysconfig/virtual-kubelet # provider name (required) PROVIDER_NAME="aws" # provider config file path (required) PROVIDER_CONFIG="/etc/kubernetes/fargate.toml" # virtual-kubelet port (required) KUBELET_PORT=10250 # other options OPTIONS="--kubeconfig=/etc/kubernetes/virtual-kubelet.conf" EOF cat <<EOF > /usr/lib/systemd/system/virtual-kubelet.service [Unit] Description=Virtual Kubelet [Service] User=root EnvironmentFile=-/etc/sysconfig/virtual-kubelet ExecStart=/usr/bin/virtual-kubelet --provider \$PROVIDER_NAME --provider-config \$PROVIDER_CONFIG \$OPTIONS [Install] WantedBy=multi-user.target EOF
最後にvirtual-kubeletサービスを有効化します。
systemctl daemon-reload systemctl enable virtual-kubelet systemctl start virtual-kubelet
以上で、Kubernetesにvirtual-kubeletというノード名のノードが追加されているはずです。
kubectl get node NAME STATUS ROLES AGE VERSION test-k8s-zpo7woffkomq-master-0 Ready,SchedulingDisabled <none> 11h v1.11.1 test-k8s-zpo7woffkomq-minion-0 Ready <none> 11h v1.11.1 virtual-kubelet Ready agent 9h v1.11.2
試しにvirtual-kubeletでPodが起動するようなDeploymentを作ってみます。
cat <<EOF | kubectl apply -f - apiVersion: extensions/v1beta1 kind: Deployment metadata: labels: app: httpd name: httpd namespace: default spec: progressDeadlineSeconds: 600 replicas: 1 revisionHistoryLimit: 10 selector: matchLabels: app: httpd strategy: rollingUpdate: maxSurge: 25% maxUnavailable: 25% type: RollingUpdate template: metadata: creationTimestamp: null labels: app: httpd spec: containers: - image: httpd imagePullPolicy: Always name: httpd resources: {} terminationMessagePath: /dev/termination-log terminationMessagePolicy: File dnsPolicy: ClusterFirst restartPolicy: Always schedulerName: default-scheduler securityContext: {} terminationGracePeriodSeconds: 30 nodeSelector: kubernetes.io/role: agent beta.kubernetes.io/os: linux type: virtual-kubelet tolerations: - key: virtual-kubelet.io/provider operator: Exists - key: azure.com/aci effect: NoSchedule EOF
しばらくするとPodがRunning
になります。
kubectl get pod NAME READY STATUS RESTARTS AGE httpd-7b5896b895-45zh6 1/1 Running 0 44s
Fargate側を確認すると、タスクが起動していることがわかります!
Neutron LBaaSのオートヒーリング設定
少しずつ、プライベートクラウド(OpenStack)の構築時ナレッジを書いていこうと思います。本日はNeutron LBaaSについてです。
Neutron LBaaS自身、Octaviaにその役割を譲りつつあり、Deprecateなのですが、LB用VM立てるよりもHAproxyのプロセスをネットワークノードに立てるほうがデプロイが高速なので、いまだに使っています。可用性を気にしなくていい環境では手軽にLBをデプロイできるので、なくなってほしくないですね。。。
Neutron LBaaSですが、デフォルトではLB(HAproxy)が起動しているネットワークノードが死ぬと、当然ながらLBも死んでしまいます。しかし、ネットワークノードが冗長化されている状況では、別ノードでLBを再起動してほしいわけです。そんなことを実現してくれるneutron.conf
のパラメータが用意されています。
allow_automatic_lbaas_agent_failover = true
このパラメータを設定し、LBaaS Agentを冗長化するだけで、LBのオートヒーリングが実現できます!
docker-composeでNginx + Django + MySQLのWeb三階層を構成する
Kubernetesクラスタの構築方法など、インフラ観点での記事を書くことが多い本ブログですが、Kubernetesを学んでみると
- インフラエンジニアもアプリケーションエンジニアの気持ちがわかったほうがいい!
というお気持ちになるのです。CI/CDとか考えると特に。
そんなことでOSにも標準でインストールされている意味でメジャーな言語であるPythonを、そのWebフレームワークであるDjangoを通して勉強しているわけなのですが、DjangoでSQLiteとか、python manage.py runserver
とか使っていると、「本番環境だとこれどう変わるのん?」というインフラエンジニアならではの疑問が沸々と湧き上がってくるのです。
そこで、Pythonのお勉強のわき道にそれて、Nginx + Django + MySQLでWeb三階層を組んでみました。せっかくDockerコンテナのことも知っているので、docker-composeを使い、コンテナでWeb三階層を組んでみました。そのときのdocker-compose.yml
をさらしたいと思います。
いきなりdocker-compose.yml
をさらす前に、プロジェクトのディレクトリ構成を示しておきます。
. ├── docker-compose.yml ├── mysite ← Djangoプロジェクトのルート │ ├── Dockerfile チュートリアルアプリであるpollsアプリを作成 │ ├── docker-entrypoint.sh │ └── mysite │ ├── manage.py │ ├── mysite │ ├── polls │ └── static ├── mysql ← MySQLプロジェクトのルート │ └── Dockerfile mysql:5.7イメージを使うだけ └── nginx ← Nginxプロジェクトのルート ├── Dockerfile 基本的にはnginx:1.15.alpineを使うだけだが、 ├── docker-entrypoint.sh Djangoと連携するためのUWSGI接続設定を組み込む └── mysite_nginx.conf
この前提の下で、docker-compose.yml
は以下のように書きました。
version: '3' services: mysite: build: mysite image: bbrfkr0129/mysite environment: MYSQL_DATABASE: mysite MYSQL_USER: mysite MYSQL_PASSWORD: password MYSQL_HOSTNAME: mysql networks: - mysite mysql: build: mysql image: bbrfkr0129/mysql environment: MYSQL_ROOT_PASSWORD: password MYSQL_DATABASE: mysite MYSQL_USER: mysite MYSQL_PASSWORD: password volumes: - "mysql_data:/var/lib/mysql" networks: - mysite nginx: build: nginx image: bbrfkr0129/nginx ports: - "80:80" environment: UWSGI_HOST: mysite volumes: - "./mysite/mysite/static:/static" networks: - mysite volumes: mysql_data: driver: local networks: mysite: driver: bridge
mysql
サービスは、公式の使い方に準拠しているので、説明を省きます。
mysite
サービスではDjangoをuWSGI接続で動作させます。バックエンドDBにMySQLを使うので、あらかじめsettings.py
にMySQL接続用のパラメータを置換用文字列で書き換えておき、コンテナ起動時にdocker-entrypoint.sh
の処理内で実際のパラメータに置換します。Dockerfile
、docker-entrypoint.sh
は以下のような感じです。
FROM python:3.6-alpine3.8 # install django uwsgi and PyMySQL RUN apk --no-cache --virtual .requirements add g++ make linux-headers && \ apk --no-cache add libffi-dev mysql-dev mysql-client && \ pip install Django uwsgi mysqlclient && rm -rf ~/.cache/pip && \ apk del .requirements # install mysite RUN mkdir /mysite COPY ./mysite/ /mysite/ WORKDIR /mysite EXPOSE 8001 COPY docker-entrypoint.sh /usr/bin/ ENTRYPOINT ["docker-entrypoint.sh"] CMD ["uwsgi", "--socket", ":8001", "--module", "mysite.wsgi"]
#!/bin/sh sed -i "s/MYSQL_DATABASE/$MYSQL_DATABASE/g" /mysite/mysite/settings.py sed -i "s/MYSQL_USER/$MYSQL_USER/g" /mysite/mysite/settings.py sed -i "s/MYSQL_PASSWORD/$MYSQL_PASSWORD/g" /mysite/mysite/settings.py sed -i "s/MYSQL_HOSTNAME/$MYSQL_HOSTNAME/g" /mysite/mysite/settings.py export connected="no" while [ $connected = "no" ] do mysql \ -u$MYSQL_USER -p$MYSQL_PASSWORD -h$MYSQL_HOSTNAME \ -e "show tables;" $MYSQL_DATABASE if [ $? -eq 0 ] ; then export connected="yes" fi sleep 1 done python manage.py makemigrations polls python manage.py migrate python manage.py shell -c "\ from django.contrib.auth import get_user_model;\ User = get_user_model();\ User.objects.create_superuser('admin', 'admin@example.com', 'admin')\ " exec "$@"
nginx
サービスでは基本的にnginx:1.15-alpine
イメージを使いますが、DjangoのuWSGIに接続するための情報が必要なので、このための設定ファイルをdocker buildで埋め込み、コンテナ起動時にdocker-entrypoint.sh
の処理内でパラメータに置換します。Dockerfile
、mysite_nginx.conf
、docker-entrypoint.sh
は以下のような感じです。
# the upstream component nginx needs to connect to upstream django { # server unix:///mysite/mysite.sock; # for a file socket server UWSGI_HOST:8001; # for a web port socket (we'll use this first) } # configuration of the server server { # the port your site will be served on listen 80; # the domain name it will serve for server_name example.com; # substitute your machine's IP address or FQDN charset utf-8; # max upload size client_max_body_size 75M; # adjust to taste location /static { alias /static; } # Finally, send all non-media requests to the Django server. location / { uwsgi_pass django; include /etc/nginx/uwsgi_params; # the uwsgi_params file you installed } }
FROM nginx:1.15-alpine RUN rm -f /etc/nginx/conf.d/* COPY mysite_nginx.conf /etc/nginx/conf.d/mysite_nginx.conf COPY docker-entrypoint.sh /usr/bin/ RUN chmod 755 /usr/bin/docker-entrypoint.sh RUN mkdir /static ENTRYPOINT ["docker-entrypoint.sh"] CMD ["nginx", "-g", "daemon off;"]
#!/bin/sh sed -i "s/UWSGI_HOST/$UWSGI_HOST/g" /etc/nginx/conf.d/mysite_nginx.conf exec "$@"
Webサービスを起動するときは以下のコマンドを叩けばOKです。上がったらhttp://localhost/admin|でDjangoの管理者サイトにアクセスできるはずです。
docker-compose up -d
すべてきれいさっぱり消すときは...(永続データも消えるのでちゅうい)
docker-compose down -v
Docker for WindowsでMySQLコンテナのデータを永続化する
Docker for WindowsでMySQLコンテナのデータを永続化する際、ホストディレクトリを/var/lib/mysql
に単純にマウントすると、MySQLコンテナ側で以下のようなエラーが出ます。
2018-11-18T10:02:32.761277Z 1 [ERROR] [MY-012646] [InnoDB] File ./ibdata1: 'open' returned OS error 71. Cannot continue operation
このエラーを回避するにはDockerボリュームを使ってデータを永続化すると、うまくいくみたいです。具体的にはdocker-compose.yml
に以下のように記載して起動するとうまくいきます。
version: '3' services: mysql: image: mysql:8.0 environment: MYSQL_ROOT_PASSWORD: password MYSQL_DATABASE: mydb MYSQL_USER: myuser MYSQL_PASSWORD: password volumes: - "mysql_data:/var/lib/mysql" volumes: mysql_data: driver: local
既定のアプリをコマンドで変更する方法
Windows 10の10月24日のアップデートでGUI上から一部の既定のアプリを変更することができないようになっているみたいです。これに見事にはまり、.txt
ファイルの既定のアプリをメモ帳から変更できなくなってしまいました。。。
Microsoft側もこのことを認識しており、11月下旬に向けて修正を予定しているようです。 https://support.microsoft.com/en-us/help/4462933/windows-10-update-kb4462933
Symptom | Workaround |
---|---|
After installing this update, some users cannot set Win32 program defaults for certain app and file type combinations using the Open with… command or Settings > Apps > Default apps. In some cases, Microsoft Notepad or other Win32 programs cannot be set as the default. | In some cases, attempting to set application defaults again will succeed. Microsoft is working on a resolution and estimates a solution will be available in late November 2018. |
11月下旬まで待ってられるか!という人は以下のようにして変更できるみたいです。
ftype txtfile="<テキストエディタのパス>" "%1"
OpenStackとoVirtで自宅クラウド環境を構築してみた
お久しぶりです。4か月間ぐらい全くポストしていませんでしたが生きています。
何やっていたかというと、自宅環境をOpenStackによってプライベートクラウド化しておりました。これが完成しないと諸々の検証ができないので、ブログのポストより優先していたら4か月も経っていた感じです。
4か月間にためていたナレッジは少しずつ文章にしていくつもりですが、まずはどんなプライベートクラウド環境を構築していたのか紹介する記事を書こうと思います。自宅環境を構築したい人、している人の少しでも参考になれば幸いです。
目的
本プライベートクラウド環境の目的ですが、以下の通りです。
- 製品の検証(主にインフラの検証。ハイパバイザレベルでの検証も含む)
- サービス提供(Wikiサイトなど)
従来はoVirtというOSSの仮想化基盤製品でこれらの目的をこなしていたわけですが、プライベートクラウド化することによって次のことを狙っていました。
- 様々なサービスのAPIコールによるデプロイ
oVirtはあくまで仮想化基盤なので、あくまでもAmazon EC2やEBS相当の機能しか提供してくれません。昨今のクラウドネイティブなアーキテクチャの学習には不向きだったのです。またコンテナ中核技術であるKubernetesの利便性を最大限引き出すにはクラウドとの連携は必須となります。このためOpenStackによって自宅IaaSを構築しようという考えに至りました。
ただし、OpenStackでは柔軟な仮想マシン設定を行うことが難しくなり、KVMなどのハイパバイザレベルでの動作検証が難しくなります。したがって検証環境すべてをOpenStackに移行したわけではなく、一部リソースをoVirt用に残すようにしました。
アーキテクチャ(物理)
物理構成は以下の通りになります。OpenStack Controllerはロードバランサなどの補助サーバはoVirt上のVMとして構築します。
- Intel NUC Pentiumモデル x 1 (oVirt Engine用)
- Intel NUC Corei3モデル x 3 (oVirt Node用)
- Intel NUC Corei3モデル x 3 (OpenStack Compute用)
アーキテクチャ(仮想)
VMを含めた構成は以下の通りです。冗長化による性能向上を狙って、OpenStack環境はActive/Activeクラスタを構成しています。(Cinder Volumeを除く)
構築したサービス
本プライベートクラウドでは以下のIaaSサービスを提供しています。
oVirt
通常の仮想化環境を提供します。KVM等のハイパバイザ自体を検証したいときはこっちを使います。VMやボリュームのプロビジョニングを行うことができ、通常の仮想化環境といってもAPIがついているので、Ansible等を用いてプロビジョニングを自動化することが可能です。OpenStack Keystone
AWSにおけるIAM相当の認証基盤を提供します。OpenStack Swift
AWSにおけるS3相当のオブジェクトストレージ機能を提供します。OpenStack Glance
AWSにおけるAMI相当のVMイメージストア機能を提供します。Swiftと連携してイメージをSwiftに保存するようにしています。OpenStack Neutron
AWSにおけるVPC、ELB相当の仮想ネットワーク、ソフトウェアロードバランサー機能を提供します。OpenStack Heat
AWSにおけるCloudFormation相当のオーケストレーション機能を提供します。OpenStack Magnum
AWSにおけるECS、EKS相当のコンテナオーケストレーション機能を提供します。Kubernetesのデプロイを一発で行えます。
まとめ
OSSを使って自宅環境をプライベートクラウド化してみましたが、ソフトウェアでインフラを制御するのはとても便利で快感です! お時間ある方は是非チャレンジしてみてはいかがでしょうか? 設計や構築方法について疑問がある方は質問していただければ可能な限りお答えしたいと思います!
kubeadmを用いたKubernetes HAクラスタ on AWS(v.1.11対応版)
前の記事を公開してすぐにv.1.11が出てしまい、構築方法が変わったので、泣きながら再検証...
構成
前提
- 作業ユーザは
root
手順
NLBの作成(AWS ManagementConsole等)
(6443/TCPのリスナを作成、aws-k8s-master[01-03]のIPをターゲットグループに登録する)
Dockerのインストール(aws-k8s-master[01-03]、aws-k8s-node[01-03])
yum install -y docker systemctl enable docker && systemctl start docker
kubeadm、kubelet、kubectlのインストール(aws-k8s-master[01-03]、aws-k8s-node[01-03])
cat <<EOF > /etc/yum.repos.d/kubernetes.repo [kubernetes] name=Kubernetes baseurl=https://packages.cloud.google.com/yum/repos/kubernetes-el7-x86_64 enabled=1 gpgcheck=1 repo_gpgcheck=1 gpgkey=https://packages.cloud.google.com/yum/doc/yum-key.gpg https://packages.cloud.google.com/yum/doc/rpm-package-key.gpg EOF sed -i 's/^SELINUX=.*/SELINUX=permissive/g' /etc/selinux/config setenforce 0 yum install -y kubelet kubeadm kubectl systemctl enable kubelet && systemctl start kubelet
cat <<EOF > /etc/sysctl.d/k8s.conf net.bridge.bridge-nf-call-ip6tables = 1 net.bridge.bridge-nf-call-iptables = 1 EOF sysctl --system
最初のMasterサーバの構築(aws-k8s-master01)
cat <<EOF > kubeadm-config.yaml apiVersion: kubeadm.k8s.io/v1alpha2 kind: MasterConfiguration kubernetesVersion: v1.11.0 apiServerCertSANs: - "<NLBのDNS名>" api: controlPlaneEndpoint: "<NLBのDNS名>:6443" etcd: local: extraArgs: listen-client-urls: "https://127.0.0.1:2379,https://<aws-k8s-master01のIP>:2379" advertise-client-urls: "https://<aws-k8s-master01のIP>:2379" listen-peer-urls: "https://<aws-k8s-master01のIP>:2380" initial-advertise-peer-urls: "https://<aws-k8s-master01のIP>:2380" initial-cluster: "aws-k8s-master01=https://<aws-k8s-master01のIP>:2380" serverCertSANs: - aws-k8s-master01 - <aws-k8s-master01のIP> peerCertSANs: - aws-k8s-master01 - <aws-k8s-master01のIP> networking: podSubnet: "192.168.0.0/16" EOF
kubeadm init --config kubeadm-config.yaml mkdir -p $HOME/.kube cp -i /etc/kubernetes/admin.conf $HOME/.kube/config chown $(id -u):$(id -g) $HOME/.kube/config
SSHキーペアの作成(aws-k8s-master02, aws-k8s-master03)
ssh-keygen -t rsa -b 4096 -C ""
cat ~/.ssh/id_rsa.pub # 出力された内容をaws-k8s-master01の/root/.ssh/authorized_keysのエントリを追加する
証明書群、設定ファイル群の配布(aws-k8s-master02、aws-k8s-master03)
mkdir -p /etc/kubernetes/pki/etcd scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/ca.crt /etc/kubernetes/pki/ca.crt scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/ca.key /etc/kubernetes/pki/ca.key scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/sa.key /etc/kubernetes/pki/sa.key scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/sa.pub /etc/kubernetes/pki/sa.pub scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/front-proxy-ca.crt /etc/kubernetes/pki/front-proxy-ca.crt scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/front-proxy-ca.key /etc/kubernetes/pki/front-proxy-ca.key scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/etcd/ca.crt /etc/kubernetes/pki/etcd/ca.crt scp root@<aws-k8s-master01のIP>:/etc/kubernetes/pki/etcd/ca.key /etc/kubernetes/pki/etcd/ca.key scp root@<aws-k8s-master01のIP>:/etc/kubernetes/admin.conf /etc/kubernetes/admin.conf
2台目のMasterサーバの構築(aws-k8s-master02)
cat <<EOF > kubeadm-config.yaml apiVersion: kubeadm.k8s.io/v1alpha2 kind: MasterConfiguration kubernetesVersion: v1.11.0 apiServerCertSANs: - "<NLBのDNS名>" api: controlPlaneEndpoint: "<NLBのDNS名>:6443" etcd: local: extraArgs: listen-client-urls: "https://127.0.0.1:2379,https://<aws-k8s-master02のIP>:2379" advertise-client-urls: "https://<aws-k8s-master02のIP>:2379" listen-peer-urls: "https://<aws-k8s-master02のIP>:2380" initial-advertise-peer-urls: "https://<aws-k8s-master02のIP>:2380" initial-cluster: "aws-k8s-master01=https://<aws-k8s-master01のIP>:2380,aws-k8s-master02=https://<aws-k8s-master02のIP>:2380" initial-cluster-state: existing serverCertSANs: - aws-k8s-master02 - <aws-k8s-master02のIP> peerCertSANs: - aws-k8s-master02 - <aws-k8s-master02のIP> networking: podSubnet: "192.168.0.0/16" EOF
kubeadm alpha phase certs all --config kubeadm-config.yaml kubeadm alpha phase kubelet config write-to-disk --config kubeadm-config.yaml kubeadm alpha phase kubelet write-env-file --config kubeadm-config.yaml kubeadm alpha phase kubeconfig kubelet --config kubeadm-config.yaml systemctl start kubelet
CP0_IP=<aws-k8s-master01のIP> CP0_HOSTNAME=aws-k8s-master01 CP1_IP=<aws-k8s-master02のIP> CP1_HOSTNAME=aws-k8s-master02 KUBECONFIG=/etc/kubernetes/admin.conf kubectl exec -n kube-system etcd-${CP0_HOSTNAME} -- etcdctl --ca-file /etc/kubernetes/pki/etcd/ca.crt --cert-file /etc/kubernetes/pki/etcd/peer.crt --key-file /etc/kubernetes/pki/etcd/peer.key --endpoints=https://${CP0_IP}:2379 member add ${CP1_HOSTNAME} https://${CP1_IP}:2380 kubeadm alpha phase etcd local --config kubeadm-config.yaml
kubeadm alpha phase kubeconfig all --config kubeadm-config.yaml kubeadm alpha phase controlplane all --config kubeadm-config.yaml kubeadm alpha phase mark-master --config kubeadm-config.yaml
3台目のMasterサーバの構築(aws-k8s-master03)
cat <<EOF > kubeadm-config.yaml apiVersion: kubeadm.k8s.io/v1alpha2 kind: MasterConfiguration kubernetesVersion: v1.11.0 apiServerCertSANs: - "<NLBのDNS名>" api: controlPlaneEndpoint: "<NLBのDNS名>:6443" etcd: local: extraArgs: listen-client-urls: "https://127.0.0.1:2379,https://<aws-k8s-master03のIP>:2379" advertise-client-urls: "https://<aws-k8s-master03のIP>:2379" listen-peer-urls: "https://<aws-k8s-master03のIP>:2380" initial-advertise-peer-urls: "https://<aws-k8s-master03のIP>:2380" initial-cluster: "aws-k8s-master01=https://<aws-k8s-master01のIP>:2380,aws-k8s-master02=https://<aws-k8s-master02のIP>:2380,aws-k8s-master03=https://<aws-k8s-master03のIP>:2380" initial-cluster-state: existing serverCertSANs: - aws-k8s-master03 - <aws-k8s-master03のIP> peerCertSANs: - aws-k8s-master03 - <aws-k8s-master03のIP> networking: podSubnet: "192.168.0.0/16" EOF
kubeadm alpha phase certs all --config kubeadm-config.yaml kubeadm alpha phase kubelet config write-to-disk --config kubeadm-config.yaml kubeadm alpha phase kubelet write-env-file --config kubeadm-config.yaml kubeadm alpha phase kubeconfig kubelet --config kubeadm-config.yaml systemctl start kubelet
CP0_IP=<aws-k8s-master01のIP> CP0_HOSTNAME=aws-k8s-master01 CP2_IP=<aws-k8s-master03のIP> CP2_HOSTNAME=aws-k8s-master03 KUBECONFIG=/etc/kubernetes/admin.conf kubectl exec -n kube-system etcd-${CP0_HOSTNAME} -- etcdctl --ca-file /etc/kubernetes/pki/etcd/ca.crt --cert-file /etc/kubernetes/pki/etcd/peer.crt --key-file /etc/kubernetes/pki/etcd/peer.key --endpoints=https://${CP0_IP}:2379 member add ${CP2_HOSTNAME} https://${CP2_IP}:2380 kubeadm alpha phase etcd local --config kubeadm-config.yaml
kubeadm alpha phase kubeconfig all --config kubeadm-config.yaml kubeadm alpha phase controlplane all --config kubeadm-config.yaml kubeadm alpha phase mark-master --config kubeadm-config.yaml
flannelのインストール(aws-k8s-master01)
curl -O https://raw.githubusercontent.com/coreos/flannel/v0.10.0/Documentation/kube-flannel.yml sed -i 's/10.244.0.0/192.168.0.0/g' kube-flannel.yml kubectl apply -f kube-flannel.yml
Nodeのクラスタ参加(aws-k8s-node[01-03])
kubeadm join --token <token> <NLBのDNS名>:6443 --discovery-token-ca-cert-hash sha256:<hash> # <token>、<hash>はkubeadm initをaws-k8s-master01で実行した際に表示されたものを使用