Το kubectl είναι ένα τηλεχειριστήριο γενικής χρήσης. Δεν κάνει τίποτα από μόνο του: στέλνει εντολές σε μια συσκευή, τον API server του μαθήματος 01, σε HTTPS στη θύρα 6443. Έχει έναν επιλογέα πηγής, το context, που λέει ποιο cluster να στοχεύσει (docker-desktop, ένα παλιό minikube, η παραγωγή της επιχείρησής σου): πάτα «Play» στοχεύοντας τη λάθος συσκευή και τίποτα δεν κουνιέται, πιστεύεις ότι το τηλεχειριστήριο χάλασε. Έχει μπαταρίες μιας ορισμένης τάσης: ένα kubectl 1.30 μπροστά σε ένα cluster 1.34 δουλεύει περίπου, αλλά σε προειδοποιεί ότι δεν εγγυάται πια τίποτα. Και μιλά μια σταθερή γραμματική: ένα ρήμα (get), έναν πόρο (pods), μερικές φορές ένα όνομα, έπειτα επιλογές (-n premiers-pas -o wide). Σε σαράντα λεπτά θα ξέρεις να διαβάζεις αυτή τη φράση με την πρώτη, θα έχεις διορθώσει μια πραγματική παγίδα έκδοσης, και θα έχεις ανοίξει το δικό σου συρτάρι στο cluster: το namespace premiers-pas, όπου θα συμβεί όλη η ενότητα.
Το kubectl διαβάζει ένα μόνο αρχείο στην εκκίνηση: το ~/.kube/config (C:\Users\<εσύ>\.kube\config σε Windows), το kubeconfig. Περιέχει τρεις λίστες: clusters (μια διεύθυνση API και το πιστοποιητικό που επιτρέπει να την αναγνωρίσεις), users (τα διαπιστευτήρια: εδώ ένα πιστοποιητικό πελάτη που παρήγαγε το Docker Desktop) και contexts, που συνδέουν ένα cluster με έναν χρήστη, με ενδεχομένως ένα προεπιλεγμένο namespace. Η γραμμή current-context ορίζει αυτό που χρησιμοποιεί κάθε εντολή. Το Docker Desktop γράφει εκεί docker-desktop κατά την ενεργοποίηση· το minikube, το kind ή ένας πάροχος cloud προσθέτουν τα δικά τους, και έτσι ένα ίδιο kubectl χειρίζεται πολλά clusters.
Κάθε εντολή διαβάζεται σαν φράση: kubectl <ρήμα> <πόρος> [όνομα] [επιλογές]. Το ρήμα λέει τι να κάνεις· ο πόρος, σε ποιον τύπο αντικειμένου· το όνομα στοχεύει ένα συγκεκριμένο αντικείμενο (χωρίς όνομα, το ρήμα εφαρμόζεται σε όλα αυτά του namespace)· οι επιλογές διευκρινίζουν το συρτάρι (-n), τη μορφή (-o), την εμβέλεια (-A) ή τη ζωντανή παρακολούθηση (-w). Οι πόροι δέχονται συντομεύσεις που το kubectl api-resources λιστάρει στη στήλη του SHORTNAMES.
| Κομμάτι | Παραδείγματα | Ρόλος |
|---|---|---|
| ρήμα | get, describe, create, apply, delete, logs, exec, scale, explain | η ενέργεια που ζητείται από το API |
| πόρος | pods (po), deployments (deploy), services (svc), namespaces (ns), nodes (no) | ο τύπος αντικειμένου· το pod/api ισοδυναμεί με pod api |
| όνομα | api, api-9bfb55fc6-988xh, docker-desktop | ένα συγκεκριμένο αντικείμενο· απόν = όλα τα αντικείμενα του namespace |
-n <ns> | -n premiers-pas | το στοχευόμενο namespace· χωρίς αυτό, default (το μάθημα δεν το χρησιμοποιεί ποτέ) |
-A | kubectl get pods -A | όλα τα namespaces (προσθέτει μια στήλη NAMESPACE) |
-o wide / -o yaml / -o json / -o name | kubectl get pods -o wide | περισσότερες στήλες / το πλήρες αντικείμενο όπως το αποθηκεύει το API / το ίδιο σε JSON / μόνο τύπος/όνομα |
-w | kubectl get pods -n premiers-pas -w | μένει συνδεδεμένο και εμφανίζει κάθε αλλαγή (Ctrl+C για έξοδο) |
--help | kubectl get --help | η βοήθεια οποιουδήποτε ρήματος, με παραδείγματα |
Τα namespaces είναι τα συρτάρια του cluster: ένα ίδιο όνομα Pod ή Service μπορεί να υπάρχει σε δύο namespaces χωρίς σύγκρουση, τα quotas και τα δικαιώματα δεσμεύονται στο namespace, και το kubectl delete namespace αδειάζει όλα με μία κίνηση. Το cluster γεννιέται με default, kube-system (το control plane), kube-public και kube-node-lease. Αυτό το μάθημα δεν γράφει ποτέ στο default: κάθε ενότητα έχει το namespace της, και κάθε εντολή φέρει -n. Να ξεχάσεις το -n σημαίνει να ψάχνεις το Pod σου στο λάθος συρτάρι: «δεν υπάρχει», ενώ τρέχει μια χαρά δίπλα. Θα προκαλέσεις αυτό το λάθος στην καθοδηγούμενη πρακτική για να μην σε ξαναπιάσει ποτέ.
| Τι θέλεις να μάθεις | Εντολή | Μιλά στο cluster; |
|---|---|---|
| ποιο εκτελέσιμο απαντά | where.exe kubectl (Windows) / which -a kubectl (bash) | όχι |
| έκδοση πελάτη και server | kubectl version | ναι |
| σε ποιο cluster δείχνω | kubectl config current-context | όχι |
| όλα τα γνωστά clusters | kubectl config get-contexts | όχι |
| τι περιέχει ένα πεδίο YAML | kubectl explain deployment.spec.replicas | ναι |
| όλοι οι τύποι αντικειμένων και οι συντομεύσεις τους | kubectl api-resources | ναι |
Σε PowerShell, το μηχάνημα του μαθήματος κρατά επίτηδες μια παγίδα: τρία kubectl στο PATH, από τα οποία ένα παλιό 1.30 εγκατεστημένο με το χέρι πριν το Docker Desktop. Σε σένα πιθανότατα υπάρχει μόνο ένα· κάνε πάντως τα βήματα 1 έως 3, θα σου γλιτώσουν μία ώρα σύγχυσης τη μέρα που θα εγκαταστήσεις ένα δεύτερο εργαλείο.
Βρες ποιο kubectl απαντά. Το shell παίρνει το πρώτο εκτελέσιμο που βρίσκει στη σειρά του PATH.
where.exe kubectlwhich -a kubectlΠραγματική έξοδος (Windows):
C:\Program Files\Docker\Docker\resources\bin\kubectl.exe
C:\Users\<toi>\Documents\kubectl\kubectl.exe
C:\kubectl\kubectl.exeΤι πρέπει να δεις: η πρώτη γραμμή είναι αυτή που εκτελείται όταν πληκτρολογείς kubectl. Εδώ είναι αυτή του Docker Desktop, γιατί το PATH έχει αναδιαταχθεί· το βήμα 2 δείχνει τι συμβαίνει όταν δεν ισχύει αυτό. Σε macOS, περίμενε /usr/local/bin/kubectl (Docker Desktop) και ίσως /opt/homebrew/bin/kubectl (Homebrew).
Κοίτα καλά τι θα συμβεί: εκκίνησε το παλιό kubectl επίτηδες. Στο μηχάνημα του μαθήματος, το δεύτερο εκτελέσιμο είναι ένα 1.30. Καλούμενο με την πλήρη διαδρομή του μπροστά στο cluster 1.34:
& "C:\Users\<toi>\Documents\kubectl\kubectl.exe" versionΠραγματική έξοδος:
Client Version: v1.30.0
Kustomize Version: v5.0.4-0.20230601165947-6ce0bf390ce3
Server Version: v1.34.1
WARNING: version difference between client (1.30) and server (1.34) exceeds the supported minor version skew of +/-1Τι πρέπει να δεις: η εντολή απαντά παρ' όλα αυτά (το cluster είναι προσβάσιμο), αλλά η προειδοποίηση είναι σαφής: το Kubernetes εγγυάται το kubectl μόνο σε απόσταση μίας δευτερεύουσας έκδοσης από τον server (1.33, 1.34 ή 1.35 για ένα cluster 1.34). Πέρα από αυτό, ορισμένες υποεντολές συμπεριφέρονται περίεργα ή αγνοούν πρόσφατα πεδία. Αν δεις αυτή τη γραμμή σε σένα, είναι αυτή η παγίδα: ένα παλιό kubectl (Homebrew, Chocolatey, χειροκίνητο κατέβασμα) περνά μπροστά από αυτό του Docker Desktop.
Διόρθωσε τη σειρά του PATH. Για την τρέχουσα συνεδρία PowerShell, έπειτα επαλήθευσε:
$env:Path = "C:\Program Files\Docker\Docker\resources\bin;" + $env:Path
kubectl versionΠραγματική έξοδος:
Client Version: v1.34.1
Kustomize Version: v5.7.1
Server Version: v1.34.1Τι πρέπει να δεις: πελάτης και server ευθυγραμμισμένοι στο v1.34.1, καμία προειδοποίηση πια. Για να κάνεις την αλλαγή μόνιμη σε Windows: Ρυθμίσεις → Σύστημα → Πληροφορίες συστήματος → Ρυθμίσεις συστήματος για προχωρημένους → Μεταβλητές περιβάλλοντος → Path του χρήστη σου → ανέβασε το C:\Program Files\Docker\Docker\resources\bin στην κορυφή (ή διάγραψε την καταχώρηση του παλιού kubectl), έπειτα ξανάνοιξε το τερματικό. Σε macOS/Linux, διάγραψε το διπλότυπο (brew uninstall kubectl) ή βάλε το /usr/local/bin πιο μπροστά στο ~/.zshrc σου. Το script του kit το επαληθεύει για σένα: το .\labo.ps1 prerequis εμφανίζει ✘ kubectl client v1.30.0 trop ancien (minimum 1.33) — … όσο η σειρά είναι λάθος.
Διάβασε το kubeconfig και το τρέχον context. Δύο εντολές που δεν αγγίζουν το cluster.
kubectl config get-contexts
kubectl config current-contextΠραγματική έξοδος:
CURRENT NAME CLUSTER AUTHINFO NAMESPACE
* docker-desktop docker-desktop docker-desktop
minikube minikube minikube default
docker-desktopΤι πρέπει να δεις: το αστεράκι στο docker-desktop. Το μηχάνημα του μαθήματος κρατά ένα context minikube από ένα παλιό σβηστό cluster: είναι το είδος του υπολείμματος που κάνει κάποιον να λέει «το kubectl δεν δουλεύει πια» όταν γίνεται τρέχον κατά λάθος. Αν σε σένα το αστεράκι είναι αλλού, το kubectl config use-context docker-desktop το μετακινεί (μην το πληκτρολογήσεις αν είναι ήδη στη σωστή θέση: η εντολή ξαναγράφει το ~/.kube/config). Η άδεια στήλη NAMESPACE σημαίνει «default εκτός αν δώσω -n»· δεν θα τη γεμίσουμε, το μάθημα θέλει το -n να γίνει αντανακλαστικό.
Διάβασε μια εντολή σαν φράση, με το explain. Το εγχειρίδιο είναι μέσα στο cluster: το kubectl explain ζητά από τον API server την τεκμηρίωση ενός τύπου ή ενός πεδίου, για την ακριβή έκδοση που χρησιμοποιείς.
kubectl explain deployment.spec.replicasΠραγματική έξοδος:
GROUP: apps
KIND: Deployment
VERSION: v1
FIELD: replicas <integer>
DESCRIPTION:
Number of desired pods. This is a pointer to distinguish between explicit
zero and not specified. Defaults to 1.Έπειτα κατέβα ένα επίπεδο μέσα σε ένα Pod:
kubectl explain pod.spec.containersΠραγματική έξοδος (συντομευμένη: η πλήρης λίστα μετρά καμιά τριανταριά πεδία):
KIND: Pod
VERSION: v1
FIELD: containers <[]Container>
DESCRIPTION:
List of containers belonging to the pod. Containers cannot currently be
added or removed. There must be at least one container in a Pod. Cannot be
updated.
A single application container that you want to run within a pod.
FIELDS:
args <[]string>
Arguments to the entrypoint. The container image's CMD is used if this is
not provided. …
image <string>
Container image name. More info:
https://kubernetes.io/docs/concepts/containers/images …
imagePullPolicy <string>
enum: Always, IfNotPresent, Never
Image pull policy. One of Always, Never, IfNotPresent. Defaults to Always if
:latest tag is specified, or IfNotPresent otherwise. Cannot be updated. …
name <string> -required-
Name of the container specified as a DNS_LABEL. Each container in a pod must
have a unique name (DNS_LABEL). Cannot be updated.
ports <[]ContainerPort>
List of ports to expose from the container. …Τι πρέπει να δεις: το <[]Container> λέει «μια λίστα», το -required- σημειώνει τα υποχρεωτικά πεδία (name· το image δεν είναι τυπικά, αλλά ένα container χωρίς εικόνα δεν ξεκινά), και η γραμμή imagePullPolicy … Defaults to Always if :latest tag is specified εξηγεί γιατί αυτό το μάθημα δεν γράφει ποτέ :latest: δεν θα ξέρεις πια ποια έκδοση τρέχει, και το Kubernetes θα την ξανακατέβαζε σε κάθε εκκίνηση.
Ανακάλυψε τους πόρους και τις συντομεύσεις τους. Η πλήρης λίστα ξεπερνά τις πενήντα γραμμές· φίλτραρε τους τύπους που θα συναντήσεις στις τρεις πρώτες ενότητες.
kubectl api-resources | Select-String -Pattern '^(pods|deployments|services|namespaces|nodes|configmaps|secrets|replicasets|jobs|cronjobs|ingresses)\s'kubectl api-resources | grep -E '^(pods|deployments|services|namespaces|nodes|configmaps|secrets|replicasets|jobs|cronjobs|ingresses) 'Πραγματική έξοδος:
configmaps cm v1 true ConfigMap
namespaces ns v1 false Namespace
nodes no v1 false Node
pods po v1 true Pod
secrets v1 true Secret
services svc v1 true Service
deployments deploy apps/v1 true Deployment
replicasets rs apps/v1 true ReplicaSet
cronjobs cj batch/v1 true CronJob
jobs batch/v1 true Job
ingresses ing networking.k8s.io/v1 true IngressΤι πρέπει να δεις: η στήλη SHORTNAMES (po, deploy, svc, ns, no, cm, rs), η στήλη APIVERSION που θα αντιγράφεις στην κορυφή κάθε YAML (v1 για ένα Pod, apps/v1 για ένα Deployment), και κυρίως το NAMESPACED: true για ένα Pod ή ένα Service (ζουν σε ένα συρτάρι, -n υποχρεωτικό), false για namespaces και nodes (ανήκουν σε ολόκληρο το cluster, το -n δεν έχει νόημα).
Δημιούργησε το συρτάρι σου: το namespace premiers-pas. Πρώτη εντολή που γράφει στο cluster.
kubectl create namespace premiers-pas
kubectl get namespace premiers-pas
kubectl get pods -n premiers-pasΠραγματική έξοδος:
namespace/premiers-pas created
NAME STATUS AGE
premiers-pas Active 0s
No resources found in premiers-pas namespace.Τι πρέπει να δεις: η τυπική απάντηση μιας δημιουργίας, τύπος/όνομα created· ένα namespace Active αμέσως· και το μήνυμα ενός άδειου συρταριού, No resources found in premiers-pas namespace.: δεν είναι λάθος, είναι η σωστή απάντηση στο «τι υπάρχει εδώ;» όταν δεν υπάρχει τίποτα. Αν η πρώτη εντολή απαντήσει Error from server (AlreadyExists), το namespace υπάρχει ήδη (ίσως προχώρησες στο μάθημα 04 νωρίτερα): συνέχισε.
Κάνε τη ζωή σου εύκολη: alias και αυτόματη συμπλήρωση. k στη θέση του kubectl και το πλήκτρο Tab που συμπληρώνει ρήματα, πόρους και ονόματα αντικειμένων. Πρόσθεσε αυτές τις γραμμές στο προφίλ σου ώστε να ξαναφορτώνονται σε κάθε τερματικό.
notepad $PROFILEΕπικόλλησε στο ανοιχτό αρχείο (δημιούργησέ το αν το Notepad το προτείνει):
$env:Path = "C:\Program Files\Docker\Docker\resources\bin;" + $env:Path
kubectl completion powershell | Out-String | Invoke-Expression
Set-Alias k kubectlΣε bash (αρχείο ~/.bashrc):
source <(kubectl completion bash)
alias k=kubectl
complete -o default -F __start_kubectl kΣε zsh (~/.zshrc, το προεπιλεγμένο shell του macOS):
source <(kubectl completion zsh)
alias k=kubectl
compdef __start_kubectl kΞανάνοιξε το τερματικό, έπειτα πληκτρολόγησε kubectl get dep και πάτα Tab. Πραγματικό αποτέλεσμα σε PowerShell: η γραμμή γίνεται kubectl get deployments.apps. Πληκτρολόγησε έπειτα k get nodes:
NAME STATUS ROLES AGE VERSION
docker-desktop Ready control-plane 18d v1.34.1Τι πρέπει να δεις: το k απαντά ακριβώς όπως το kubectl. Το μάθημα συνεχίζει να γράφει kubectl ολόκληρο για να μένει ευανάγνωστο· εσύ, πληκτρολόγησε k. Τίποτα να καθαρίσεις: το namespace premiers-pas μένει στη θέση του, το μάθημα 04 το χρησιμοποιεί αμέσως.
WARNING: version difference between client (1.30) and server (1.34) exceeds the supported minor version skew of +/-1 → ένα παλιό kubectl περνά μπροστά από αυτό του Docker Desktop στο PATH. where.exe kubectl / which -a kubectl για να το δεις, βήμα 3 για να διορθώσεις. Η εντολή λειτούργησε παρ' όλα αυτά: η προειδοποίηση δεν μπλοκάρει, προειδοποιεί.Unable to connect to the server: dial tcp 127.0.0.1:6443: connectex: No connection could be made because the target machine actively refused it. → το Docker Desktop είναι σταματημένο ή το Kubernetes απενεργοποιημένο (μάθημα 02). Δεν είναι ποτέ το ίδιο το kubectl: το kubectl version --client απαντά πάντα, το kubectl version όχι.Error in configuration: context was not found for specified context: … ή το kubectl config current-context που επιστρέφει error: current-context is not set → το ζητούμενο context δεν υπάρχει στο kubeconfig που διαβάζεται, ή αυτό το αρχείο είναι άδειο (ένα άλλο εργαλείο ξαναέγραψε το ~/.kube/config, ή η μεταβλητή KUBECONFIG δείχνει αλλού: μηνύματα που προκλήθηκαν στοχεύοντας ένα context bogus και έπειτα ένα άδειο αρχείο). Έλεγξε echo $env:KUBECONFIG (PowerShell) / echo $KUBECONFIG (bash): πρέπει να είναι άδεια· αλλιώς απενεργοποίησε και ξαναενεργοποίησε το Kubernetes στο Docker Desktop, ξαναγράφει το context.Error from server (NotFound): pods "api-…" not found ενώ το Pod εμφανίζεται στο kubectl get pods -n premiers-pas → ξέχασες το -n premiers-pas: το kubectl έψαξε στο default. Πρόσθεσε την επιλογή. Το kubectl get pods -A δείχνει όλα τα Pods με το namespace τους όταν δεν ξέρεις πια πού έβαλες κάτι.kubectl : Impossible de charger le fichier … completion ή Invoke-Expression : … n'est pas reconnu στο $PROFILE → η γραμμή kubectl completion … εκτελείται πριν το PATH περιέχει το kubectl. Βάλε τη γραμμή $env:Path = … πρώτη στο προφίλ, όπως στο βήμα 8· και αν το PowerShell αρνείται να εκτελέσει το προφίλ, Set-ExecutionPolicy -Scope CurrentUser RemoteSigned.Error from server (AlreadyExists): namespaces "premiers-pas" already exists → το namespace είναι ήδη εκεί, τίποτα να κάνεις. Για να ξεκινήσεις από το μηδέν: kubectl delete namespace premiers-pas, περίμενε να εξαφανιστεί από το kubectl get ns (10 έως 30 δευτ.), ξαναδημιούργησέ το.kubectl <ρήμα> <πόρος> [όνομα] [επιλογές]: το kubectl get pods -n premiers-pas -o wide διαβάζεται «δείξε τα Pods του συρταριού premiers-pas, με τις επιπλέον στήλες».where.exe kubectl / which -a kubectl αποκαλύπτει το εκτελέσιμο που απαντά· το kubectl version πρέπει να δείχνει έναν πελάτη το πολύ μία δευτερεύουσα έκδοση μακριά από τον server (v1.34.1 και στις δύο πλευρές σε Docker Desktop 4.68), αλλιώς διόρθωσε τη σειρά του PATH.kubectl config current-context πρέπει να λέει docker-desktop· το kubectl config get-contexts λιστάρει τα άλλα γνωστά clusters· το use-context πληκτρολογείται μόνο αν το αστεράκι είναι στη λάθος θέση.kubectl create namespace premiers-pas, έπειτα -n premiers-pas σε κάθε εντολή· το kubectl api-resources σου λέει ποιοι πόροι είναι NAMESPACED.kubectl explain pod.spec.containers είναι το ενσωματωμένο εγχειρίδιο, ακριβές για την έκδοσή σου· το kubectl get --help δίνει παραδείγματα για κάθε ρήμα.http://localhost:8080 και ένα Pod που ξαναγεννιέται όταν το διαγράφεις.Το kubeconfig δεν είναι αποκλειστικό του Docker Desktop: τη μέρα που η ομάδα σου θα σου δώσει πρόσβαση σε ένα cluster δοκιμών στο cloud, θα λάβεις ένα αρχείο ίδιας μορφής (τα az aks get-credentials, aws eks update-kubeconfig, gcloud container clusters get-credentials το γράφουν για σένα) και το kubectl config get-contexts θα εμφανίσει μία γραμμή παραπάνω. Πάρε από τώρα τη συνήθεια να επαληθεύεις το current-context πριν από κάθε delete: η εντολή δεν ρωτά ποτέ «είσαι σίγουρος;». Η πλήρης αναφορά ρημάτων, επιλογών και μορφών εξόδου είναι στο kubectl Quick Reference (kubernetes.io), με στην κορυφή της σελίδας τις ίδιες γραμμές αυτόματης συμπλήρωσης όπως στο βήμα 8.