Mengingat kluster kubernetes yang menjalankan sejumlah pod, layanan, penerapan, dll, saya ingin membuat satu atau lebih file ( lebih disukai format yml) yang akan menghasilkan ulang konfigurasi saat ini, bila diterapkan ke kluster baru.
Kasus penggunaan saya adalah sistem promosi. Saya memiliki 'file tumpukan' sebagai file yml di git repo, tetapi saya harus mengizinkan manusia untuk menyetujui perubahan sebelum diterapkan ke cluster.
Salah satu cara untuk melakukannya adalah dengan menggunakan sistem 'loop terbuka'. Saya dapat menggunakan tag atau mekanisme lain untuk menentukan versi mana yang telah diterapkan ke cluster, dan kemudian membandingkan versi terbaru yang tersedia dengan versi terbaru yang diterapkan.
Masalah dengan sistem loop terbuka adalah bahwa ia tidak menganggap bahwa perubahan dapat dilakukan di luar file, atau bahwa perubahan yang diterapkan dapat menimbulkan masalah, dll.
Jika saya dapat mengekstrak file 'setara' dari cluster yang sedang berjalan, saya dapat membandingkannya dengan yang akan diterapkan. Ini adalah sistem 'loop tertutup' yang jauh lebih kuat-- ia dapat memahami dengan benar apa yang akan terjadi ketika perubahan diterapkan, bahkan jika kita kehilangan jejak keadaan target sebenarnya.
jika ada yang namanya kubectl apply -f
Apakah ada yang punya pemikiran tentang ini? Kami baru mengenal kubernet, tetapi kami telah membuat fungsionalitas yang saya jelaskan di atas untuk penerapan berbasis rpm RedHat/Satelit kami, jadi saya ingin membuatnya kembali di K8s. Tentu saja, di k8s, kami memiliki kerumitan yang dapat diubah oleh infrastruktur itu sendiri, bukan hanya versi paket yang diinstal!
kubectl get po,deployment,rc,rs,ds,no,job -o yaml?
Ah ya, tentu saja! Ini berhasil, tetapi bukan itu yang saya cari. Itu menjawab pertanyaan saya, tetapi tidak memberi saya file yang cocok dengan yang saya gunakan.
Saya mengetahui bahwa jawaban untuk pertanyaan ini adalah dengan membaca anotasi 'last-applied-configuration' yang ditambahkan oleh kubectl. ini akan memberikan file yang digunakan untuk menghasilkan konfigurasi.
@dcowden juga lihat kubectl get --export
ah itu lebih baik! Terima kasih!
Menggabungkan jawaban lain, inilah yang saya buat untuk bash:
for n in $(kubectl get -o=name pvc,configmap,serviceaccount,secret,ingress,service,deployment,statefulset,hpa,job,cronjob)
do
mkdir -p $(dirname $n)
kubectl get -o=yaml --export $n > $n.yaml
done
k8s 1.8
kubectl get all --export=true -o yaml
Untuk orang-orang yang datang ke sini dari Google, pada contoh pengujian saya, komentar terakhir all
tampaknya tidak menyertakan ingress
, dan Anda juga harus mengatakan --all-namespaces
untuk mendapatkannya membuang namespace lain.
Terkait: https://github.com/kubernetes/kubernetes/issues/42885 dan https://github.com/kubernetes/kubernetes/pull/42954#issuecomment -285949856 dll.
Variasi di atas solusi yang disediakan oleh @alahijani
for n in $(kubectl get -o=name pvc,configmap,ingress,service,secret,deployment,statefulset,hpa,job,cronjob | grep -v 'secret/default-token')
do
kubectl get -o=yaml --export $n > $(dirname $n)_$(basename $n).yaml
done
Ini untuk memiliki semua file yaml dalam satu direktori untuk kubectl apply -f
. Itu juga mengecualikan rahasia akun layanan default yang tidak dapat diekspor.
Versi lain: Mengekspor semua yaml dari semua ruang nama. Untuk setiap namespace sebuah direktori dibuat.
i=$((0))
for n in $(kubectl get -o=custom-columns=NAMESPACE:.metadata.namespace,KIND:.kind,NAME:.metadata.name pv,pvc,configmap,ingress,service,secret,deployment,statefulset,hpa,job,cronjob --all-namespaces | grep -v 'secrets/default-token')
do
if (( $i < 1 )); then
namespace=$n
i=$(($i+1))
if [[ "$namespace" == "PersistentVolume" ]]; then
kind=$n
i=$(($i+1))
fi
elif (( $i < 2 )); then
kind=$n
i=$(($i+1))
elif (( $i < 3 )); then
name=$n
i=$((0))
echo "saving ${namespace} ${kind} ${name}"
if [[ "$namespace" != "NAMESPACE" ]]; then
mkdir -p $namespace
kubectl get $kind -o=yaml --export $name -n $namespace > $namespace/$kind.$name.yaml
fi
fi
done
dan untuk mengimpor lagi:
path=$(pwd)
for n in $(ls -d */)
do
echo "Creating namespace ${n:0:-1}"
kubectl create namespace ${n:0:-1}
for yaml in $(ls $path/$n)
do
echo -e "\t Importing $yaml"
kubectl apply -f $path/$n$yaml -n ${n:0:-1}
done
done
Tweak kecil lainnya untuk mengecualikan token akun layanan:
#!/bin/env bash
## https://github.com/kubernetes/kubernetes/issues/24873#issuecomment-416189335
i=$((0))
for n in $(kubectl get -o=custom-columns=NAMESPACE:.metadata.namespace,KIND:.kind,NAME:.metadata.name pv,pvc,configmap,ingress,service,secret,deployment,statefulset,hpa,job,cronjob --all-namespaces | grep -v 'secrets/default-token')
do
if (( $i < 1 )); then
namespace=$n
i=$(($i+1))
if [[ "$namespace" == "PersistentVolume" ]]; then
kind=$n
i=$(($i+1))
fi
elif (( $i < 2 )); then
kind=$n
i=$(($i+1))
elif (( $i < 3 )); then
name=$n
i=$((0))
if [[ "$namespace" != "NAMESPACE" ]]; then
mkdir -p $namespace
yaml=$((kubectl get $kind -o=yaml $name -n $namespace ) 2>/dev/null)
if [[ $kind != 'Secret' || $yaml != *"type: kubernetes.io/service-account-token"* ]]; then
echo "Saving ${namespace}/${kind}.${name}.yaml"
kubectl get $kind -o=yaml --export $name -n $namespace > $namespace/$kind.$name.yaml
fi
fi
fi
done
Bagi mereka yang bekerja di windows Powershell, inilah satu kalimat:
Foreach ($i in $(kubectl get -o=name pvc,configmap,ingress,service,secret,deployment,statefulset,hpa,job,cronjob)) {If($i -notmatch "default-token") {kubectl get -o=yaml --export $i | Out-File -filepath $($i.Replace("/", "-") + ".yaml")}}
@mrwulf @acondrat
Saya pikir grep -v 'secrets/default-token'
harus diubah menjadi grep -v 'secret/default-token'
secrets
tidak bekerja dengan saya.
Saya menggunakan versi kubectl dan k8s cluster berikut
Client Version: version.Info{Major:"1", Minor:"12", GitVersion:"v1.12.2", GitCommit:"17c77c7898218073f14c8d573582e8d2313dc740", GitTreeState:"clean", BuildDate:"2018-10-24T06:54:59Z", GoVersion:"go1.10.4", Compiler:"gc", Platform:"linux/amd64"}
Server Version: version.Info{Major:"1", Minor:"10", GitVersion:"v1.10.5", GitCommit:"32ac1c9073b132b8ba18aa830f46b77dcceb0723", GitTreeState:"clean", BuildDate:"2018-06-21T11:34:22Z", GoVersion:"go1.9.3", Compiler:"gc", Platform:"linux/amd64"}
@4m3ndy Anda benar! Terima kasih!
Hai teman-teman baru saja membuat gambar buruh pelabuhan ini untuk mengekspor file yaml yang diperlukan untuk setiap komponen per namespace. cadangan ini diekspor kemudian dienkripsi dengan kata sandi dan diunggah ke S3 Bucket.
Jika ada yang ingin melakukan perubahan atau berbagi komentar, Anda dipersilahkan :+1:
ambien-inovasi/k8s-backup
contoh: menghasilkan pv yaml.
kubectl get pv -o yaml --export | sed -e '/resourceVersion: "[0-9]\+"/d' -e '/uid: [a-z0-9-]\+/d' -e '/selfLink: [a-z0-9A-Z/]\+/d' -e '/status:/d' -e '/phase:/d' -e '/creationTimestamp:/d' > pvList.yaml
@xiaoping378
https://github.com/ambient-innovation/k8s-backup/blob/01c1bfe750136648fd91e14dd691ba39bb05f282/k8s-backup.sh#L38
Script ini harus menghasilkan semua pvc untuk setiap namespace kemudian mengekspor file yaml untuk setiap pv, lihat
Buat folder ${HOME}/clusterstate/, lalu jalankan:
kubectl cluster-info dump --all-namespaces --output-directory=${HOME}/clusterstate/ -o yaml
Semua entitas Anda akan berada dalam struktur folder terpisah, sesuai dengan ruang nama.
Ekstensi .json, yaitu deployments.json, menyesatkan, karena flag -o yaml
akan membuat ekspor yaml.
Buat folder ${HOME}/clusterstate/, lalu jalankan:
kubectl cluster-info dump --all-namespaces --output-directory=${HOME}/clusterstate/ -o yaml
Semua entitas Anda akan berada dalam struktur folder terpisah, sesuai dengan ruang nama.
Ekstensi .json, yaitu deployments.json, menyesatkan, karena flag-o yaml
akan membuat ekspor yaml.
FYI, ini tampaknya membutuhkan jumlah RAM yang layak untuk penyebaran besar, 2GB RAM CLI jumpbox VM saya tidak dapat menanganinya (mungkin perlu 4 atau 8 saya bayangkan):
fatal error: runtime: out of memory
runtime stack:
runtime.throw(0x1ab7c29, 0x16)
/usr/local/go/src/runtime/panic.go:774 +0x72
runtime.sysMap(0xc068000000, 0x10000000, 0x2da7238)
/usr/local/go/src/runtime/mem_linux.go:169 +0xc5
runtime.(*mheap).sysAlloc(0x2d8e9a0, 0x10000000, 0x0, 0x0)
/usr/local/go/src/runtime/malloc.go:701 +0x1cd
runtime.(*mheap).grow(0x2d8e9a0, 0x8000, 0xffffffff)
/usr/local/go/src/runtime/mheap.go:1255 +0xa3
runtime.(*mheap).allocSpanLocked(0x2d8e9a0, 0x8000, 0x2da7248, 0x42c7bc)
/usr/local/go/src/runtime/mheap.go:1170 +0x266
runtime.(*mheap).alloc_m(0x2d8e9a0, 0x8000, 0x101, 0xc000103f18)
/usr/local/go/src/runtime/mheap.go:1022 +0xc2
Saya menjalankan ulang di desktop saya dan melacak penggunaan memori proses kubectl, puncaknya hanya sekitar 4GB, jadi 8GB!
Tampaknya kira-kira cocok dengan ukuran total keluaran dump, yang mencakup log dan beberapa pod kami (90 di antaranya) mengeluarkan log dengan ukuran lebih dari 100MB. Ini akan menunjukkan kepada saya bahwa perintah dump menyimpan semua yang ada di RAM meskipun sedang ditulis ke disk, mungkin dapat dioptimalkan untuk menghapus RAM karena log selesai ditulis.
Adakah yang bisa memberi tahu saya perintah atau skrip yang akan mengambil cadangan cluster (termasuk file ns, penyebaran, svc, rahasia, pv pvc, cm yaml saja) dengan semua informasi dan mengembalikannya di cluster baru.
Saya telah mencoba dengan --export perintah tetapi dalam layanan nama file yaml layanan tidak ada dan jika saya mengambil cadangan tanpa --export maka itu termasuk IP clusterIP , nodePort ,
kubernetes cluster versi 1.14 dan seterusnya 1.15/16/17 (mencoba melakukan backup/restore di GCP gke atau AWS eks).
Terima kasih kepada kubectl api-resources
! Saya bisa mendapatkan manifes (file yaml) dari semua sumber daya di semua ruang nama di k8s menggunakan skrip bash berikut:
#!/usr/bin/env bash
while read -r line
do
output=$(kubectl get "$line" --all-namespaces -o yaml 2>/dev/null | grep '^items:')
if ! grep -q "\[\]" <<< $output; then
echo -e "\n======== "$line" manifests ========\n"
kubectl get "$line" --all-namespaces -o yaml
fi
done < <(kubectl api-resources | awk '{print $1}' | grep -v '^NAME')
Skrip bash di atas diuji dengan:
v1.16.3
18.04.3
OS4.4.20(1)-release (x86_64-pc-linux-gnu)
@vhosakot Penyederhanaan kecil untuk skrip Anda.
Anda dapat mengganti: kubectl api-resources | awk '{print $1}' | grep -v '^NAME'
Dengan: kubectl api-resources -o name
#!/usr/bin/env bash
while read -r namespace
do
echo "scanning namespace '${namespace}'"
mkdir -p "${HOME}/cluster-backup/${namespace}"
while read -r resource
do
echo " scanning resource '${resource}'"
mkdir -p "${HOME}/cluster-backup/${namespace}/${resource}"
while read -r item
do
echo " exporting item '${item}'"
kubectl get "$resource" -n "$namespace" "$item" -o yaml > "${HOME}/cluster-backup/${namespace}/${resource}/$item.yaml"
done < <(kubectl get "$resource" -n "$namespace" 2>&1 | tail -n +2 | awk '{print $1}')
done < <(kubectl api-resources --namespaced=true 2>/dev/null | tail -n +2 | awk '{print $1}')
done < <(kubectl get namespaces | tail -n +2 | awk '{print $1}')
saya sedikit memperpanjang skrip di atas (dan memperlambatnya). ini memuat semua ruang nama, memuat semua sumber daya di semua ruang nama dan kemudian memuat setiap konfigurasi sebagai satu file di setiap sumber daya di setiap ruang nama. itu bertele-tele dan menunjukkan beberapa kesalahan, tetapi hasil akhirnya (dump) harus bersih.
#!/usr/bin/env bash
ROOT=${HOME}/clusterstate
while read -r resource
do
echo " scanning resource '${resource}'"
while read -r namespace item x
do
mkdir -p "${ROOT}/${namespace}/${resource}"
echo " exporting item '${namespace} ${item}'"
kubectl get "$resource" -n "$namespace" "$item" -o yaml > "${ROOT}/${namespace}/${resource}/$item.yaml" &
done < <(kubectl get "$resource" --all-namespaces 2>&1 | tail -n +2)
done < <(kubectl api-resources --namespaced=true 2>/dev/null | tail -n +2 | awk '{print $1}')
wait
Terinspirasi oleh @scones tetapi berjalan sedikit lebih cepat karena proses forking dan pengurangan loop nesting yang berguna jika Anda memiliki banyak definisi sumber daya khusus!
Sama seperti @nathan-c
Saya menghapus events
dari daftar sumber daya untuk memperbaiki kesalahan
#!/usr/bin/env bash
ROOT=${HOME}/clusterstate
while read -r resource
do
echo " scanning resource '${resource}'"
while read -r namespace item x
do
mkdir -p "${ROOT}/${namespace}/${resource}"
echo " exporting item '${namespace} ${item}'"
kubectl get "$resource" -n "$namespace" "$item" -o yaml > "${ROOT}/${namespace}/${resource}/$item.yaml" &
done < <(kubectl get "$resource" --all-namespaces 2>&1 | tail -n +2)
done < <(kubectl api-resources --namespaced=true 2>/dev/null | grep -v "events" | tail -n +2 | awk '{print $1}')
wait
Komentar yang paling membantu
kubectl get po,deployment,rc,rs,ds,no,job -o yaml?