К виртуальной машине (ВМ) можно обращаться напрямую по её IP-адресу, но у такого подхода есть ограничения. Адрес приходится знать заранее, при пересоздании машины он может смениться, а обратиться сразу к группе машин не получится. Все эти задачи решают сервисы Kubernetes.
Сервис даёт машине или группе машин постоянное имя, за которым скрываются их адреса, и равномерно распределяет между ними запросы. Имя формируется как <SERVICE_NAME>.<NAMESPACE>.svc.<CLUSTER_NAME>, а внутри того же неймспейса достаточно короткой формы <SERVICE_NAME>.
Какой тип сервиса выбрать, зависит от задачи:
Headless— прямой доступ к конкретным машинам внутри кластера без единой точки входа;ClusterIP— единый внутренний адрес с балансировкой между машинами;NodePort— доступ извне через порт на узлах кластера;LoadBalancer— доступ извне через внешний балансировщик.
Если подключение к ВМ с узла кластера не проходит, проверьте NetworkPolicy в проекте. Политика может запрещать трафик к машине.
Машина попадает в сервис по лейблам. Проставьте машине лейбл, который сервис будет искать:
- В командной строке
- В веб-интерфейсе
Проставьте лейбл командой d8 k label:
d8 k label vm linux-vm app=nginx
Пример вывода:
virtualmachine.virtualization.deckhouse.io/linux-vm labeled
- Перейдите на вкладку «Проекты» и выберите нужный проект.
- Перейдите в раздел «Виртуализация» → «Виртуальные машины».
- Из списка выберите нужную ВМ и нажмите на её имя.
- Перейдите на вкладку «Мета».
- Нажмите кнопку «Добавить» в секции «Лейблы» или «Аннотации».
- В открывшемся окне задайте ключ и значение, затем нажмите клавишу «Enter».
- Нажмите появившуюся кнопку «Сохранить».
Headless сервис
Headless-сервис не выделяет собственный IP-адрес, а возвращает адреса самих машин. Так вы обращаетесь к конкретной машине по DNS-имени, не заводя для неё отдельную точку входа. Даже для одной машины это удобнее фиксированного адреса, потому что имя не меняется при пересоздании.
- В командной строке
- В веб-интерфейсе
Создайте сервис с clusterIP: None:
d8 k apply -f - <<EOF
apiVersion: v1
kind: Service
metadata:
name: http
namespace: default
spec:
clusterIP: None
selector:
# Лейбл, по которому сервис отбирает виртуальные машины.
app: nginx
EOF
После создания к машине можно обратиться по имени http.default.svc.
- Перейдите на вкладку «Проекты» и выберите нужный проект.
- Перейдите в раздел «Сеть» → «Services».
- Нажмите кнопку «Создать».
- В открывшейся форме в поле «Имя» введите имя сервиса.
- В поле «Тип» выберите
Headless. - В блоке «Селектор нагрузок» отметьте нужные виртуальные машины, их лейблы попадут в селектор сервиса.
- В блоке «Порты» задайте значения «Порт» и «Целевой порт».
- Нажмите кнопку «Создать».
Сервис с типом ClusterIP
ClusterIP — это стандартный тип сервиса, который предоставляет внутренний IP-адрес для доступа к сервису внутри кластера. Этот IP-адрес используется для маршрутизации трафика между различными компонентами системы и позволяет виртуальным машинам взаимодействовать друг с другом через предсказуемый и стабильный адрес.
- В командной строке
- В веб-интерфейсе
Пример конфигурации ClusterIP:
d8 k apply -f - <<EOF
apiVersion: v1
kind: Service
metadata:
name: http
spec:
selector:
# Лейбл по которому сервис определяет на какую виртуальную машину направлять трафик.
app: nginx
EOF
- Перейдите на вкладку «Проекты» и выберите нужный проект.
- Перейдите в раздел «Сеть» → «Services».
- В открывшемся окне выполните настройки сервиса.
- Нажмите кнопку «Создать».
Сервис с типом NodePort
NodePort — это расширение сервиса ClusterIP, которое обеспечивает доступ к сервису через заданный порт на всех узлах кластера. Это делает сервис доступным извне кластера через комбинацию IP-адреса узла и порта и подходит для случаев, когда внешний балансировщик не нужен.
- В командной строке
- В веб-интерфейсе
Создайте следующий сервис:
d8 k apply -f - <<EOF
apiVersion: v1
kind: Service
metadata:
name: linux-vm-nginx-nodeport
spec:
type: NodePort
selector:
# Лейбл по которому сервис определяет на какую виртуальную машину направлять трафик.
app: nginx
ports:
- protocol: TCP
port: 80
targetPort: 80
nodePort: 31880
EOF

В данном примере будет создан сервис с типом NodePort, который открывает внешний порт 31880 на всех узлах вашего кластера. Этот порт будет направлять входящий трафик на внутренний порт 80 виртуальной машины, где запущено приложение Nginx.
Если не указывать значение nodePort явно, для сервиса будет назначен произвольный порт, который можно посмотреть в статусе сервиса, сразу после его создания.
- Перейдите на вкладку «Проекты» и выберите нужный проект.
- Перейдите в раздел «Сеть» → «Services».
- Нажмите кнопку «Создать».
- В открывшейся форме в поле «Имя» введите имя сервиса.
- В поле «Тип» выберите
NodePort. - В блоке «Селектор нагрузок» отметьте нужные виртуальные машины.
- В блоке «Порты» задайте значения «Порт», «Целевой порт» и, при необходимости, «Порт узла».
- Нажмите кнопку «Создать».
Сервис с типом LoadBalancer
LoadBalancer — это тип сервиса, который автоматически создаёт внешний балансировщик нагрузки с постоянным IP-адресом. Этот балансировщик распределяет входящий трафик среди виртуальных машин, обеспечивая доступность сервиса из интернета.
- В командной строке
- В веб-интерфейсе
d8 k apply -f - <<EOF
apiVersion: v1
kind: Service
metadata:
name: linux-vm-nginx-lb
spec:
type: LoadBalancer
selector:
# Лейбл по которому сервис определяет на какую виртуальную машину направлять трафик
app: nginx
ports:
- protocol: TCP
port: 80
targetPort: 80
EOF

- Перейдите на вкладку «Проекты» и выберите нужный проект.
- Перейдите в раздел «Сеть» → «Services».
- Нажмите кнопку «Создать».
- В открывшейся форме в поле «Имя» введите имя сервиса.
- В поле «Тип» выберите
LoadBalancer. - В блоке «Селектор нагрузок» отметьте нужные виртуальные машины.
- В блоке «Порты» задайте значения «Порт» и «Целевой порт».
- Нажмите кнопку «Создать».
- Внешний адрес сервиса отображается в списке сервисов в колонке «Внешний IP».
Публикация сервисов ВМ с использованием Ingress
Ingress позволяет управлять входящими HTTP/HTTPS-запросами и маршрутизировать их к различным серверам в рамках вашего кластера. Это наиболее подходящий метод, если вы хотите использовать доменные имена и SSL-терминацию для доступа к вашим виртуальным машинам.
- В командной строке
- В веб-интерфейсе
Для публикации сервиса виртуальной машины через Ingress необходимо создать следующие ресурсы:
Внутренний сервис для связки с Ingress. Пример:
d8 k apply -f - <<EOF
apiVersion: v1
kind: Service
metadata:
name: linux-vm-nginx
spec:
selector:
# лейбл по которому сервис определяет на какую виртуальную машину направлять трафик
app: nginx
ports:
- protocol: TCP
port: 80
targetPort: 80
EOF
И ресурс Ingress для публикации. Пример:
d8 k apply -f - <<EOF
apiVersion: networking.k8s.io/v1
kind: Ingress
metadata:
name: linux-vm
spec:
rules:
- host: linux-vm.example.com
http:
paths:
- path: /
pathType: Prefix
backend:
service:
name: linux-vm-nginx
port:
number: 80
EOF

- Перейдите на вкладку «Проекты» и выберите нужный проект.
- Перейдите в раздел «Сеть» → «Ingresses».
- Нажмите кнопку «Создать».
- В открывшейся форме «Создать Ingress» в поле «Наименование» введите имя ресурса, а в поле «Ingress Class» выберите класс контроллера (
spec.ingressClassName). - В блоке «Правила» нажмите кнопку «Добавить правило (хост)» и опишите хост и пути маршрутизации на нужный сервис.
- Если требуется HTTPS, в блоке «TLS-сертификаты» нажмите кнопку «Добавить сертификат» и укажите секрет с сертификатом; при необходимости задайте «Бэкенд по умолчанию».
- Нажмите кнопку «Создать».