はじめに
Kubernetesを扱っていると様々な場面で証明書発行が必要となります。
昨今cert-managerでも証明書の自動発行が可能ですが、今回は自前で証明書発行を行うコマンドを記載します。
シチュエーション
- TLS接続可能なPodをデプロイする場合
- TLS接続可能なIngressをデプロイする場合
- X509クライアント証明書認証を行う場合
コマンド
TLS接続可能なPodをデプロイする場合
insecureな接続でもよい
クライアント証明書を必要としないinsecureな接続の場合は以下コマンドを使用します。
証明書を使用してPod作成後は、curl -k https://<host>:<port>
コマンドで接続します。
openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout nginx.key -out nginx.crt -subj "/CN=mynginxsvc/O=mynginxsvc"
secureな接続をしたい
opensslでも可能ですが、cfsslの方がわかりやすく簡単であるため、こちらを使用します。
なお、CNやSAN(hostsの値)などは適宜変更します。少し長いので手順ごとに記載します。
profile作成
$ mkdir testcrt
$ cd testcrt
$ cat << EOT > ca-config.json
> {
> "signing": {
> "default": {
> "expiry": "8760h"
> },
> "profiles": {
> "server": {
> "expiry": "8760h",
> "usages": ["signing", "key encipherment", "server auth"]
> },
> "client": {
> "expiry": "8760h",
> "usages": ["signing", "key encipherment", "client auth"]
> },
> "client-server": {
> "expiry": "8760h",
> "usages": ["signing", "key encipherment", "server auth", "client auth"]
> }
> }
> }
> }
> EOT
CA作成
$ cat << EOT > ca.json
> {
> "CN": "my-ca.example.com",
> "key": {
> "algo": "ecdsa",
> "size": 256
> },
> "names": [
> {
> "C": "JP",
> "ST": "Tokyo",
> "L": "Minato-ku",
> "O": "my-group"
> }
> ]
> }
> EOT
$ cfssl genkey -initca ca.json | cfssljson -bare ca
$ ls -l testcrt
total 32
-rw------- 1 user group 227 6 21 10:28 ca-key.pem
-rw-r--r-- 1 user group 460 6 21 10:28 ca.csr
-rw-r--r-- 1 user group 186 6 21 10:27 ca.json
-rw-r--r-- 1 user group 761 6 21 10:28 ca.pem
server証明書作成
$ cat << EOT > server.json
> {
> "CN": "my-nginx",
> "hosts": [
> "127.0.0.1",
> "localhost",
> "*.svc.cluster.local"
> ],
> "key": {
> "algo": "ecdsa",
> "size": 256
> },
> "names": [
> {
> "C": "JP",
> "ST": "Tokyo",
> "L": "Minato-ku",
> "O": "my-group"
> }
> ]
> }
> EOT
$ cfssl gencert -ca ca.pem -ca-key ca-key.pem -config ca-config.json -profile server server.json | cfssljson -bare server
$ ls -l testcrt
total 80
-rw-r--r-- 1 user group 579 6 21 11:49 ca-config.json
-rw------- 1 user group 227 6 21 10:28 ca-key.pem
-rw-r--r-- 1 user group 460 6 21 10:28 ca.csr
-rw-r--r-- 1 user group 186 6 21 10:27 ca.json
-rw-r--r-- 1 user group 761 6 21 10:28 ca.pem
-rw-r--r-- 1 user group 361 6 21 12:21 cserver.json
-rw------- 1 user group 227 6 21 12:26 server-key.pem
-rw-r--r-- 1 user group 538 6 21 12:26 server.csr
-rw-r--r-- 1 user group 334 6 21 12:26 server.json
-rw-r--r-- 1 user group 883 6 21 12:26 server.pem
client証明書作成
$ cat << EOT > client.json
> {
> "CN": "my-client",
> "hosts": [
> "127.0.0.1",
> "localhost"
> ],
> "key": {
> "algo": "ecdsa",
> "size": 256
> },
> "names": [
> {
> "C": "JP",
> "ST": "Tokyo",
> "L": "Minato-ku",
> "O": "my-group"
> }
> ]
> }
> EOT
$ cfssl gencert -ca ca.pem -ca-key $ cfssl gencert -ca ca.pem -ca-key ca-key.pem -config ca-config.json -profile client client.json | cfssljson -bare client
$ ls -l testcrt
total 112
-rw-r--r-- 1 user group 579 6 21 11:49 ca-config.json
-rw------- 1 user group 227 6 21 10:28 ca-key.pem
-rw-r--r-- 1 user group 460 6 21 10:28 ca.csr
-rw-r--r-- 1 user group 186 6 21 10:27 ca.json
-rw-r--r-- 1 user group 761 6 21 10:28 ca.pem
-rw------- 1 user group 227 6 21 12:34 client-key.pem
-rw-r--r-- 1 user group 509 6 21 12:34 client.csr
-rw-r--r-- 1 user group 304 6 21 12:33 client.json
-rw-r--r-- 1 user group 859 6 21 12:34 client.pem
-rw-r--r-- 1 user group 361 6 21 12:21 cserver.json
-rw------- 1 user group 227 6 21 12:26 server-key.pem
-rw-r--r-- 1 user group 538 6 21 12:26 server.csr
-rw-r--r-- 1 user group 334 6 21 12:26 server.json
-rw-r--r-- 1 user group 883 6 21 12:26 server.pem
secret作成
$ kubectl create secret generic nginx-certs-keys --from-file=./server.pem --from-file=./server-key.pem --from-file=ca.pem
接続テスト
このsecretをPodにmountし、端末にCA証明書をインストール後、以下コマンドで接続可能となる。
curl --head --cert client.pem --key client-key.pem https://<host>:<port>
TLS接続可能なIngressをデプロイする場合
$ openssl req -x509 -sha256 -nodes -days 365 -newkey rsa:2048 -keyout tls.key -out tls.crt -subj "/CN=nginxsvc/O=nginxsvc"
X509クライアント証明書認証を行う場合
秘密鍵およびCSRの作成
CNにはユーザ名を指定します。
$ openssl genrsa -out jane.key 2048
$ openssl req -new -key jane.key -subj "/CN=jane" -out jane.csr
証明書の作成
CertificateSigningRequestリソースにて作成します。
最後に
シチュエーション別によく使う証明書発行コマンドを記載してみました。
これ以外にも証明書が必要な場面は多々ありますが、誰かの助けになれば幸いです。