Bagaimana sebuah pod di Kubernetes mendapatkan alamat IP

Catatan. terjemahan: Artikel ini, ditulis oleh seorang insinyur SRE dari LinkedIn, menjelaskan secara detail tentang keajaiban batin di Kubernetes - lebih tepatnya, interaksi CRI, CNI, dan kube-apiserver - yang terjadi ketika pod berikutnya perlu diberi alamat IP.

Salah satu persyaratan dasar Model jaringan Kubernetes adalah setiap pod harus memiliki alamat IP sendiri dan pod lain di cluster harus dapat menghubunginya di alamat tersebut. Ada banyak “penyedia” jaringan (Flannel, Calico, Canal, dll.) yang membantu mengimplementasikan model jaringan ini.

Ketika saya pertama kali mulai bekerja dengan Kubernetes, saya tidak sepenuhnya jelas bagaimana tepatnya pod mendapatkan alamat IP-nya. Bahkan dengan pemahaman tentang fungsi masing-masing komponen, sulit membayangkan komponen-komponen tersebut bekerja sama. Misalnya, saya tahu untuk apa plugin CNI, tapi saya tidak tahu apa sebenarnya namanya. Oleh karena itu, saya memutuskan untuk menulis artikel ini untuk berbagi pengetahuan tentang berbagai komponen jaringan dan bagaimana mereka bekerja sama dalam sebuah cluster Kubernetes, yang memungkinkan setiap pod mendapatkan alamat IP uniknya sendiri.

Ada berbagai cara untuk mengatur jaringan di Kubernetes, sama seperti opsi runtime yang berbeda untuk container. Publikasi ini akan digunakan Flanel untuk mengatur jaringan dalam sebuah cluster, dan sebagai lingkungan yang dapat dieksekusi - kontainer. Saya juga berasumsi bahwa Anda mengetahui cara kerja jaringan antar container, jadi saya akan membahasnya secara singkat, hanya untuk konteksnya.

Beberapa konsep dasar

Kontainer dan Jaringan: Tinjauan Singkat

Ada banyak publikasi bagus di Internet yang menjelaskan bagaimana container berkomunikasi satu sama lain melalui jaringan. Oleh karena itu, saya hanya akan memberikan gambaran umum tentang konsep dasar dan membatasi diri pada satu pendekatan, yang melibatkan pembuatan jembatan Linux dan enkapsulasi paket. Detailnya dihilangkan, karena topik jaringan kontainer itu sendiri layak mendapat artikel terpisah. Tautan ke beberapa publikasi yang berwawasan luas dan mendidik akan disediakan di bawah ini.

Kontainer di satu host

Salah satu cara untuk mengatur komunikasi melalui alamat IP antar container yang berjalan pada host yang sama melibatkan pembuatan jembatan Linux. Untuk tujuan ini, perangkat virtual dibuat di Kubernetes (dan Docker) veth (ethernet virtual). Salah satu ujung perangkat veth terhubung ke namespace jaringan kontainer, ujung lainnya ke jembatan Linux pada jaringan tuan rumah.

Semua container pada host yang sama memiliki salah satu ujung veth yang terhubung ke jembatan yang melaluinya mereka dapat berkomunikasi satu sama lain melalui alamat IP. Bridge Linux juga memiliki alamat IP dan bertindak sebagai pintu gerbang untuk lalu lintas keluar dari pod yang ditujukan ke node lain.

Bagaimana sebuah pod di Kubernetes mendapatkan alamat IP

Kontainer di host yang berbeda

Enkapsulasi paket adalah salah satu metode yang memungkinkan kontainer pada node berbeda untuk berkomunikasi satu sama lain menggunakan alamat IP. Di Flanel, teknologi bertanggung jawab atas peluang ini. vxlan, yang “mengemas” paket asli menjadi paket UDP dan kemudian mengirimkannya ke tujuannya.

Di cluster Kubernetes, Flannel membuat perangkat vxlan dan memperbarui tabel rute di setiap node. Setiap paket yang ditujukan untuk wadah pada host berbeda melewati perangkat vxlan dan dienkapsulasi dalam paket UDP. Di tujuan, paket yang disarangkan diekstraksi dan diteruskan ke pod yang diinginkan.

Bagaimana sebuah pod di Kubernetes mendapatkan alamat IP
Catatan: Ini hanyalah salah satu cara untuk mengatur komunikasi jaringan antar container.

Apa itu CRI?

CRI (Antarmuka Runtime Kontainer) adalah sebuah plugin yang memungkinkan kubelet menggunakan lingkungan runtime container yang berbeda. CRI API dibangun ke dalam berbagai runtime, sehingga pengguna dapat memilih runtime pilihan mereka.

Apa itu CNI?

Proyek CNI adalah a spesifikasi untuk mengatur solusi jaringan universal untuk container Linux. Selain itu, itu termasuk plugin, bertanggung jawab atas berbagai fungsi saat menyiapkan jaringan pod. Plugin CNI adalah file yang dapat dieksekusi yang sesuai dengan spesifikasi (kami akan membahas beberapa plugin di bawah).

Alokasi subnet ke node untuk menetapkan alamat IP ke pod

Karena setiap pod dalam sebuah cluster harus memiliki alamat IP, penting untuk memastikan bahwa alamat ini unik. Hal ini dicapai dengan menetapkan subnet unik pada setiap node, yang kemudian akan diberikan alamat IP pada pod pada node tersebut.

Pengontrol IPAM Node

Ketika nodeipam diteruskan sebagai parameter bendera --controllers kube-controller-manager, ia mengalokasikan subnet terpisah (podCIDR) ke setiap node dari CIDR cluster (yaitu rentang alamat IP untuk jaringan cluster). Karena podCIDR ini tidak tumpang tindih, setiap pod dapat diberi alamat IP yang unik.

Node Kubernetes diberi podCIDR saat node tersebut pertama kali didaftarkan ke cluster. Untuk mengubah podCIDR node, Anda perlu membatalkan pendaftarannya lalu mendaftarkannya kembali, sehingga membuat perubahan yang sesuai pada konfigurasi lapisan kontrol Kubernetes di antaranya. Anda dapat menampilkan podCIDR dari sebuah node menggunakan perintah berikut:

$ kubectl get no <nodeName> -o json | jq '.spec.podCIDR'
10.244.0.0/24

Kubelet, runtime container, dan plugin CNI: cara kerjanya

Menjadwalkan sebuah pod per node melibatkan banyak langkah persiapan. Di bagian ini, saya hanya akan fokus pada hal-hal yang berhubungan langsung dengan pengaturan jaringan pod.

Menjadwalkan sebuah pod ke node tertentu akan memicu rangkaian kejadian berikut:

Bagaimana sebuah pod di Kubernetes mendapatkan alamat IP

Bantuan: Arsitektur plugin Containerd CRI.

Interaksi antara runtime container dan plugin CNI

Setiap penyedia jaringan memiliki plugin CNI sendiri. Runtime container menjalankannya untuk mengonfigurasi jaringan untuk pod saat pod tersebut dijalankan. Dalam kasus containerd, plugin CNI diluncurkan oleh plugin tersebut dalam wadah CRI.

Apalagi setiap penyedia mempunyai agennya masing-masing. Itu diinstal di semua node Kubernetes dan bertanggung jawab atas konfigurasi jaringan pod. Agen ini disertakan dengan konfigurasi CNI atau membuatnya secara mandiri di node. Konfigurasi ini membantu plugin CRI mengatur plugin CNI mana yang akan dipanggil.

Lokasi konfigurasi CNI dapat disesuaikan; secara default sudah masuk /etc/cni/net.d/<config-file>. Administrator cluster juga bertanggung jawab untuk menginstal plugin CNI pada setiap node cluster. Lokasinya juga dapat disesuaikan; direktori bawaan - /opt/cni/bin.

Saat menggunakan containerd, jalur untuk konfigurasi plugin dan binari dapat diatur di bagian tersebut [plugins.«io.containerd.grpc.v1.cri».cni] в file konfigurasi containerd.

Karena kita menggunakan Flanel sebagai penyedia jaringan, mari kita bahas sedikit tentang pengaturannya:

  • Flaneld (daemon Flanel) biasanya dipasang di cluster sebagai DaemonSet dengan install-cni sebagai init wadah.
  • Install-cni menciptakan File konfigurasi CNI (/etc/cni/net.d/10-flannel.conflist) pada setiap node.
  • Flaneld membuat perangkat vxlan, mengambil metadata jaringan dari server API, dan memantau pembaruan pod. Saat dibuat, ia mendistribusikan rute ke semua pod di seluruh cluster.
  • Rute-rute ini memungkinkan pod untuk berkomunikasi satu sama lain melalui alamat IP.

Untuk informasi lebih detail tentang karya Flanel, saya sarankan menggunakan link di akhir artikel.

Berikut diagram interaksi antara plugin Containerd CRI dan plugin CNI:

Bagaimana sebuah pod di Kubernetes mendapatkan alamat IP

Seperti yang bisa kamu lihat di atas, kubelet memanggil plugin Containerd CRI untuk membuat pod, yang kemudian memanggil plugin CNI untuk mengonfigurasi jaringan pod. Dengan melakukan hal ini, plugin CNI penyedia jaringan memanggil plugin inti CNI lainnya untuk mengonfigurasi berbagai aspek jaringan.

Interaksi antar plugin CNI

Ada berbagai plugin CNI yang tugasnya membantu mengatur komunikasi jaringan antar container di host. Artikel ini akan membahas tiga di antaranya.

Flanel plugin CNI

Saat menggunakan Flanel sebagai penyedia jaringan, komponen Containerd CRI melakukan panggilan Flanel plugin CNImenggunakan file konfigurasi CNI /etc/cni/net.d/10-flannel.conflist.

$ cat /etc/cni/net.d/10-flannel.conflist
{
  "name": "cni0",
  "plugins": [
    {
      "type": "flannel",
      "delegate": {
         "ipMasq": false,
        "hairpinMode": true,
        "isDefaultGateway": true
      }
    }
  ]
}

Plugin Flanel CNI bekerja sama dengan Flaneld. Selama startup, Flaneld mengambil podCIDR dan detail terkait jaringan lainnya dari server API dan menyimpannya ke file /run/flannel/subnet.env.

FLANNEL_NETWORK=10.244.0.0/16 
FLANNEL_SUBNET=10.244.0.1/24
FLANNEL_MTU=1450 
FLANNEL_IPMASQ=false

Plugin Flanel CNI menggunakan data dari /run/flannel/subnet.env untuk mengkonfigurasi dan memanggil plugin jembatan CNI.

Jembatan plugin CNI

Plugin ini dipanggil dengan konfigurasi berikut:

{
  "name": "cni0",
  "type": "bridge",
  "mtu": 1450,
  "ipMasq": false,
  "isGateway": true,
  "ipam": {
    "type": "host-local",
    "subnet": "10.244.0.0/24"
  }
}

Saat dipanggil pertama kali, ini menciptakan jembatan Linux dengan «name»: «cni0», yang ditunjukkan dalam konfigurasi. Kemudian sepasang veth dibuat untuk setiap pod. Salah satu ujungnya terhubung ke namespace jaringan penampung, ujung lainnya disertakan dalam jembatan Linux di jaringan host. Jembatan plugin CNI menghubungkan semua kontainer host ke jembatan Linux di jaringan host.

Setelah selesai menyiapkan pasangan veth, plugin Bridge memanggil plugin IPAM CNI host-lokal. Jenis plugin IPAM dapat dikonfigurasi dalam konfigurasi CNI yang digunakan plugin CRI untuk memanggil plugin Flannel CNI.

Plugin IPAM CNI host-lokal

Jembatan panggilan CNI plugin IPAM host-lokal CNI dengan konfigurasi berikut:

{
  "name": "cni0",
  "ipam": {
    "type": "host-local",
    "subnet": "10.244.0.0/24",
    "dataDir": "/var/lib/cni/networks"
  }
}

Plugin IPAM host-lokal (IP Address Mmanajemen - manajemen alamat IP) mengembalikan alamat IP untuk kontainer dari subnet dan menyimpan IP yang dialokasikan pada host di direktori yang ditentukan di bagian tersebut dataDir - /var/lib/cni/networks/<network-name=cni0>/<ip>. File ini berisi ID wadah yang alamat IP-nya ditetapkan.

Saat memanggil plugin IPAM host-lokal, ia mengembalikan data berikut:

{
  "ip4": {
    "ip": "10.244.4.2",
    "gateway": "10.244.4.3"
  },
  "dns": {}
}

Ringkasan

Kube-controller-manager menugaskan sebuah podCIDR ke setiap node. Setiap pod node menerima alamat IP dari ruang alamat dalam rentang podCIDR yang dialokasikan. Karena podCIDR node tidak tumpang tindih, semua pod menerima alamat IP unik.

Administrator klaster Kubernetes mengonfigurasi dan menginstal kubelet, runtime container, agen penyedia jaringan, dan menyalin plugin CNI ke setiap node. Selama startup, agen penyedia jaringan menghasilkan konfigurasi CNI. Ketika sebuah pod dijadwalkan ke sebuah node, kubelet akan memanggil plugin CRI untuk membuatnya. Selanjutnya, jika containerd digunakan, plugin Containerd CRI akan memanggil plugin CNI yang ditentukan dalam konfigurasi CNI untuk mengonfigurasi jaringan pod. Hasilnya, pod menerima alamat IP.

Butuh beberapa waktu bagi saya untuk memahami semua seluk-beluk dan nuansa dari semua interaksi ini. Saya harap pengalaman ini dapat membantu Anda lebih memahami cara kerja Kubernetes. Jika saya salah tentang sesuatu, silakan hubungi saya di Twitter atau di alamatnya [email dilindungi]. Jangan ragu untuk menghubungi kami jika Anda ingin mendiskusikan aspek artikel ini atau hal lainnya. Saya ingin mengobrol dengan Anda!

referensi

Kontainer dan jaringan

Bagaimana cara kerja Flanel?

CRI dan CNI

PS dari penerjemah

Baca juga di blog kami:

Sumber: www.habr.com

Tambah komentar