在Kubernetes上运行PySpark作业时遭遇依赖缺失问题求助
第一阶段错误:找不到/opt/spark目录
Unpacking an archive local://pyspark_venv.tar.gz#environment from /opt/spark to /opt/spark/./environment
Exception in thread "main" java.io.FileNotFoundException: /opt/spark
at org.apache.spark.util.Utils$.unpack(Utils.scala:597)
第二阶段错误:修改Worker镜像后仍缺失Python依赖
为解决上述问题,修改Worker镜像添加以下指令:
RUN mkdir /opt/spark/conf RUN chmod -R 777 /opt/spark/conf RUN echo "export PYSPARK_PYTHON=/opt/spark/work-dir/env/bin/python3.9" > /opt/spark/conf/spark-env.sh
且镜像内虚拟环境已安装findspark等依赖,但作业执行仍报错:
Unpacking an archive s3a://my-bucket/dependencies/spark-upload-5d9d9645-01fe-4979-8014-b9da1810d300/pyspark_venv.tar.gz#environment
from /tmp/spark-aaadcabb-bf96-4531-82c1-858389224ff4/pyspark_venv.tar.gz
to /opt/spark/./environmentFile "/tmp/spark-1a1b36e7-64d9-4460-b346-ffb4afd67860/policy_processor.py"
ModuleNotFoundError: No module named 'findspark'
1. 修复Worker镜像的目录结构与权限
- 不要仅创建
/opt/spark/conf,需确保完整的/opt/spark目录存在并开放权限(部分基础镜像默认无此目录):RUN mkdir -p /opt/spark /opt/spark/work-dir /opt/spark/conf RUN chmod -R 777 /opt/spark - 优先选择官方Spark镜像(如
apache/spark:3.5.0-python3)作为基础镜像,这类镜像已预设好/opt/spark目录结构,避免手动配置的遗漏。
2. 修正虚拟环境的路径匹配
Spark在K8s环境下会解压S3中的依赖包,但需确保PySpark能正确识别虚拟环境路径:
- 不要在
spark-env.sh中硬编码虚拟环境路径,改用Spark配置参数指定解压后的Python解释器路径:
这里spark-submit \ --conf spark.pyspark.python=/opt/spark/environment/bin/python3.9 \ --conf spark.pyspark.driver.python=/opt/spark/environment/bin/python3.9 \ # 其他参数.../opt/spark/environment对应你在--archives参数中指定的别名(即tar.gz#environment的后缀部分)。 - 打包虚拟环境时,用
venv-pack的--python-prefix参数指定解压后的目标路径,避免路径不匹配:venv-pack --python-prefix /opt/spark/environment -o pyspark_venv.tar.gz
3. 确保Spark依赖加载参数正确
提交作业时,通过--archives参数正确指定依赖包与解压别名:
spark-submit \ --master k8s://https://<k8s-api-server-address> \ --deploy-mode cluster \ --archives s3a://my-bucket/dependencies/pyspark_venv.tar.gz#environment \ --conf spark.kubernetes.container.image=your-custom-worker-image \ policy_processor.py
4. 验证镜像内Python环境一致性
- 确保Worker镜像的系统Python版本与虚拟环境版本完全一致(如均为3.9),版本不兼容会导致依赖无法被识别。
- 在Dockerfile中添加验证步骤,确认依赖安装状态:
构建镜像时若能输出RUN /opt/spark/work-dir/env/bin/pip list | grep findsparkfindspark的版本信息,说明镜像内虚拟环境配置正确。
5. 调试作业运行时环境
在作业代码中添加调试逻辑,确认虚拟环境是否被正确加载:
import sys print("当前Python路径:", sys.path) import subprocess subprocess.run([sys.executable, "-m", "pip", "list"])
从作业日志中查看输出,确认是否包含虚拟环境的site-packages目录。
内容的提问来源于stack exchange,提问作者Rodrigo Alarcón

