Karena kunci dan rahasia Anda seharusnya hanya itu—rahasia
Halo dan selamat datang 👋👋 Kami melanjutkan perjalanan Singkatnya Kubernetes. Di salah satu blog sebelumnya, kita melihat cara mengonfigurasi aplikasi Kubernetes menggunakan ConfigMap
object. Dalam postingan ini, kita akan menjelajahi Kubernetes Secrets
dan bagaimana mereka dapat digunakan untuk menyimpan data konfigurasi sensitif yang perlu ditangani dengan aman (misalnya, kredensial database, kunci API, dll.).
Seperti biasa, ini akan didasarkan pada contoh, dan Anda akan belajar:
- cara membuat
Secrets
(CLI,yaml
dll) dan - berbagai cara menggunakannya di aplikasi Anda (variabel env, volume, dll.)
Kode (dan YAML
) tersedia di GitHub.
Bagian ini telah dibagi menjadi dua bagian logis: cara membuat Secrets
dan teknik menggunakan Secrets
dalam aplikasi Anda.
Prasyarat
Untuk melihat contoh dalam postingan ini, yang Anda perlukan hanyalah cluster Minikube dan alat kubectl CLI untuk mengakses cluster.
Instal Minikube sebagai cluster Kubernetes node tunggal di mesin virtual di komputer Anda. Di Mac, Anda cukup:
curl -Lo minikube https://storage.googleapis.com/minikube/releases/latest/minikube-darwin-amd64 \ && chmod +x minikube
sudo mv minikube /usr/local/bin
Instal kubectl untuk berinteraksi dengan cluster Minikube. Di Mac, Anda dapat:
curl -LO https://storage.googleapis.com/kubernetes-release/release/$(curl -s https://storage.googleapis.com/kubernetes-release/release/stable.txt)/bin/darwin/amd64/kubectl
chmod +x ./kubectl
sudo mv ./kubectl /usr/local/bin/kubectl
Menciptakan Rahasia
Mari kita lihat teknik yang dapat digunakan untuk membuat Secret
.
Gunakan bagian data
Dimungkinkan untuk membuat Secret
bersama dengan data konfigurasi yang disimpan sebagai pasangan nilai kunci di bagian data
definisi.
apiVersion: v1
kind: Secret
metadata:
name: service-apikey
data:
apikey: Zm9vYmFy
Secret
berisi data nilai kunci yang mewakili info sensitif, dengan apikey
sebagai kunci dan nilainya adalah string yang dikodekan base64
.
Untuk membuat Secret
ini di Kubernetes:
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/secret-data.yaml
Untuk mempermudah, file YAML direferensikan langsung dari repo GitHub, tetapi Anda juga dapat mengunduh file tersebut ke mesin lokal Anda dan menggunakannya dengan cara yang sama.
Untuk mengonfirmasi bahwa Secret
telah dibuat:
kubectl get secret/service-apikey -o yaml
Anda akan mendapatkan respons YAML yang mirip dengan:
apiVersion: v1
data:
apikey: Zm9vYmFy
kind: Secret
metadata:
annotations:
kubectl.kubernetes.io/last-applied-configuration: |
{"apiVersion":"v1","data":{"apikey":"Zm9vYmFy"},"kind":"Secret","metadata":{"annotations":{},"name":"service-apikey","namespace":"default"}}
creationTimestamp: "2019-12-17T11:11:27Z"
name: service-apikey
namespace: default
resourceVersion: "113009"
selfLink: /api/v1/namespaces/default/secrets/service-apikey
uid: 671b547c-3316-4916-b6dc-be2b551b974e
type: Opaque
Mengambil detail Secret
menggunakan kubectl get tidak mengungkapkan isinya.
Perhatikan bahwa apikey: Zm9vYmFy
adalah apa yang kami sediakan di manifes YAML. Anda dapat memeriksa formulir teks biasa dengan mendekodekannya:
echo 'Zm9vYmFy' | base64 --decode
//foobar
Gunakan bagian stringData
Atribut data
yang digunakan dalam contoh di atas digunakan untuk menyimpan informasi yang dikodekan base64
. Jika Anda ingin menyimpan data teks biasa dengan aman, Anda dapat menggunakan bagian stringData
. Berikut ini contohnya:
apiVersion: v1
kind: Secret
metadata:
name: plaintext-secret
stringData:
foo: bar
mac: cheese
Nilai untuk foo
dan mac
diteruskan sebagai teks biasa. Buat Secret
ini dan konfirmasikan:
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/secret-plaintext.yaml
kubectl get secret/plaintext-secret -o yaml
Berikut adalah bagian data
dari respons YAML. Data aktual disimpan dalam format berkode base64
.
data:
foo: YmFy
Jika Anda memecahkan kode data, Anda dapat mengonfirmasi bahwa data tersebut cocok dengan masukan teks biasa asli (bar
) yang kami sediakan
echo 'YmFy' | base64 --decode
//bar
Perhatikan bahwa bagiandata
tidak menerima atribut teks biasa. Mencoba melakukannya akan menghasilkan kesalahan sepertiini:illegal base64 data at input byte 8
Isi file
Anda juga dapat memberikan konten seluruh file sebagai masukan ke bagian stringData
. Berikut tampilannya:
apiVersion: v1
kind: Secret
metadata:
name: secret-in-a-file
stringData:
app-config.yaml: |-
hello: world
john: doe
Buat ini Secret
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/secret-file.yaml
Secret
yang dihasilkan ini akan berisi kunci bernama app-config.yaml
dan isinya (nilai) akan menjadi base64
pengkodean data yang disediakan.
Seperti biasa, Anda mengonfirmasi hal ini di Kubernetes dan juga mendekode isinya.
kubectl get secret/secret-in-a-file -o yaml
echo '<"data" content in yaml response> | base64 --decode
Catatan: Saat Anda menggunakan teknik ini, aplikasi Anda bertanggung jawab untuk menguraikan data yang mewakili konfigurasi Secret
. Dalam hal ini, pasangan kunci-nilai yang dipisahkan baris baru, namun bisa juga yang lainnya.
Menggunakan kubectl
Anda dapat menggunakan perintah kubectl create secret
untuk membuat objek Secret
Menggunakan --from-literal
Anda dapat menggunakan data teks biasa untuk membuat Secret
menggunakan CLI (ini akan disimpan dalam format berkode base64
di Kubernetes):
kubectl create secret generic redis-credentials --from-literal=user=poweruser --from-literal=password='f0ob@r'
Menggunakan --from-file
kubectl create secret generic topsecret --from-file=api_keys.txt
Ini akan membuat rahasia (topsecret
) dengan
- kunci dengan nama file yang sama yaitu
api_keys.txt
dalam kasus ini - dan, nilai sebagai isi file
Dari file dalam direktori
Anda cukup menunjuk ke direktori dan semua file di dalamnya akan digunakan untuk membuat file Secret
.
kubectl create secret generic topsecrets --from-file=/home/credentials/
Anda akan berakhir dengan
- beberapa kunci yang akan sama dengan nama file individual
- nilainya akan menjadi isi file masing-masing
Menggunakan Rahasia
Agar Rahasia dapat berguna, kita perlu memastikan bahwa Rahasia tersedia untuk aplikasi kita (yaitu Pod). Mari kita jelajahi cara-cara yang dapat kita lakukan untuk melakukan hal ini
Variabel lingkungan
Anda dapat menggunakan data Secret
sebagai variabel lingkungan di Pod
(seperti ConfigMap
). Berikut ini contohnya:
apiVersion: v1
kind: Pod
metadata:
name: pod1
spec:
containers:
- name: nginx
image: nginx
env:
- name: API_KEY
valueFrom:
secretKeyRef:
name: service-apikey
key: apikey
Kami menggunakan kunci apikey
dari Secret
service-apikey
dan memastikan nilainya tersedia sebagai variabel lingkungan API_KEY
di dalam Pod
.
Buat Pod
(dengan asumsi Anda telah membuat Secret
dari contoh sebelumnya) dan konfirmasi.
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/pod-secret-env.yaml
kubectl get pods -w
Tunggu hingga Pod
bertransisi ke status Running
. Kemudian, konfirmasikan bahwa variabel lingkungan telah dimasukkan ke dalam Pod
.
kubectl exec pod1 -- env | grep API_KEY
Anda seharusnya mendapatkan tanggapan ini — API_KEY=foobar
.
Daripada merujuk ke entri individual di Secret
, Anda dapat menggunakan envFrom
untuk dengan mudah menggunakan semua entri sebagai variabel lingkungan di Pod
. Inilah cara Anda menggunakannya:
apiVersion: v1
kind: Pod
metadata:
name: pod2
spec:
containers:
- name: nginx
image: nginx
envFrom:
- secretRef:
name: plaintext-secret
Kami mengacu pada plaintext-secret
Secret
menggunakan envFrom.secretRef
. Untuk membuat Pod
ini:
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/pod-secret-envFrom.yaml
kubectl get pods -w
Tunggu hingga Pod
bertransisi ke status Running
lalu konfirmasikan keberadaan variabel lingkungan.
kubectl exec pod2 -- env | grep foo //foo=bar
kubectl exec pod2 -- env | grep mac //mac=cheese
Hal ini mengonfirmasi bahwa foo
dan mac
telah ditambahkan sebagai variabel lingkungan ke dalam the
Pod bersama dengan nilai yang didekodekan yaitu masing-masing bar
dan cheese
Volume
Anda dapat memasang Secrets
sebagai Volume
dalam Pod
. Misalnya:
apiVersion: v1
kind: Pod
metadata:
name: pod3
spec:
containers:
- name: nginx
image: nginx
volumeMounts:
- name: apikey-config-volume
mountPath: /secret
readOnly: true
volumes:
- name: apikey-config-volume
secret:
secretName: service-apikey
Volume apikey-config-volume
mengacu pada service-apikey
Secret
. Untuk membuat Pod
ini:
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/pod-secret-volume.yaml
kubectl get pods -w
Tunggu hingga Pod
bertransisi ke status Running
. Kemudian jalankan perintah berikut:
kubectl exec pod3 -- cat /secret/apikey
//foobar
Ini mengonfirmasi bahwa kunci apikey
secara rahasia service-apikey
telah dipasang sebagai file (dengan nama apikey
) di direktori /secret
(khusus di Pod). Isi file tidak lain adalah nilai rahasia yaitu foobar
dalam kasus ini.
Menggunakan imagePullSecrets
Ada cara untuk menggunakan Secrets
sehingga Pod aplikasi Anda dapat menggunakannya untuk mengautentikasi dan menarik image Docker dari registry Docker privat.
Sebenarnya ada tiga jenis Secrets
:
generic
- digunakan untuk menyimpan pasangan nilai kunci, seperti yang telah kita lihat pada contoh sejauh initls
- menyimpan info pasangan kunci publik.pribadi sebagaiSecrets
docker-registry
- kredensial untuk mengautentikasi ke registri Docker.
Cara penggunaan teknik ini sangat sederhana:
- Gunakan tipe
docker-registry
Secret
untuk menyimpan kredensial registri Docker pribadi di Kubernetes. - Dan kemudian,
imagePullSecrets
(dalam sebuah Pod) untuk mereferensikanSecret
yang berisi kredensial registri Docker.
Sebuah contoh selalu membantu:
apiVersion: v1
kind: Pod
metadata:
name: pod4
spec:
containers:
- name: privateapp
image: abhirockzz/test-private-repo:latest
command: ["/bin/sh"]
args: ["-c", "while true; do date; sleep 5;done"]
imagePullSecrets:
- name: docker-repo-secret
Lihat bagaimana imagePullSecrets.name
mengacu pada Secret
yang disebut docker-repo-secret
. Mari kita ciptakan.
Namun sebelum itu, pastikan Anda memiliki registri Docker pribadi. Saya menggunakan DockerHub
, tetapi Anda dapat memilih yang lain.
Mulailah dengan membuat Secret
(dengan nama docker-repo-secret
) yang berisi kredensial Docker Anda menggunakan kubectl create secret docker-registry
command.
kubectl create secret docker-registry docker-repo-secret --docker-server=DOCKER_REG_SERVER --docker-username=DOCKER_REG_USERNAME --docker-password=DOCKER_REG_PASSWORD --docker-email=DOCKER_REG_EMAIL
Untuk Hub Docker:
kubectl create secret docker-registry docker-repo-secret --docker-server=https://index.docker.io/v1/ --docker-username=foobarbaz --docker-password=t0ps3cr3t [email protected]
kubectl get secret/docker-repo-secret -o yaml
https://index.docker.io/v1/
adalah server registri Docker Hub
Untuk mengujinya, kita akan menggunakan gambar busybox
dan tag
it
docker pull busybox docker tag busybox [DOCKER_REG]/[DOCKER_PRIVATE_REPO]:[IMAGE_TAG]
e.g. docker tag busybox abhirockzz/test-private-repo:latest
… dan push
itu
docker push [DOCKER_REG]/[DOCKER_PRIVATE_REPO]:[IMAGE_TAG]
e.g. docker push abhirockzz/test-private-repo:latest
Setelah repo pribadi siap, Anda dapat membuat Pod
yang akan menarik gambar dari repo pribadi menggunakan kredensial registri yang diberikan melalui Secret
kubectl apply -f https://raw.githubusercontent.com/abhirockzz/kubernetes-in-a-nutshell/master/secrets/pod-secret-docker.yaml
kubectl get pods -w
Tunggu hingga Pod
berpindah ke status Running
.
Jika Anda melihat kesalahan ErrImagePull
, ini menunjukkan bahwa mungkin ada masalah dalam mengautentikasi registri Docker. Untuk mendapatkan detailnya, gunakan: kubectl describe pod/pod4
Untuk mengonfirmasi bahwa pod berfungsi dengan baik: kubectl logs -f pod4
Karena gambar busybox
tidak melakukan apa pun dengan sendirinya, kami mengeksekusi: while true; do date; sleep 5;done
(seperti yang disediakan dalam spesifikasi Pod
). Hasilnya, Anda akan melihat log (dicetak setiap 5 detik).
Tue Dec 17 14:17:34 UTC 2019
Tue Dec 17 14:17:39 UTC 2019
Tue Dec 17 14:17:44 UTC 2019
Tue Dec 17 14:18:49 UTC 2019
Semuanya bagus! Artinya, Pod dapat menarik image Anda dari repo Docker pribadi menggunakan kredensial Docker yang dimasukkan ke Pod
menggunakan imagePullSecrets
, yang mereferensikan Secret
Senang mendengarnya
Berikut adalah daftar (tidak lengkap) hal-hal yang harus Anda ingat saat menggunakan Secrets
:
Secret
harus dibuat sebelumPod
mana pun yang ingin menggunakannya.Secrets
berlaku dalamnamespace
yaitu hanya dapat digunakan olehPods
dinamespace
yang samaPod
tidak akan dimulai jika ada referensi ke kunci yang tidak ada diSecret
(menggunakansecretKeyRef
)- 1MiB adalah batas ukuran untuk individu
Secrets
Sekian untuk edisi seri Kubernetes in a Nutshell kali ini. Nantikan selengkapnya!
Jika Anda tertarik mempelajari Kubernetes dan Container menggunakan “Azure”, cukup “buat akun gratis” dan mulai. Titik awal yang baik adalah dengan menggunakan mulai cepat, tutorial, dan contoh kode dalam dokumentasi untuk membiasakan diri Anda dengan layanan ini. Saya juga sangat merekomendasikan untuk memeriksa Jalur Pembelajaran Kubernetes 50 hari. Pengguna tingkat lanjut mungkin ingin merujuk ke “praktik terbaik Kubernetes” atau menonton beberapa “video” untuk demo, fitur unggulan, dan sesi teknis.
Saya sangat berharap Anda menikmati dan mempelajari sesuatu dari artikel ini. 🙌