В данном *сравнении* приняли участие след. ingress controller:
  • Kong Ingress
  • Traefik
  • Voyager
  • Haproxy
  • Gloo
  • Kubernetes nginx
  • Ambassador
  • Istio
Хотели найти Ingress, который удовлетворял все наши потребности. А именно:
  • Возможность добавлять заголовок
  • Добавлять CORS
  • Менять max-body-size
  • regex в ингрессах. например: /(lol|lil)
  • проброс сокетов
  • воможность менять hostNetwork и DaemonSet\Deployment из values.yaml helm
Теперь кратко по каждому.

Ambassador

site: https://www.getambassador.io/

helm chart: https://github.com/datawire/ambassador-chart

Первым делоим идем на сайт, и смотрим инструкцию по установки. Сразу натыкаемся на странный пункт: manifest_sorter.go:175: info: skipping unknown hook: "crd-install"
Since this hook is required for Helm 2 support it IS NOT AN ERROR AND CAN BE SAFELY IGNORED.

хм, ну ок. дальше есть еще один:

edgectl install automatically configures TLS for your instance and provisions a domain name for your Ambassador Edge Stack. This is not necessary if you already have a domain name and certificates.

забегая вперед: опытным путем выяснил, что если edgectl фейлится после установке кнтроллера helm-ом, то она молча его удаляет. лол

values.yaml - тут все хорошо. Можем указать DaemonSet и hostNetwork. Есть заготовки resources, autoscaling и др. Из минусов могу отметить только то, что по умочанию занят порт 8080, который у нас уже используется и hostNetwork так просто не включить/ Но это можно исправить.

После правки хелм велью и установки ингресса получаем свой ds и пару svc, что не может не радовать. Так-же радует отсутствие лишнего говна, которое присутствует, например, у Kong. Добавляем антоацию вида kubernetes.io/ingress.class: ambassador и проверяем. Сразу узнаем об одной особенности: 80 по умолчанию отправляет нас на 443 (похоже, зашито в контроллере). По 443 видим свой сайт - радуемся. Если зайти по биндам 80\443, то попадаем на страницу с поздравлением и предложением скачать edgectl

Repeat users can log in to the Edge Policy Console directly with this command: edgectl login --namespace=ambassador 35.241.197.154:31012

В процессе более глубокого погружения в документацию узнаем:

  • Ingress с точки зрения ambassador, слишком *громозткий* и лучше использовать kind: Mapping
  • Параметры (например max_connections) надо менять через Mapping
    circuit_breakers:
    - max_connections: 2048
    
  • надо глобально? не беда! поможет новый Kind
    kind:  Module
    ...
    spec:
        config:
            circuit_breakers:
            - max_connections: 2048
    
  • А как же корс? а его через Mapping
    spec:
        prefix: /cors/
        service: cors-example
        cors:
    
  • регексп? есть
    apiVersion: getambassador.io/v2
    kind: Mapping
    metadata:
        name:  qotm
    spec:
        prefix: "/(v1|v2)/qotm/.*"
        prefix_regex: true
        service: qotm
    
  • и еще некоторое колличество Kind. Зачем? ну так надо.

по итогу:

Удовлетворяет всем требованиям. Осталось понять, что должно заставить переписать все Ingress для полного погружения в мир ambassador. Отдельный плюс за документацию: подробно с yaml примерами.

Voyager

site: https://voyagermesh.com/

helm chart: https://github.com/voyagermesh/installer/tree/release-13.0/charts/voyager

Первым делом, просматриваем инструкцию по установки и видим, что нам подходит только версия бета(т.к. у нас k8s v18). Стейбл вышла 18 мая, а сейчас 11 ноября. Пол года нзаад - похоже все очень стабильно)

Voyager           Kubernetes Version
v13.0.0-beta.1    1.14.x+
v12.0.0           1.11.x - 1.17.x
Делать нечего - ставим v13.0.0-beta.1.

values.yaml - достаточно скудный. Нельзя выкрутить даже DaemonSet или hostNetwork что для нас является достаточно важным. Замечаем, что ингресс использует apiserver.

If true, generates on install/upgrade the certs that allow the kube-apiserver to authenticate operators pods. Otherwise specify certs in `apiserver.servingCerts.{caCrt, serverCrt, serverKey}`

Все выглядит так, когбуд-то его использует узкий круг лиц и их все устраивает.

После установки и попытки применить тестовый ингресс получаем ошибку: Error from server (InternalError): error when creating "ingress.yaml": Internal error occurred: failed calling webhook "admission.voyager.appscode.com": the server is currently unable to handle the request

погуглив находим ответ: Run kubectl delete validatingwebhookconfiguration admission.voyager.appscode.com That should fix the issue.

Проверяем и правда - помогло. После удаления можем добавить свой ингресс. Смотрим, что происходит в namespace куда добавили ingress.yaml Но в нем появился не только ingress.voyager.appscode.com/petstore-ingress-voyager2 который мы добавили, а еще и Deployment(deployment.apps/voyager-petstore-ingress-voyager2) и service (service/voyager-petstore-ingress-voyager2). Похоже Voyager создает свой контроллер в каждом неймспейсе, где используется apiVersion: voyager.appscode.com/v1beta1. Чудесное решение.

В остальном, если не замечать (apiVersion: voyager.appscode.com/v1beta1) и созданных контроллеров для каждого ns, все достаточно штатно: возможность добавлять заголовок, CORS, nax-body-size - через annotations; возможность использовать regex есть; возможность менять hostNetwork и DaemonSet\Deployment из values.yaml helm - нет.

По итогу: Сомнительное решение по поводу контроллеров и использование apiServer. Настораживает частота входа обновлений и поддержка новых версий k8s. Так-же смущает *частота* ответов на вопросы на git(есть достаточно спорные вопросы, но это не значит что их надо игнорить). Радует отсутствие *лишних* Kind и документация.

После helm uninstall созданные Deployment-ы в namespace-ах где создавали ingress - оставляет. Скорее всего для того, чтоб все не упало(при удалении\обновлении), с другой: СЕРЬЕЗНО?

Haproxy

site: https://www.haproxy.com/documentation/kubernetes/latest/installation/

helm chart: https://github.com/haproxytech/helm-charts

Первое что бросается в глаза - наличие Enterprise версии. По своему опыту, могу сказать, что часто это значит, что вкусняшки и новыи фичи по началу будут только в Enterprise версии. Хорошо, что это не аксиома и каждая компания сама для себя решает что делать с платной версией своего софта. Для себя отметил только 24x7 Support.

values.yaml - очень хорошо продуманная структура файла, есть все необходимое. Для нас является плюсом, что без всяких проблем можно включить DaemonSet и HostNetwork (тут это useHostNetwork).

Устанавливается без единной проблемы.

Документация на высоте. На первый взгляд кажется, что информации представлено мало. Но когда начинаешь читать\искать\смотреть, то осознаешь, что был не прав. Все выверено, воды нет, примеры есть. Одним словом -красота.

Расширения функционала происходит за счет добавления annotations для Ingress, Service, ConfigMap. Можно управлять blacklist, создавать health-check, управлять CORS, лимитами и многое другое.

Выглядит как хорошо отлаженный, выверенный продукт.

По итогу: На первый взгляд выглядит как хорошо отлаженный, выверенный продукт. Часто выходят новые Releases что свидетельствует о модофикации и модорнезации продукта. Есть только одна особенность: под капотом haproxy, но это не плохо.
Можно смело использовать.

Traefik

site: https://traefik.io/

helm chart: https://github.com/traefik/traefik-helm-chart/tree/master/traefik

По моему мнение, достаточно неудачно составлен сайт. Сложно найти интересующую документацию, все перепутано. values.yaml - поменять DaemonSet и HostNetwork нельзя, зато много *полезных* фич: включение Pilot integration и exerimental features. А это все точно про Ingress?))

После установки появляется 1 Deployment и 1 Service - что уже радует.

Что же дальше? Давайте протестируем Ingress? А как?

И после этого вопроса, Вы начинаете погружаться в документацию. Находите отрывистые куски, которые непонятно где и как использовать. А в какой-то момент находите всего два раздела: kubernetes-ingress и Kubernetes IngressRoute. А все что было до этого, относиться к самому traefik и ничего общего с Ingress controller не имеет. Чудесная документация. Спасибо тебе doc.traefik.io

Вру конечно, но часто не понятно к чему относиться кусок кода. Где-то есть универсальный разделы, зайдя в который можно увидеть пример выбрав Kubernetes, а где то вы все еще думаете: мне точно это нужно и как вкорячить это и главное куда..

Из коробки есть dashbord на котором можно видеть, все что обслуживает traefik. Показываются ошибки, созданные ресурсы. Всегда удобно увидеть визуально то, что понасоздавали (лично мне). За это траефику большой +.

Погружаясь дальше:
есть у Траефика сущность kind: Middleware за счет которой вы делаете почти все: меняете CORS, body_size, тайминги и пр.

Звучит круто - создаем.
apiVersion: traefik.containo.us/v1alpha1
kind: Middleware
metadata:
  name: limit20m
spec:
  buffering:
    maxRequestBodyBytes: 20000000

И цепляем через анотации ингрессу. traefik.ingress.kubernetes.io/router.middlewares: limit20m

Проверяем - фиг. Смотрим через dashbord там не прицепилось. Методом гугла и тыка находим, что надо название указывать вида: namespace_limit20m@kubernetescrd. Если вы решили middlewares создать в namespace default, то надо указать: default_limit20m@kubernetescrd

Прикольно конечно, что можно создать все middlewares в одном месте и потом за счет annotations цеплять их повсюду, но как мы могли узнать формат для меня остается загадка.

Задавшись вопросом: а как надо, узнаем, что traefik предлагает вместо Ingress использовать kind: IngressRoute и в нем уже указывать просто названия которые мы создали и ходим применить для конкретного IngressRoute:

    middlewares:
      - name: limit20m
      - name: cors 

Для примера, мой тестовый yaml выглядит так:

apiVersion: traefik.containo.us/v1alpha1
kind: IngressRoute
metadata:
  name: test
  namespace: default
spec:
  entryPoints:
    - web
  routes:
  - match: Host(`test.route.ru`) 
    kind: Rule
    services:
    - name: nginx
      port: 80
      namespace: default
  - match: |
          Host(`test.route.rur`) && 
          PathPrefix(`/foo`)
    kind: Rule
    services:
    - name: nginx
      port: 80
    middlewares:
      - name: limit20m
      - name: cors

entryPoints - будем считать как сбинженный порт. Удобно, можно понасоздавать entryPoints (80, 8080,443 и т.д.) и дать им разные имена, а затем за счет обычного тегирования накидывать. Мне показался данный подход удобным.

Схема получается такая: приходит запрос который попадает на entryPoints, после на подходящий routes, а дальше или сразу на Kubernetes Service за счет Rule или сначала пред обрабатывается за счет middlewares.

По итогу: достаточно хороший продукт, есть прикольные плюшки(dashboard). Из минусов:
на мой взгляд, отвратительная документация и нет возможности использовать калсс Ingress без IngressRoute и middlewares. А половинчетое использование порождает проблемы.

kubernetes nginx

Про него не буду много говорить. Хорошая документация, частые обновления, обширное комьюнити, есть все необходимое. Из минусов: иногда, новый релиз порождает новые баги. Впрочем, у всех такое может быть.

Kong Ingress

кратко: говно

Gloo

кратко: говно

Istio

site: https://istio.io/

helm chart: deprecated

На первый взгляд кажется очень простым Ingress controllerom, но после первой же попытки установки мнение меняется.

Имеет великолепный туториал, по которому каждый от мала до велика сможет поставить его и протестировать. В ходе прохождения мы узнаем об основных классах: gateways, virtualservices и destinationrules. Начинаем понимать как с ними работать. У istio есть даже Dashbord под названием kiali.

Dashbord - очень крутой. По мимо ресурсов, которые находятся в k8s мы видим взаимодействие подов на сетевом уровне с сигнализированием активностей и ошибок возникающих в процессе передачи данных. Можем просматривать ресурсы gateways, virtualservices и destinationrules: подсветка синаксиса, уведомление об ошибках, а также есть возможность править yaml файлы прямо из web интерфейса.

В istio есть поддержка штатного Ingress, включается за счет добавления анотации. Но весь функционал раскрывается только после использования Istio-вских ресурсов. Как сказано на сайте: расширяет функционал. Но все это не будет работать, если Вы не включите istio-injection, который может включается как на весь неймспейс, так и на опр. деплоимент. istio-injection добавляет каждому pod-у дополнительный контейнер, который берет на себя управление сетевым трафиком.

Туториал - как я и писал ранее - отчень крутой. Но есть момент: он не объясняет механику взаимодействия. А т.к. istio-injection шифрует весь трафик, то и отследить не так уж и просто. И получается, что вы понимаете как управлять всем, но не понимаете как оно работает.

Итого:
Istio представляет достаточно мощный firewall\ingress\controller, которым можно управлять как из terminala, так и из Web. Имеет хорошо структуированную документацию, с очень подробным разбором *что делать и где*.
К минусам хочу отнести два момента:
1) Достаточно *тяжелый* и требовательный к ресурсам.
2) Не очевидная механика взаимодействия компонентов. Как следствие, сложность траблишутинга в аварийных ситуациях. Даже механизм обновления сертификатов скрыт от администратора, за счет которых шифруется сетевое общение.