Кафка в кластере Кубернете - Как публиковать/употреблять сообщения извне кластера Кубернете
- У меня Кафка развернута и работает в кластере Kubernetes. Я использую это изображение из докер-хаба - https://hub.docker.com/r/cloudtrackinc/kubernetes-kafka/
- У меня есть 3 kube-узла в моем кластере kubernetes. У меня запущены 3 приложения Kafka и 3 приложения zookeeper, и у меня есть соответствующие службы zoo1, zoo2, zoo3 и kafka-1, kafka-2 и kafka-3. Я могу публиковать/потреблять изнутри кластера kubernetes, но я не могу публиковать/потреблять из-за пределов кластера kubernetes, т.е. с внешней машины, не входящей в кластер kubernetes.
- Я могу получить доступ к kube-узлам с внешней машины - в основном я могу пинговать их, используя name/ip.
- Я не использую какой-либо внешний балансировщик нагрузки, но у меня есть DNS, который может разрешить как мою внешнюю машину, так и kube-узлы.
- Использование NodePort или ExternalIP для предоставления сервиса Kafka в этом случае не работает.
- Установка
KAFKA_ADVERTISED_HOST_NAME
или KAFKA_ADVERTISED_LISTENERS
в Kafka RC YML, которые в конечном итоге устанавливают свойства ADVERTISED_HOST_NAME
/ADVERTISED_LISTENERS
в server.properties
также не помогает получить доступ к kafka из-за пределов кластера kubernetes.
Пожалуйста, предложите, как я могу публиковать/использовать вне кластера kubernetes. Большое спасибо!
Ответы
Ответ 1
У меня была та же проблема с доступом к кафке из-за кластера k8s на AWS. Мне удается решить эту проблему, используя функцию прослушивания кафки, которая с версии 0.10.2 поддерживает несколько интерфейсов.
вот как я сконфигурировал контейнер kafka.
ports:
- containerPort: 9092
- containerPort: 9093
env:
- name: KAFKA_ZOOKEEPER_CONNECT
value: "zookeeper:2181"
- name: KAFKA_LISTENER_SECURITY_PROTOCOL_MAP
value: "INTERNAL_PLAINTEXT:PLAINTEXT,EXTERNAL_PLAINTEXT:PLAINTEXT"
- name: KAFKA_ADVERTISED_LISTENERS
value: "INTERNAL_PLAINTEXT://kafka-internal-service:9092,EXTERNAL_PLAINTEXT://123.us-east-2.elb.amazonaws.com:9093"
- name: KAFKA_LISTENERS
value: "INTERNAL_PLAINTEXT://0.0.0.0:9092,EXTERNAL_PLAINTEXT://0.0.0.0:9093"
- name: KAFKA_INTER_BROKER_LISTENER_NAME
value: "INTERNAL_PLAINTEXT"
Кроме того, я настроил две службы. Один для внутреннего (без головного) и один для внешнего (LoadBalancer).
Надеюсь, это спасет людей.
Ответ 2
Я смог решить свою проблему, выполнив следующие изменения -
-
Использование NodeSelector в YML для запуска модуля kafka на конкретном узле кластера kube.
-
Установите для KAFKA_ADVERTISED_HOST_NAME
значение Kube hostName, для которого настроен этот POD Kafka (как настроено на шаге 1)
-
Откройте сервис Kafka с помощью NodePort и установите порт POD таким же, как и у открытого NodePort, как показано ниже -
spec: порты: - имя: порт broker-2: 30031 targetPort: 9092 nodePort: 30031 протокол: TCP селектор: приложение: kafka-2 broker_id: "2" тип: NodePort
Теперь вы можете получить доступ к брокерам Kafka из-за пределов кластера kube, используя host :posedPort
Ответ 3
Я решил эту проблему, используя прокси файл Confluent Kafka REST.
https://hub.docker.com/r/confluentinc/cp-kafka-rest/
Документация прокси-сервера REST находится здесь:
http://docs.confluent.io/3.1.2/kafka-rest/docs/index.html
Шаг A: Создайте изображение докеры брокерской компании Kafka, используя последнюю версию Kafka
Я использовал настраиваемое изображение брокера Kafka на основе того же изображения, которое вы использовали. Вам просто нужно обновить изображение cloudtrackinc для использования версии Kafka 0.10.1.0 или иначе это не сработает. Просто обновите файл Docker из изображения cloudertrackinc, чтобы использовать последнее изображение kurka wurstmeister и перестроить изображение докера.
- FROM wurstmeister/kafka:0.10.1.0
Я установил ADVERTISED_HOST_NAME для каждого брокера Kafka на POD IP, чтобы каждый брокер получал уникальный URL-адрес.
- name: ADVERTISED_HOST_NAME
valueFrom:
fieldRef:
fieldPath: status.podIP
Шаг B: Установите прокси-сервер cp-kafka-rest, чтобы использовать кластер брокеров Kafka
Прокси-сервер Kafka Rest должен работать в том же кластере, что и ваш кластер брокеров Kafka.
Вам нужно предоставить две переменные среды для изображения cp-kafka-rest как минимум для запуска. KAFKA_REST_HOST_NAME и KAFKA_REST_ZOOKEEPER_CONNECT. Вы можете установить KAFKA_REST_HOST_NAME для использования POD IP.
- name: KAFKA_REST_HOST_NAME
valueFrom:
fieldRef:
fieldPath: status.podIP
- name: KAFKA_REST_ZOOKEEPER_CONNECT
value: "zookeeper-svc-1:2181,zookeeper-svc-2:2181,zookeeper-svc-3:2181"
Шаг C: Выполнить прокси-сервер Kafka REST в качестве службы
spec:
type: NodePort or LoadBalancer
ports:
- name: kafka-rest-port
port: 8082
protocol: TCP
Вы можете использовать NodePort или LoadBalancer для использования одного или нескольких модулей POS-прокси Kafka.
Плюсы и минусы использования прокси-сервера Kafka REST
Плюсы:
- Вы можете легко масштабировать кластер брокеров Kafka.
- Вам не нужно выставлять брокеров Kakfa вне кластера
- Вы можете использовать loadbalancer с прокси.
- Вы можете использовать любой тип клиента для доступа к кластеру Kafka (т.е. завивка). Очень легкий вес.
Минусы:
- Другой компонент/слой поверх кластера Kakfa.
- Потребители создаются в пределах прокси-сервера. Это нужно будет отслеживать вашим клиентом REST.
- Производительность не идеальна: REST вместо собственного протокола Kafka. Хотя при развертывании нескольких прокси-серверов это может немного помочь. Я бы не использовал эту настройку для трафика большого объема. Для сообщений с низким объемом сообщений это может быть хорошо.
Итак, если вы можете жить с вышеуказанными проблемами, попробуйте попробовать Kafka Rest Proxy.
Ответ 4
В настоящее время это кажется невозможным, сетевая архитектура kafka довольно бедна в отношении этой темы. Новый потребитель использует список брокеров, которые возвращают хост zookeeper, но, к сожалению, это в другой сети, поэтому его невозможно получить от вашего локального клиента. Плохая часть kafka, это невозможно указать брокеров и серверов zookeeper. Это предотвращает доступ клиентов к системе снаружи.
Мы работали над этим на данный момент, используя busybox, где мы установили инструменты для взаимодействия с kafka. В нашем случае plunger