Search code examples
pythonazure-devopsazure-functionskuduoryx

Unable to find module after trying to install custom wheel using POST_BUILD_COMMAND in Zip Deploy task for a Python Function App on Azure


Intro

My scenario is that I want to re-use shared code from a repo in Azure DevOps across multiple projects. I've built a pipeline that produces a wheel as an artifact so I can download it to other pipelines.

The situation

Currently I have succesfully setup a pipeline that deploys the Python Function App. The app is running fine and stable. I use SCM_DO_BUILD_DURING_DEPLOYMENT=1 and ENABLE_ORYX_BUILD=1 to achieve this.

I am now in the position that I want to use the artifact (Python/pip wheel) as mentioned in the intro. I've added a step in the pipeline and I am able to download the artifact successfully. The next step is ensuring that the artifact is installed during my Python Function App Zip Deployment. And that is where I am stuck at.

The structure of my zip looks like:

__app__
 | - MyFirstFunction
 | | - __init__.py
 | | - function.json
 | | - example.py
 | - MySecondFunction
 | | - __init__.py
 | | - function.json
 | - wheels
 | | - my_wheel-20201014.10-py3-none-any.whl                            <<< this is my wheel
 | - host.json
 | - requirements.txt 

The problem

I've tried to add commands like POST_BUILD_COMMAND and PRE_BUILD_COMMAND to get pip install the wheel but it seems the package is not found (by Oryx/Kudu) when I use the command: -POST_BUILD_COMMAND "python -m pip install --find-links=home/site/wwwroot/wheels my_wheel" Azure DevOps does not throw any exception or error message. Just when I execute the function I get an exception saying: Failure Exception: ModuleNotFoundError: No module named 'my_wheel'.

My question is how can I change my solution to make sure the build is able to install my_wheel correctly.

Sidenote: Unfortunately I am not able to use the Artifacts feed from Azure DevOps to publish my_wheel and let pip consume that feed.


Solution

  • I have solved my issue by checking out the repository of my shared code and included the shared code in the function app package.

    Also I replaced the task AzureFunctionApp@1 with the AzureCLI@2 task and deploy the function app with a az functionapp deployment source config-zip command. I set the application settings via a separate AzureAppServiceSettings@1 step in the pipeline.

    AzureCLI@2: AzureCLI@2 task

    It is not the exact way I wanted to solve this because I still have to include the requirements of the shared code in the root requirements.txt as well.

    Switching the task AzureFunctionApp@1 to the AzureCLI@2 gives me more feedback in the pipeline. The result should be the same.