从在Mac上本地Docker中部署的服务中访问本地Kafka(包括Kubernetes扩展)

Maa*_*mon 4 apache-kafka docker kubernetes docker-for-mac

  • 我在OSX上本地工作。
    • 我在本地模式下使用Kafka和zookeeper。我的Kafka装置中的意思是zookeeper。一节点集群。
    • 两者都在回送本地主机上工作

zookeeper.connect=localhost:2181

  • 我的/etc/host样子如下:
127.0.0.1         localhost MaatPro.local  
255.255.255.255   broadcasthost  
::1               localhost MaatPro.local  
fe80::1%lo0       localhost MaatPro.local
Run Code Online (Sandbox Code Playgroud)
  • 我的机器上安装了Mac版的docker,带有Kubernetes扩展名。

我的情况

  • 我有一个Akka流微服务dockerized,它从外部数据库读取数据并将其写入Kafka主题。它用作引导服务器:

"localhost:9092"

问题

  • 当我直接在计算机上运行服务时(例如,命令行或从Intellij内部运行),一切正常。当我在本地Docker或Kubernetes上运行它时,出现以下错误:

(o.a.k.clients.NetworkClient) [Producer clientId=producer-1] Connection to node 0 could not be established. The broker may not be available.

使用Kubernetes,我构建了以下YAML文件来部署我的Pod:

apiVersion: v1
kind: Pod
metadata:
  name: fetcher
spec:
  hostNetwork: true
  containers:
   - image: entellectextractorsfetchers:0.1.0-SNAPSHOT
     name: fetcher
Run Code Online (Sandbox Code Playgroud)

我采取了预防措施来设置hostNetwork:true

直接使用Docker守护程序,我最初也尝试将网络设置为主机,但是发现这不适用于Mac的docker。因此,我放弃了那条路线。我知道这与虚拟化有关。

1)Docker发生的虚拟化问题是否与我的本地kubernetes相同?基本上,主机网络是虚拟机,而不是我的mac?

2)我尝试更改代码,并根据文档添加以下地址作为引导服务器:host.docker.internal。但是问题仍然存在。基本问题是我正在使用环回地址的事实吗?我确实可以在我的网络地址上工作吗?host.docker.internal指向哪个地址?如何使其与环回地址一起使用?如果我完全不了解,对实现该功能需要执行的任何想法?

非常感谢您对此的任何帮助。

Maa*_*mon 5

基于@ cricket_007指导Kafka Listeners-解释以及在此问题上到处都有的阅读文章,包括我想从容器连接到主机上的服务方的正式docker文档

我想出了以下解决方案。

我将以下内容添加到默认的本地kafka配置(即server.properties)中

listeners=EXTERNAL://0.0.0.0:19092,INTERNAL://0.0.0.0:9092
listener.security.protocol.map=INTERNAL:PLAINTEXT,EXTERNAL:PLAINTEXT
advertised.listeners=INTERNAL://127.0.0.1:9092,EXTERNAL://docker.for.mac.localhost:19092
inter.broker.listener.name=INTERNAL
Run Code Online (Sandbox Code Playgroud)

实际上,这里的External 有望成为docker网络。此配置仅用于我的OSX机器,用于我的本地开发目的。我不希望连接到我的笔记本电脑的人使用我的本地kafka,因此我可以使用EXTERNAL://docker.for.mac.localhost:19092.这是广告到docker / kube中我的容器的东西。从该网络中可以访问docker.for.mac.localhost。

请注意,这可能不适用于Minikube。这是特定于Docker For Mac的。我在机器上运行的kubernetes是docker for mac附带的,而不是minikube。

最后,在我的代码中,我在列表中同时使用了两者

"localhost:9092, docker.for.mac.localhost:19092"
Run Code Online (Sandbox Code Playgroud)

我使用typeSafe config,因此在prod中,它被env变量删除。如果未指定env变量,则使用该变量。当我运行我从Intellij的微服务时localhost:9092。那是因为在这种情况下,我与我的机器中的kafka / zookeeper位于同一网络中。但是,当我从docker / kube运行相同的微服务时docker.for.mac.localhost:19092

回答我的附带问题

  1. 是。Docker for Mac将HyperKit用作轻量级虚拟机,并在其上运行linux,并在其上运行Docker Engine。Docker for MAC Kubernetes扩展基本上是关于在Docker守护程序中将kubernetes集群服务/基础架构作为容器运行。Docker for Mac与Docker Toolbox。换句话说,主机是hyperkit,而不是osx。但是正如上面的文档所解释的那样,Mac的Docker实施就是要让它在用户看来就像OSX和Docker之间没有虚拟化一样。

    • 使用环回地址连接到主机是尚未解决的问题。我什至不确定即使主机是Linux,它也能完美运行。不确定,这时可能已经解决。尽管如此,仍然需要通过声明容器或Pod(如果是kube)在主机网络上来运行映像。但是在Mac版Docker中,根据我的在线阅读资料,该功能将永远无法使用。因此,使用docker.for.mac.localhosthost.docker.internal的解决方案使Docker for Mac设置为引用mac主机而不是hyperkit主机。

    • host.docker.internaldocker.for.mac.localhost是其中之一,最近的建议是host.docker.internal。话虽如此,该地址最初不适用于我,因为我的卡夫卡设置不好。值得准备@ criket_007链接以很好地理解http://rmoff.net/2018/08/02/kafka-listeners-explained