GitHub Actions部署Azure Python函数:已安装依赖运行时无法找到
优化Azure Python函数部署:无需打包依赖解决
ModuleNotFoundError 问题核心
GitHub Actions部署Azure Python函数时,依赖包在Runner环境安装成功,但函数运行时抛出ModuleNotFoundError: No module named 'sftplib'。临时方案是将依赖打包到.python_packages目录,但会导致部署包体积暴涨、耗时增加,需要更高效的解决方法。
原因分析
原部署流程中,依赖被安装在GitHub Runner的系统Python路径中,但Azure/functions-action@v1默认仅打包当前目录的代码文件,不会将Runner中的依赖包含到部署包中。Azure函数运行环境无法访问Runner的依赖路径,因此出现模块找不到的错误。
优化解决方案
方案1:启用Azure Oryx远程构建(推荐)
利用Azure函数内置的Oryx构建工具,部署时自动读取requirements.txt并在Azure环境中安装依赖,无需本地打包。
修改后的deploy.yaml配置
steps: - name: Checkout uses: actions/checkout@v4 - name: 'Azure Login' uses: azure/login@v2 with: client-id: ${{ env.ARM_CLIENT_ID }} subscription-id: ${{ env.ARM_SUBSCRIPTION_ID }} tenant-id: ${{ env.ARM_TENANT_ID }} - name: 'Download Azure Function publishing profile' env: AZURE_SUBSCRIPTION_ID: ${{ env.ARM_SUBSCRIPTION_ID }} FUNCTION_APP_RESOURCE_GROUP: ${{ env.ARM_RESOURCE_GROUP_NAME }} FUNCTION_APP_NAME: fa-${{ env.APP_NAME }} run: | echo "FUNCTION_APP_PUB_PROFILE=$(az functionapp deployment list-publishing-profiles --subscription $AZURE_SUBSCRIPTION_ID --resource-group $FUNCTION_APP_RESOURCE_GROUP --name $FUNCTION_APP_NAME --xml)" >> $GITHUB_ENV - name: "Deploy function" uses: Azure/functions-action@v1 with: app-name: fa-${{ env.APP_NAME }} publish-profile: ${{ env.FUNCTION_APP_PUB_PROFILE }} package: '.' enable-oryx-build: true # 强制启用Oryx远程构建
关键配置验证
- 确保函数应用的运行时版本与代码兼容:在Azure Portal的函数应用配置 > 应用程序设置中,设置
FUNCTIONS_WORKER_RUNTIME_VERSION为3.9(与你指定的Python版本一致)。 - Oryx默认会读取根目录的
requirements.txt,无需额外路径配置。
方案2:替换小众依赖包
注意到你使用的sftplib是一个版本仅为0.0.2的小众包,标准Python生态中通常使用paramiko实现SFTP功能(维护更活跃、兼容性更好)。
- 修改
requirements.txt:azure-functions matplotlib numpy paramiko # 替换sftplib pandas python-dateutil azure-identity azure-keyvault-secrets Office365-REST-Python-Client - 更新函数代码中的导入:
# 替换import sftplib为 import paramiko # 使用paramiko的SFTP客户端示例 transport = paramiko.Transport(("hostname", 22)) transport.connect(username="user", password="pass") sftp = paramiko.SFTPClient.from_transport(transport)
这个改动不仅能避免小众包的兼容性问题,还能让Oryx构建更顺畅。
方案3:使用虚拟环境优化本地构建(可选)
如果需要在本地验证依赖,但不想打包到部署包,可以利用虚拟环境隔离依赖,同时让部署工具忽略虚拟环境目录:
steps: - name: Checkout uses: actions/checkout@v4 - name: 'Azure Login' uses: azure/login@v2 with: client-id: ${{ env.ARM_CLIENT_ID }} subscription-id: ${{ env.ARM_SUBSCRIPTION_ID }} tenant-id: ${{ env.ARM_TENANT_ID }} - name: Set up Python uses: actions/setup-python@v4 with: python-version: '3.9.20' - name: Install dependencies in virtual env run: | python -m venv .venv source .venv/bin/activate pip install --upgrade pip pip install -r requirements.txt - name: 'Download Azure Function publishing profile' env: AZURE_SUBSCRIPTION_ID: ${{ env.ARM_SUBSCRIPTION_ID }} FUNCTION_APP_RESOURCE_GROUP: ${{ env.ARM_RESOURCE_GROUP_NAME }} FUNCTION_APP_NAME: fa-${{ env.APP_NAME }} run: | echo "FUNCTION_APP_PUB_PROFILE=$(az functionapp deployment list-publishing-profiles --subscription $AZURE_SUBSCRIPTION_ID --resource-group $FUNCTION_APP_RESOURCE_GROUP --name $FUNCTION_APP_NAME --xml)" >> $GITHUB_ENV - name: "Deploy function" uses: Azure/functions-action@v1 with: app-name: fa-${{ env.APP_NAME }} publish-profile: ${{ env.FUNCTION_APP_PUB_PROFILE }} package: '.' # 让部署工具跳过虚拟环境目录 exclude-files: '.venv/'
注:此方案仍需依赖Oryx远程安装依赖,虚拟环境仅用于本地验证,不会被打包部署。
总结
- 优先选择方案1+方案2:启用Oryx远程构建减少部署包体积,替换小众依赖包提升稳定性。
- 无需再将依赖安装到
.python_packages目录,部署速度会大幅提升,同时避免依赖冗余。
内容的提问来源于stack exchange,提问作者mbieren
相关产品推荐
相关产品推荐

