一、问题背景
使用 Kafka 客户端连接远端 Kafka 集群,程序启动后持续报错: Disconnected while requesting ApiVersion: might be caused by incorrect security.protocol,broker 返回主机名为 kafka1:9092,程序反复断开重连,无法正常消费生产消息。
现象:网络端口能通,但是客户端拿到 broker 返回的主机名 kafka1,本机无法解析该域名,导致连接失败。 根本原因:Kafka 的 advertised.listeners 返回的是主机名而非 IP,本地机器 DNS /hosts 无法解析 kafka1,客户端拿到域名后无法建立真实 TCP 连接。
二、现场拓扑简述
业务自研 Kafka 程序部署在自有服务器,无法直连内网 Kafka 集群,链路经过跳板机做 SSH 隧道转发。

约束:
完整链路: 自有服务器(自研 Kafka 转发程序) → socat 监听127.0.0.1:9092 → 转发至跳板机x.x.x.x:9093 → 跳板机 SSH 隧道 → 内网 Kafka 集群 9092
三、两种解决思路
方案 1:hosts 域名解析 + socat 端口转发
适用场景:无法修改远端 Kafka 服务端server.properties配置,不能改动线上 Kafka 集群,只能在业务应用侧做适配。
1)配置 /etc/hosts 域名映射
把 Kafka 广播返回的主机名映射到本机回环地址,让客户端解析kafka1指向本机。
echo "127.0.0.1 kafka1" >> /etc/hosts
2)socat 端口转发代理
利用 socat 做 TCP 端口转发:本地监听 端口,将流量转发到远端真实 Kafka 地址x.x.x.x:9093。 命令释义:
- TCP-LISTEN:9092,bind=127.0.0.1:仅在本机 127.0.0.1 监听 9092 端口
- fork:支持多客户端并发连接
- reuseaddr:端口可快速复用,避免服务重启端口占用报错
- TCP:x.x.x.x:9093:后端真实 Kafka 服务地址
# 临时前台后台运行
/opt/socat/bin/socat TCP-LISTEN:9092,bind=127.0.0.1,fork,reuseaddr TCP:x.x.x.x:9093 &
socat 编译部署步骤
cd /opt
tar -zxvf socat-1.8.0.0.tar.gz
cd socat-1.8.0.0
./configure –prefix=/opt/socat
make -j4
make install
# 验证版本
/opt/socat/bin/socat -V
tar -czzf socat-deploy.tar.gz socat/
cd /opt
tar -xzvf socat-deploy.tar.gz
设置 systemd 开机自启常驻服务
编写socat-forward.service单元文件,实现开机自动端口转发,进程异常自动重启。
[Unit]
Description=Socat Kafka TCP Forward
After=network.target
[Service]
ExecStart=/opt/socat/bin/socat TCP-LISTEN:9092,bind=127.0.0.1,fork,reuseaddr TCP:x.x.x.x:9093
Restart=always
[Install]
WantedBy=multi-user.target
生效命令:
systemctl daemon-reload
systemctl enable socat-forward.service
systemctl start socat-forward.service
配置完成后,启动业务 Kafka 程序,连接本地kafka1:9092即可正常工作。
方案 2:治本方案(修改 Kafka 服务端 server.properties)
如果有权限修改 Kafka 服务端,优先改服务端,不需要 socat 转发。 修改server.properties中advertised.listeners,写业务服务器可以直接访问的真实 IP 地址。
关键点:advertised.listeners是 broker 返回给客户端的连接地址,客户端会拿这个地址去连接 broker。填域名,客户端必须能解析域名;填 IP,客户端直接使用 IP 连接。
四、问题根因总结
五、socat 简单科普
socat 全称 SOcket CAT,就是一个 Linux 命令行工具,作用很简单:把两个数据流打通,双向转发数据。它常被叫做 netcat 的增强版。作用:
端口转发:把本机某个端口收到的数据,转发到另一个 IP 和端口。
协议桥接:比如 TCP ↔ UDP、TCP ↔ Unix Socket、TCP ↔ 串口。
网络调试:模拟服务端、客户端,看数据能不能通。
文件/管道/设备转发:不只是网络,还能转发文件、管道、串口设备。
SSL 隧道:给普通 TCP 连接加一层加密。
远程 Shell:也能用来建立正向或反向 Shell,但运维现场一般只用它做转发。
注意:socat 端口转发会增加一层网络开销,生产环境评估性能;bind=127.0.0.1 限制只能本机访问转发端口,提升安全性。
# 本地端口转发(同主机端口映射)
socat TCP-LISTEN:端口,bind=127.0.0.1,fork,reuseaddr TCP:目标IP:目标端口
# 双向管道简易测试(本地回环测试)
socat – TCP:127.0.0.1:28080
六、踩坑清单
- listeners:broker 本机监听哪个网卡端口;
- advertised.listeners:返回给外部客户端的访问地址。




