Ескерту. аударма: Бұл мақала қоғамдық доменде жарияланған жоба материалдарының бөлігі болып табылады , компаниялар мен жеке әкімшілерді Kubernetes-пен жұмыс істеуге үйретеді. Онда жоба менеджері Даниэле Поленчич K8s кластерінде жұмыс істейтін қолданбалармен жалпы ақаулар туындаған жағдайда қандай қадамдар жасау керектігі туралы көрнекі нұсқаулармен бөліседі.

TL; DR: мұнда Kubernetes-те орналастыруды жөндеуге көмектесетін диаграмма:
Кластердегі қателерді табуға және түзетуге арналған блок-схема. Түпнұсқасын (ағылшын тілінде) мына жерден алуға болады и .
Қолданбаны Kubernetes қолданбасына орналастырған кезде, әдетте үш компонентті анықтау қажет:
- Орналастыру - бұл қосымшаның көшірмелерін құруға арналған рецепт түрі, подневки деп аталады;
- қызмет көрсету — трафикті блоктар арасында тарататын ішкі жүктеме балансы;
- Кіріс — сыртқы әлемнен Қызметке трафик қалай түсетінін сипаттау.
Мұнда жылдам графикалық қорытынды:
1) Kubernetes-те қолданбалар сыртқы әлемнен трафикті жүк балансының екі қабаты арқылы алады: ішкі және сыртқы.

2) Ішкі теңгерімдегіші Сервис деп аталады, сыртқысы - Ingress.

3) Орналастыру подкасттарды жасайды және оларды бақылайды (олар қолмен жасалмайды).

Сіз қарапайым қолданбаны қолданғыңыз келеді делік Сәлем Әлем. Оның YAML конфигурациясы келесідей болады:
apiVersion: apps/v1
kind: Deployment # <<<
metadata:
name: my-deployment
labels:
track: canary
spec:
selector:
matchLabels:
any-name: my-app
template:
metadata:
labels:
any-name: my-app
spec:
containers:
- name: cont1
image: learnk8s/app:1.0.0
ports:
- containerPort: 8080
---
apiVersion: v1
kind: Service # <<<
metadata:
name: my-service
spec:
ports:
- port: 80
targetPort: 8080
selector:
name: app
---
apiVersion: networking.k8s.io/v1beta1
kind: Ingress # <<<
metadata:
name: my-ingress
spec:
rules:
- http:
paths:
- backend:
serviceName: app
servicePort: 80
path: /Анықтама өте ұзақ және компоненттердің бір-бірімен байланысы туралы шатасу оңай.
Мысалы:
- 80 портын қашан пайдалану керек және 8080 қашан пайдалану керек?
- Әр қызмет үшін олар қайшы келмеуі үшін жаңа порт жасауым керек пе?
- Белгі атаулары маңызды ма? Олар барлық жерде бірдей болуы керек пе?
Түзетуге назар аудармас бұрын, үш құрамдас бір-бірімен қалай байланысты екенін еске түсірейік. Орналастыру және қызмет көрсетуден бастайық.
Орналастыру мен қызмет көрсету арасындағы байланыс
Сіз таң қаласыз, бірақ Орналастыру мен Қызмет ешбір жолмен байланысты емес. Оның орнына, Қызмет орналастыруды айналып өтіп, тікелей Pods-ке нұсқайды.
Осылайша, бізді Pod және Services бір-бірімен қалай байланыстыратыны қызықтырады. Есте сақтау керек үш нәрсе:
- селектор (
selector) Қызмет үшін кемінде бір Pod белгісіне сәйкес келуі керек. -
targetPortсәйкес келуі керекcontainerPortPod ішіндегі контейнер. -
portҚызмет кез келген нәрсе болуы мүмкін. Әртүрлі қызметтер бір портты пайдалана алады, себебі олардың IP мекенжайлары әртүрлі.
Төмендегі диаграмма жоғарыда аталғандардың барлығын графикалық түрде көрсетеді:
1) Қызмет трафикті белгілі бір подкастқа бағыттайтынын елестетіңіз:

2) Подкаст жасау кезінде көрсету керек containerPort бүршіктердегі әрбір контейнер үшін:

3) Қызметті құру кезінде көрсету керек port и targetPort. Бірақ қайсысы контейнерге қосылу үшін қолданылады?

4) арқылы targetPort. Ол сәйкес болуы керек containerPort.

5) Контейнерде 3000 порты ашық делік targetPort бірдей болуы керек.

YAML файлында белгілер және ports / targetPort сәйкес болуы керек:
apiVersion: apps/v1
kind: Deployment
metadata:
name: my-deployment
labels:
track: canary
spec:
selector:
matchLabels:
any-name: my-app
template:
metadata:
labels: # <<<
any-name: my-app # <<<
spec:
containers:
- name: cont1
image: learnk8s/app:1.0.0
ports:
- containerPort: 8080 # <<<
---
apiVersion: v1
kind: Service
metadata:
name: my-service
spec:
ports:
- port: 80
targetPort: 8080 # <<<
selector: # <<<
any-name: my-app # <<< Жапсырма ше? track: canary Орналастыру бөлімінің жоғарғы жағында? Сәйкес келуі керек пе?
Бұл белгі орналастыруға арналған және қызмет трафикті бағыттау үшін пайдаланбайды. Басқаша айтқанда, оны жоюға немесе басқа мән беруге болады.
Селектор туралы не деуге болады matchLabels?
Ол әрқашан Pod белгілеріне сәйкес келуі керек, себебі ол бөлімшелерді бақылау үшін Deployment арқылы пайдаланылады.
Сіз дұрыс өңдеулер жасадыңыз делік. Оларды қалай тексеруге болады?
Под жапсырмасын келесі пәрмен арқылы тексеруге болады:
kubectl get pods --show-labelsНемесе, бөтелкелер бірнеше қолданбаларға тиесілі болса:
kubectl get pods --selector any-name=my-app --show-labels Қайда? any-name=my-app белгі болып табылады any-name: my-app.
Қандай да бір қиындықтар қалды ма?
Сіз подкастқа қосыла аласыз! Ол үшін пәрменді пайдалану керек port-forward kubectl ішінде. Бұл қызметке қосылуға және қосылымды тексеруге мүмкіндік береді.
kubectl port-forward service/<service name> 3000:80Мұнда:
-
service/<service name>— қызмет атауы; біздің жағдайда солайmy-service; - 3000 - компьютерде ашу керек порт;
- 80 - өрісте көрсетілген порт
portқызмет көрсету.
Егер қосылым орнатылған болса, онда параметрлер дұрыс.
Қосылым сәтсіз болса, белгілерде ақаулық бар немесе порттар сәйкес келмейді.
Қызмет пен кіру арасындағы байланыс
Қолданбаға кіруді қамтамасыз етудің келесі қадамы Ingress орнатуды қамтиды. Кіріс қызметті қалай табуға болатынын білуі керек, содан кейін қосқыштарды тауып, оларға трафикті бағыттау керек. Кіріс аты және ашық порт бойынша қажетті қызметті табады.
Ingress және Service сипаттамасында екі параметр сәйкес келуі керек:
-
servicePortIngress параметріне сәйкес келуі керекportқызметте; -
serviceNameIngress өрісіне сәйкес келуі керекnameқызметте.
Төмендегі диаграмма порт қосылымдарын қорытындылайды:
1) Өздеріңіз білетіндей, Сервис белгілі бір нәрсені тыңдайды port:

2) Ingress деп аталатын параметр бар servicePort:

3) Бұл параметр (servicePort) әрқашан сәйкес болуы керек port Қызмет анықтамасында:

4) Сервисте 80 порт көрсетілген болса, бұл қажет servicePort сонымен қатар 80-ге тең болды:

Іс жүзінде сіз келесі жолдарға назар аударуыңыз керек:
apiVersion: v1
kind: Service
metadata:
name: my-service # <<<
spec:
ports:
- port: 80 # <<<
targetPort: 8080
selector:
any-name: my-app
---
apiVersion: networking.k8s.io/v1beta1
kind: Ingress
metadata:
name: my-ingress
spec:
rules:
- http:
paths:
- backend:
serviceName: my-service # <<<
servicePort: 80 # <<<
path: /Ingress жұмыс істеп тұрғанын қалай тексеруге болады?
көмегімен әдісті қолдануға болады kubectl port-forward, бірақ қызметтің орнына Ingress контроллеріне қосылу керек.
Алдымен сіз Ingress контроллері бар подкасттың атын білуіңіз керек:
kubectl get pods --all-namespaces
NAMESPACE NAME READY STATUS
kube-system coredns-5644d7b6d9-jn7cq 1/1 Running
kube-system etcd-minikube 1/1 Running
kube-system kube-apiserver-minikube 1/1 Running
kube-system kube-controller-manager-minikube 1/1 Running
kube-system kube-proxy-zvf2h 1/1 Running
kube-system kube-scheduler-minikube 1/1 Running
kube-system nginx-ingress-controller-6fc5bcc 1/1 Running Кіру подкағын тауып (ол басқа аттар кеңістігінде болуы мүмкін) және пәрменді іске қосыңыз describeпорт нөмірлерін білу үшін:
kubectl describe pod nginx-ingress-controller-6fc5bcc
--namespace kube-system
| grep Ports
Ports: 80/TCP, 443/TCP, 18080/TCPСоңында, подводқа қосылыңыз:
kubectl port-forward nginx-ingress-controller-6fc5bcc 3000:80 --namespace kube-systemЕнді компьютердегі 3000 портына сұрау жіберген сайын, ол Ingress контроллері бар подкасттың 80 портына жіберіледі. Бару арқылы , қолданба жасаған бетті көруіңіз керек.
Порттардың қысқаша мазмұны
Қай порттар мен белгілер сәйкес келуі керек екенін тағы бір рет еске түсірейік:
- Қызмет анықтамасындағы селектор подвод белгісіне сәйкес болуы керек;
-
targetPortанықтамасында Қызмет сәйкес болуы керекcontainerPortқорап ішіндегі контейнер; -
portанықтамасында Қызмет кез келген нәрсе болуы мүмкін. Әртүрлі қызметтер бір портты пайдалана алады, себебі олардың IP мекенжайлары әртүрлі; -
servicePortКіріс сәйкес келуі керекportҚызмет анықтамасында; - Қызмет атауы өріске сәйкес келуі керек
serviceNameIngress.
Өкінішке орай, YAML конфигурациясын қалай дұрыс құрылымдау керектігін білу жеткіліксіз.
Істер дұрыс емес болғанда не болады?
Қосқыш іске қосылмауы немесе істен шығуы мүмкін.
Kubernetes қолданбасындағы ақауларды диагностикалаудың 3 қадамы
Орналастыруды жөндеуді бастамас бұрын, Kubernetes қалай жұмыс істейтінін жақсы түсінуіңіз керек.
K8s-де жүктелген әрбір қосымшаның үш құрамдас бөлігі болғандықтан, оларды ең төменгі жағынан бастап белгілі бір ретпен жөндеу керек.
- Алдымен сіз бұршақтардың жұмыс істеп тұрғанына көз жеткізуіңіз керек, содан кейін...
- Қызметтің блоктарға трафик беретінін тексеріңіз, содан кейін...
- Ingress дұрыс конфигурацияланғанын тексеріңіз.
Көрнекі көрініс:
1) Мәселелерді түбінен іздеуді бастау керек. Алдымен қосқыштардың күйлері бар екенін тексеріңіз Ready и Running:

2) Егер бұршақ дайын болса (Ready), қызметтің трафикті қосқыштар арасында тарататынын білуіңіз керек:

3) Соңында, қызмет пен кіріс арасындағы байланысты талдау керек:

1. Бұршақтардың диагностикасы
Көп жағдайда мәселе бөтелкеге байланысты. Бұршақтардың тізімделгеніне көз жеткізіңіз Ready и Running. Мұны пәрмен арқылы тексеруге болады:
kubectl get pods
NAME READY STATUS RESTARTS AGE
app1 0/1 ImagePullBackOff 0 47h
app2 0/1 Error 0 47h
app3-76f9fcd46b-xbv4k 1/1 Running 1 47h Жоғарыдағы пәрмен шығысында соңғы подвод ретінде тізімделген Running и Ready, дегенмен, бұл қалған екеуіне қатысты емес.
Ненің дұрыс емес екенін қалай түсінуге болады?
Бөлшектерді диагностикалау үшін төрт пайдалы пәрмен бар:
-
kubectl logs <имя pod'а>бөренелерді контейнерлерден шығаруға мүмкіндік береді; -
kubectl describe pod <имя pod'а>подкастпен байланысты оқиғалар тізімін көруге мүмкіндік береді; -
kubectl get pod <имя pod'а>Kubernetes ішінде сақталған подкасттың YAML конфигурациясын алуға мүмкіндік береді; -
kubectl exec -ti <имя pod'а> bashподконтейнерлердің бірінде интерактивті пәрмен қабығын іске қосуға мүмкіндік береді
Қайсысын таңдау керек?
Өйткені, әмбебап бұйрық жоқ. Олардың комбинациясы қолданылуы керек.
Типтік қабық проблемалары
Қоспа қателерінің екі негізгі түрі бар: іске қосу қателері және орындалу қателері.
Іске қосу қателері:
-
ImagePullBackoff -
ImageInspectError -
ErrImagePull -
ErrImageNeverPull -
RegistryUnavailable -
InvalidImageName
Орындалу қателері:
-
CrashLoopBackOff -
RunContainerError -
KillContainerError -
VerifyNonRootError -
RunInitContainerError -
CreatePodSandboxError -
ConfigPodSandboxError -
KillPodSandboxError -
SetupNetworkError -
TeardownNetworkError
Кейбір қателер басқаларға қарағанда жиі кездеседі. Мұнда ең жиі кездесетін қателер және оларды түзету жолдары берілген.
ImagePullBackOff
Бұл қате Kubernetes подконтейнерлердің біреуі үшін кескінді ала алмаған кезде орын алады. Мұның ең көп тараған үш себебі:
- Кескіннің аты дұрыс емес – мысалы, сіз онда қате жібердіңіз немесе сурет жоқ;
- Кескін үшін жоқ тег көрсетілді;
- Кескін жеке тізілімде сақталады және Кубернетестің оған кіруге рұқсаты жоқ.
Алғашқы екі себепті жою оңай - сурет атауы мен тегін түзетіңіз. Соңғы жағдайда құпияда жабық тізілім үшін тіркелгі деректерін енгізіп, оған сілтемелерді подкасттарда қосу керек. Kubernetes құжаттамасында мұны қалай жасауға болады.
CrashLoopBackOff
Kubenetes қате жібереді CrashLoopBackOff, егер контейнер іске қосылмаса. Бұл әдетте келесі жағдайларда болады:
- Қолданбада оны іске қосуға кедергі келтіретін қате бар;
- Контейнер ;
- Тірілік сынағы тым көп рет сәтсіз аяқталды.
Оның істен шығу себебін білу үшін контейнерден журналдарға жетуге тырысу керек. Контейнер тым жылдам қайта іске қосылғандықтан журналдарға қол жеткізу қиын болса, келесі пәрменді пайдалануға болады:
kubectl logs <pod-name> --previousОл контейнердің алдыңғы нұсқасынан қате туралы хабарларды көрсетеді.
RunContainerError
Бұл қате контейнер іске қосылмағанда орын алады. Бұл қолданба іске қосылғанға дейінгі сәтке сәйкес келеді. Бұл әдетте дұрыс емес параметрлерден туындайды, мысалы:
- ConfigMap немесе Secrets сияқты жоқ томды орнату әрекеті;
- тек оқуға арналған томды оқу-жазу ретінде орнатуға тырысыңыз.
Команда мұндай қателерді талдауға өте қолайлы kubectl describe pod <pod-name>.
Қоспалар күту күйінде
Жасалғаннан кейін подвод күйде қалады Pending.
Неге бұлай болып жатыр?
Міне, ықтимал себептер (мен жоспарлаушы жақсы жұмыс істейді деп ойлаймын):
- Кластерде қондырманы іске қосу үшін өңдеу қуаты және жад сияқты ресурстар жеткіліксіз.
- Нысан сәйкес аттар кеңістігінде орнатылған
ResourceQuotaжәне подкаст жасау аттар кеңістігінің квотаның шегінен шығуына әкеледі. - Pod күтуде
PersistentVolumeClaim.
Бұл жағдайда пәрменді пайдалану ұсынылады kubectl describe және бөлімді тексеріңіз Events:
kubectl describe pod <pod name> қатысты қателер болған жағдайда ResourceQuotas, пәрменін пайдаланып кластер журналдарын қарау ұсынылады
kubectl get events --sort-by=.metadata.creationTimestampҚоспалар дайын емес
Егер подкаст тізімде болса Running, бірақ күйде емес Ready, дайындығын тексеру дегенді білдіреді (дайындық зонды) сәтсіздікке ұшырайды.
Бұл орын алғанда, подключ қызметке қосылмайды және оған ешқандай трафик ағыны болмайды. Дайындық сынағының сәтсіздігі қолданбадағы ақаулардан туындайды. Бұл жағдайда қатені табу үшін бөлімді талдау керек Events пәрмен шығысында kubectl describe.
2. Қызметтік диагностика
Егер бөтелкелер тізімде болса Running и Ready, бірақ қолданбадан әлі жауап жоқ, қызмет параметрлерін тексеру керек.
Қызметтер белгілерге байланысты трафикті подкасттарға бағыттауға жауапты. Сондықтан, ең алдымен, қызметпен қанша бөтелке жұмыс істейтінін тексеру керек. Ол үшін қызметтегі соңғы нүктелерді тексеруге болады:
kubectl describe service <service-name> | grep Endpoints Соңғы нүкте - пішін мәндерінің жұбы <IP-адрес:порт>, және шығыста кемінде бір осындай жұп болуы керек (яғни, қызметпен кем дегенде бір подвод жұмыс істейді).
Егер бөлімі Endpoins бос, екі нұсқа мүмкін:
- дұрыс белгісі бар бөтелкелер жоқ (кеңес: аттар кеңістігінің дұрыс таңдалғанын тексеріңіз);
- Селектордағы қызмет көрсету белгілерінде қате бар.
Егер сіз соңғы нүктелердің тізімін көрсеңіз, бірақ әлі де қолданбаға қол жеткізе алмасаңыз, ықтимал кінәлі қате targetPort қызмет сипаттамасында.
Қызметтің функционалдығын қалай тексеруге болады?
Қызмет түріне қарамастан, сіз пәрменді пайдалана аласыз kubectl port-forward оған қосылу үшін:
kubectl port-forward service/<service-name> 3000:80Мұнда:
-
<service-name>— қызмет атауы; - 3000 - компьютерде ашылатын порт;
- 80 - қызмет көрсету жағындағы порт.
3. Кіру диагностикасы
Осы уақытқа дейін оқыған болсаңыз, онда:
- түйіршіктер ретінде тізімделген
RunningиReady; - қызмет трафикті қосқыштар арасында сәтті таратады.
Дегенмен, қолданбаға әлі де қол жеткізе алмайсыз.
Бұл Ingress контроллері дұрыс конфигурацияланбағанын білдіреді. Ingress контроллері кластердегі үшінші тарап құрамдас бөлігі болғандықтан, оның түріне байланысты әр түрлі жөндеу әдістері бар.
Бірақ кірісті конфигурациялау үшін арнайы құралдарды пайдаланбас бұрын, сіз өте қарапайым нәрсені жасай аласыз. Кіру пайдаланады serviceName и servicePort қызметке қосылу үшін. Олардың дұрыс конфигурацияланғанын тексеру керек. Мұны пәрмен арқылы орындауға болады:
kubectl describe ingress <ingress-name> Егер баған Backend бос болса, конфигурация қатесінің ықтималдығы жоғары. Егер серверлер орнында болса, бірақ қолданба әлі де қолжетімді болмаса, мәселе мынаған байланысты болуы мүмкін:
- Жалпыға қолжетімді интернеттен қол жетімділік параметрлерін енгізу;
- жалпыға қолжетімді интернеттен кластерге қол жетімділік параметрлері.
Инфрақұрылымдағы ақауларды тікелей кіріс қосқышына қосу арқылы анықтауға болады. Бұл әрекетті орындау үшін алдымен Ingress Controller подкастын табыңыз (ол басқа аттар кеңістігінде болуы мүмкін):
kubectl get pods --all-namespaces
NAMESPACE NAME READY STATUS
kube-system coredns-5644d7b6d9-jn7cq 1/1 Running
kube-system etcd-minikube 1/1 Running
kube-system kube-apiserver-minikube 1/1 Running
kube-system kube-controller-manager-minikube 1/1 Running
kube-system kube-proxy-zvf2h 1/1 Running
kube-system kube-scheduler-minikube 1/1 Running
kube-system nginx-ingress-controller-6fc5bcc 1/1 Running Пәрменді пайдаланыңыз describeпортты орнату үшін:
kubectl describe pod nginx-ingress-controller-6fc5bcc
--namespace kube-system
| grep PortsСоңында, подводқа қосылыңыз:
kubectl port-forward nginx-ingress-controller-6fc5bcc 3000:80 --namespace kube-systemЕнді компьютердегі 3000 портына барлық сұраулар қосқыштың 80 портына қайта бағытталады.
Қазір жұмыс істей ме?
- Егер иә болса, онда мәселе инфрақұрылымда. Кластерге трафиктің нақты қалай бағытталатынын анықтау қажет.
- Олай болмаса, мәселе Ingress контроллерінде.
Егер сіз Ingress контроллерін жұмысқа ала алмасаңыз, оны жөндеуге тура келеді.
Ingress контроллерінің көптеген түрлері бар. Ең танымал Nginx, HAProxy, Traefik және т.б. (қолданыстағы шешімдер туралы қосымша ақпаратты қараңыз - шамамен. аудар.) Тиісті контроллер құжаттамасындағы ақауларды жою нұсқаулығын қараңыз. Өйткені ең танымал Ingress контроллері болып табылады, біз онымен байланысты мәселелерді шешу үшін мақалаға кейбір кеңестерді қостық.
Ingress Nginx контроллерін жөндеу
Ingress-nginx жобасында ресми тұлға бар . Команда kubectl ingress-nginx келесі мақсаттарда пайдалануға болады:
- журналдарды, серверлерді, сертификаттарды және т.б. талдау;
- Ingress байланысы;
- ағымдағы конфигурацияны зерттеу.
Төмендегі үш пәрмен сізге осыған көмектеседі:
-
kubectl ingress-nginx lint— тексередіnginx.conf; -
kubectl ingress-nginx backend— серверді зерттейді (ұқсасkubectl describe ingress <ingress-name>); -
kubectl ingress-nginx logs— журналдарды тексереді.
Кейбір жағдайларда жалаушаны пайдаланып Ingress контроллері үшін дұрыс аттар кеңістігін көрсету қажет болуы мүмкін екенін ескеріңіз --namespace <name>.
Резюме
Неден бастау керектігін білмесеңіз, Kubernetes ақауларын жою қиын болуы мүмкін. Сіз әрқашан мәселеге төменнен жоғары қарай жақындауыңыз керек: подкасттардан бастаңыз, содан кейін қызмет пен кіруге өтіңіз. Осы мақалада сипатталған жөндеу әдістерін басқа нысандарға қолдануға болады, мысалы:
- бос жұмыс орындары және CronJobs;
- StatefulSets және DaemonSets.
ризашылығымды білдіремін , и құнды пікірлер мен толықтырулар үшін.
Аудармашыдан PS
Біздің блогта да оқыңыз:
- ««;
- ««;
- ««;
- ««.
Ақпарат көзі: www.habr.com
