Как обеспечить доступ к Deployment в Kubernetes
Комментарии (1)
Ответ сгенерирован нейросетью и может содержать ошибки
Ответ
Как обеспечить доступ к Deployment в Kubernetes
Deployment в Kubernetes — это контроллер для управления подами. Но поды имеют временные IP адреса и автоматически пересоздаются. Поэтому нужны Service и Ingress для стабильного доступа.
1. Kubernetes Service — база для доступа
Service предоставляет стабильный сетевой эндпоинт для подов.
ClusterIP (по умолчанию) — доступ только внутри кластера:
apiVersion: v1
kind: Service
metadata:
name: api-service
namespace: default
spec:
type: ClusterIP
selector:
app: api-app
ports:
- port: 80 # Порт на Service
targetPort: 8080 # Порт на поде
protocol: TCP
Использование:
# Внутри другого пода
curl http://api-service:80
# С FQDN
curl http://api-service.default.svc.cluster.local:80
NodePort — доступ с машин снаружи:
apiVersion: v1
kind: Service
metadata:
name: api-service
spec:
type: NodePort
selector:
app: api-app
ports:
- port: 80
targetPort: 8080
nodePort: 30080 # Порт на каждой ноде (30000-32767)
status:
loadBalancer: {}
Использование:
# Снаружи кластера
curl http://<node-ip>:30080
LoadBalancer — облачный балансировщик нагрузки:
apiVersion: v1
kind: Service
metadata:
name: api-service
spec:
type: LoadBalancer
selector:
app: api-app
ports:
- port: 80
targetPort: 8080
externalIPs:
- 203.0.113.1 # Опционально явно указать
Kubernetes автоматически создаст LoadBalancer в облаке (AWS, GCP, Azure).
2. Deployment + Service (связь)
# Deployment
apiVersion: apps/v1
kind: Deployment
metadata:
name: api-deployment
spec:
replicas: 3
selector:
matchLabels:
app: api-app # Ключевая метка
template:
metadata:
labels:
app: api-app # Те же лейблы
spec:
containers:
- name: api
image: myrepo/api:v1.0
ports:
- containerPort: 8080
---
# Service выбирает поды по лейблам
apiVersion: v1
kind: Service
metadata:
name: api-service
spec:
type: ClusterIP
selector:
app: api-app # Соответствует лейблам Deployment
ports:
- port: 80
targetPort: 8080
3. Ingress — внешний доступ с HTTP/HTTPS
Ingress управляет внешним доступом, поддерживает хосты и пути.
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: api-ingress
spec:
ingressClassName: nginx # Используем nginx-ingress
rules:
- host: api.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: api-service
port:
number: 80
Использование:
curl http://api.example.com/
С HTTPS и сертификатом:
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: api-ingress-secure
annotations:
cert-manager.io/cluster-issuer: letsencrypt-prod
spec:
tls:
- hosts:
- api.example.com
secretName: api-tls-secret # Cert-manager создаст сертификат
rules:
- host: api.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: api-service
port:
number: 80
С несколькими путями (URL routing):
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: multi-path-ingress
spec:
rules:
- host: example.com
http:
paths:
- path: /api
pathType: Prefix
backend:
service:
name: api-service
port:
number: 80
- path: /web
pathType: Prefix
backend:
service:
name: web-service
port:
number: 3000
- path: /admin
pathType: Prefix
backend:
service:
name: admin-service
port:
number: 9000
4. Полный пример: Deployment + Service + Ingress
# deployment.yaml
apiVersion: apps/v1
kind: Deployment
metadata:
name: spring-app
spec:
replicas: 3
selector:
matchLabels:
app: spring-app
template:
metadata:
labels:
app: spring-app
spec:
containers:
- name: app
image: myrepo/spring-app:1.0.0
ports:
- containerPort: 8080
resources:
requests:
memory: "256Mi"
cpu: "100m"
limits:
memory: "512Mi"
cpu: "500m"
livenessProbe:
httpGet:
path: /actuator/health
port: 8080
initialDelaySeconds: 30
periodSeconds: 10
readinessProbe:
httpGet:
path: /actuator/health/readiness
port: 8080
initialDelaySeconds: 5
periodSeconds: 5
---
# service.yaml
apiVersion: v1
kind: Service
metadata:
name: spring-app-service
spec:
type: ClusterIP
selector:
app: spring-app
ports:
- protocol: TCP
port: 80
targetPort: 8080
---
# ingress.yaml
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: spring-app-ingress
spec:
ingressClassName: nginx
rules:
- host: api.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: spring-app-service
port:
number: 80
Деплой:
kubectl apply -f deployment.yaml
kubectl apply -f service.yaml
kubectl apply -f ingress.yaml
# Проверка
kubectl get deployment
kubectl get service
kubectl get ingress
kubectl get pods
5. Типы Service — сравнение
| Тип | Доступ | Использование |
|---|---|---|
| ClusterIP | Только внутри кластера | Микросервисы между собой |
| NodePort | Снаружи через IP:порт узла | Разработка, тестирование |
| LoadBalancer | Облачный балансировщик | Production с облаком |
| ExternalName | Внешний DNS | Доступ к внешним сервисам |
6. Service Discovery в Kubernetes
// В Java коде приложение может обращаться к другим сервисам по имени
@RestTemplate
public class UserClient {
@Autowired
private RestTemplate restTemplate;
public User getUser(Long id) {
// Kubernetes автоматически разрешает имя в IP
String url = "http://user-service/users/" + id;
return restTemplate.getForObject(url, User.class);
}
}
7. Проверка доступа к Deployment
# Проверить поды
kubectl get pods
kubectl describe pod <pod-name>
# Логи пода
kubectl logs <pod-name>
kubectl logs -f <pod-name> # Tail логи
# Получить доступ к поду напрямую (для отладки)
kubectl port-forward pod/<pod-name> 8080:8080
# Теперь доступен на localhost:8080
# Выполнить команду в поде
kubectl exec -it <pod-name> -- /bin/sh
# Проверить Service
kubectl get svc
kubectl describe svc spring-app-service
# Проверить Ingress
kubectl get ingress
kubectl describe ingress spring-app-ingress
8. Best Practices
- Используй Service Discovery — приложения должны обращаться по имени сервиса, не по IP
- Используй Ingress для внешнего доступа (более гибко чем NodePort)
- Добавляй livenessProbe и readinessProbe — Kubernetes будет перезагружать упавшие поды
- Задавай ресурсы (requests/limits) — для корректного планирования подов
- Используй LoadBalancer в облаке — для production с автоматическим масштабированием
- Управляй трафиком через Ingress — вместо многих Service/NodePort
Кратко: Deployment создаёт поды, Service предоставляет сетевой доступ, Ingress управляет внешним доступом.