GitHub Actions中Spark写入Kafka容器主题失败的排查求助
解决Spark写入Kafka时DNS解析失败的问题
问题核心原因
你用docker exec通过localhost:9093能创建主题,但Spark用kafka:9092连不上,本质是两个问题:
- Kafka容器的通告监听地址配置不匹配,导致外部服务无法通过
kafka:9092访问 - GitHub Workflow中Kafka与Spark(测试环境)的网络未打通,导致DNS无法解析
kafka主机名
具体解决方案
1. 修正Kafka容器的监听配置
启动Kafka时必须明确设置KAFKA_LISTENERS和KAFKA_ADVERTISED_LISTENERS环境变量,确保容器内/外的服务都能正确访问:
docker run -d --name kafka-broker \ -e KAFKA_LISTENERS=PLAINTEXT://0.0.0.0:9092,PLAINTEXT_HOST://0.0.0.0:9093 \ -e KAFKA_ADVERTISED_LISTENERS=PLAINTEXT://kafka:9092,PLAINTEXT_HOST://localhost:9093 \ -e KAFKA_ZOOKEEPER_CONNECT=zookeeper:2181 \ --network=ci-test-network \ confluentinc/cp-kafka:latest
PLAINTEXT://kafka:9092:供容器网络内的服务(比如Spark测试)访问PLAINTEXT_HOST://localhost:9093:供宿主机(比如docker exec命令)访问
2. 确保所有容器在同一自定义网络
在GitHub Workflow中,先创建一个自定义Docker网络,再把Zookeeper、Kafka、测试容器(或Spark)都加入该网络:
# 创建自定义网络 docker network create ci-test-network # 启动Zookeeper(示例) docker run -d --name zookeeper \ -e ZOOKEEPER_CLIENT_PORT=2181 \ --network=ci-test-network \ confluentinc/cp-zookeeper:latest # 启动Kafka(同上一步的命令) # 启动测试容器/Spark时同样加上--network=ci-test-network参数
自定义网络默认支持容器名解析,这样测试环境就能通过kafka主机名找到Kafka容器。
3. 修正Spark代码的错误配置
代码中test-topic未加引号,会被当作变量导致语法错误,同时确认bootstrap地址与Kafka通告地址一致:
df = # df creation code df.write.format("kafka") .option("kafka.bootstrap.servers", "kafka:9092") .option("kafka.security.protocol", "PLAINTEXT") .option("topic", "test-topic") # 这里必须加引号 .save()
4. 调试网络连通性(可选)
在运行测试前,先验证测试环境能否访问Kafka:
# 在测试容器内ping Kafka容器名,检查DNS解析 docker exec your-test-container ping -c 3 kafka # 测试9092端口是否可访问 docker exec your-test-container nc -zv kafka 9092
如果ping不通,检查网络是否正确;如果nc连接失败,检查Kafka的监听配置。
内容的提问来源于stack exchange,提问作者Panda
相关产品推荐
相关产品推荐

