
当 Airflow DAG 通过 BashOperator 调用 Python 脚本时,即使已设置 PYTHONPATH,仍报 ModuleNotFoundError: No module named 'scripts.marketing_functions',根本原因在于 PYTHONPATH 指向了子目录(如 /opt/bitnami/airflow/scripts),而非其父目录——Python 导入机制要求包路径需从顶层包根目录开始解析。
当 airflow dag 通过 bashoperator 调用 python 脚本时,即使已设置 pythonpath,仍报 `modulenotfounderror: no module named 'scripts.marketing_functions'`,根本原因在于 pythonpath 指向了子目录(如 `/opt/bitnami/airflow/scripts`),而非其父目录——python 导入机制要求包路径需从**顶层包根目录**开始解析。
在您的项目结构中:
/opt/bitnami/airflow/ ├── scripts/ │ ├── __init__.py │ ├── marketing_functions.py │ └── marketing/ │ └── some_script.py # ← 此处执行 from scripts.marketing_functions import * ├── dags/ └── ...
from scripts.marketing_functions import * 是一个绝对导入(absolute import),Python 会尝试从 sys.path 中的每个目录出发,查找名为 scripts 的包(即含 __init__.py 的子目录)。因此,PYTHONPATH 必须包含 /opt/bitnami/airflow(即 scripts 所在的父目录),而不是 /opt/bitnami/airflow/scripts。
✅ 正确配置方式:
# ✅ 正确:将 airflow 根目录加入 PYTHONPATH export PYTHONPATH="/opt/bitnami/airflow:$PYTHONPATH"
⚠️ 错误示例(您当前配置):
export PYTHONPATH="/opt/bitnami/airflow/scripts" # ❌ scripts 是包名,不是包根
此时 Python 在 /opt/bitnami/airflow/scripts 下查找 scripts/ 子目录 → 找不到,故报错。
让 macOS 自动化像说话一样简单 —— 用代码控制你的 Mac,无需学习 AppleScript 系统要求 macOS 14+ (Sonoma) Python 3.9+ 需要开启:辅助功能 + 屏幕录制权限
? 验证方法(在容器内执行):
# 确保 PYTHONPATH 已更新
echo $PYTHONPATH # 应包含 /opt/bitnami/airflow
# 进入 Python 交互环境验证
python -c "import sys; print([p for p in sys.path if 'airflow' in p])"
python -c "from scripts.marketing_functions import hello_world; print('Import success!')"
? 在 Airflow 环境中持久化配置(Bitnami 镜像推荐方式):
编辑 /opt/bitnami/airflow/conf/airflow.cfg,添加或修改:
[logging] logging_level = INFO [core] # 确保以下配置启用(默认通常已启用) dags_folder = /opt/bitnami/airflow/dags plugins_folder = /opt/bitnami/airflow/plugins
并在启动 Airflow 前,通过环境变量注入(例如在 docker-compose.yml 的 environment 或容器启动脚本中):
environment:
- PYTHONPATH=/opt/bitnami/airflow:${PYTHONPATH}
? 补充建议:
- 若不希望依赖 PYTHONPATH,可在 some_script.py 开头动态插入路径(仅作临时调试):
import sys import os sys.path.insert(0, os.path.dirname(os.path.dirname(os.path.abspath(__file__)))) # 现在可安全执行: from scripts.marketing_functions import *
- 推荐统一使用相对导入(需确保以包方式运行),但 BashOperator 直接调用 .py 文件时不支持 python -m 包执行模式,故绝对导入 + 正确 PYTHONPATH 仍是生产首选。
总结:Python 包导入的本质是“路径查找”,scripts 是包名,其所在父目录才是模块搜索起点。修正 PYTHONPATH 指向 /opt/bitnami/airflow 后,所有 from scripts.xxx import yyy 形式导入即可正常工作。
Python免费学习笔记(深入):立即使用
在学习笔记中,你将探索 Python 的核心概念和高级技巧!










