In this quickstart, you deploy a Python web app (Django, Flask, or FastAPI) to Azure App Service. Azure App Service is a fully managed web hosting service that supports Python apps hosted in a Linux server environment.
To complete this quickstart, you need:
Note
This article contains current instructions on deploying a Python web app using Azure App Service. Python on Windows is no longer supported.
Skip to the endYou can quickly deploy the sample app in this tutorial using Azure Developer CLI and see it running in Azure. Just run the following commands in the Azure Cloud Shellwant, and follow the prompt:
mkdir flask-quickstart
cd flask-quickstart
azd init --template https://github.com/Azure-Samples/msdocs-python-flask-webapp-quickstart
azd up
mkdir django-quickstart
cd django-quickstart
azd init --template https://github.com/Azure-Samples/msdocs-python-django-webapp-quickstart
azd up
mkdir fastapi-quickstart
cd fastapi-quickstart
azd init --template https://github.com/Azure-Samples/msdocs-python-fastapi-webapp-quickstart
azd up
And, to delete the resources:
azd down
Sample application
This quickstart can be completed using either Flask, Django, or FastAPI. A sample application in each framework is provided to help you follow along with this quickstart. Download or clone the sample application to your local workstation.
git clone https://github.com/Azure-Samples/msdocs-python-flask-webapp-quickstart
git clone https://github.com/Azure-Samples/msdocs-python-django-webapp-quickstart
git clone https://github.com/Azure-Samples/msdocs-python-fastapi-webapp-quickstart.git
To run the application locally:
Go to the application folder:
cd msdocs-python-flask-webapp-quickstart
Create a virtual environment for the app:
py -m venv .venv
.venv\scripts\activate
python3 -m venv .venv
source .venv/bin/activate
Install the dependencies:
pip install -r requirements.txt
Run the app:
flask run
Browse to the sample application at http://localhost:5000
in a web browser.
Having issues? Let us know.
Go to the application folder:
cd msdocs-python-django-webapp-quickstart
Create a virtual environment for the app:
py -m venv .venv
.venv\scripts\activate
python3 -m venv .venv
source .venv/bin/activate
Install the dependencies:
pip install -r requirements.txt
Run the app:
python manage.py runserver
Browse to the sample application at http://localhost:8000
in a web browser.
Having issues? Let us know.
Go to the application folder:
cd msdocs-python-fastapi-webapp-quickstart
Create a virtual environment for the app:
py -m venv .venv
.venv\scripts\activate
python3 -m venv .venv
source .venv/bin/activate
Install the dependencies:
pip install -r requirements.txt
Run the app:
uvicorn main:app --reload
Browse to the sample application at http://localhost:8000
in a web browser.
Having issues? Let us know.
Create a web app in AzureTo host your application in Azure, you need to create an Azure App Service web app in Azure. You can create a web app using the Azure CLI, VS Code, Azure Tools extension pack, or the Azure portal.
Azure CLI commands can be run on a computer with the Azure CLI installed.
Azure CLI has a command az webapp up
that will create the necessary resources and deploy your application in a single step.
If necessary, log in to Azure using az login.
az login
Create the webapp and other resources, then deploy your code to Azure using az webapp up.
az webapp up --runtime PYTHON:3.13 --sku B1 --logs
--runtime
parameter specifies what version of Python your app is running. This example uses Python 3.13. To list all available runtimes, use the command az webapp list-runtimes --os linux --output table
.--sku
parameter defines the size (CPU, memory) and cost of the app service plan. This example uses the B1 (Basic) service plan, which will incur a small cost in your Azure subscription. For a full list of App Service plans, view the App Service pricing page.--logs
flag configures default logging required to enable viewing the log stream immediately after launching the webapp.--name <app-name>
. If you don't provide one, then a name will be automatically generated.--location <location-name>
where <location_name>
is an available Azure region. You can retrieve a list of allowable regions for your Azure account by running the az appservice list-locations
command.The command may take a few minutes to complete. While the command is running, it provides messages about creating the resource group, the App Service plan, and the app resource, configuring logging, and doing ZIP deployment. It then returns a message that includes the app's URL, which is the app's URL on Azure.
The webapp '<app-name>' doesn't exist Creating Resource group '<group-name>' ... Resource group creation complete Creating AppServicePlan '<app-service-plan-name>' ... Creating webapp '<app-name>' ... Configuring default logging for the app, if not already enabled Creating zip with contents of dir /home/cephas/myExpressApp ... Getting scm site credentials for zip deployment Starting zip deployment. This operation can take a while to complete ... Deployment endpoint responded with status code 202 You can launch the app at <URL> { "URL": "<URL>", "appserviceplan": "<app-service-plan-name>", "location": "centralus", "name": "<app-name>", "os": "<os-type>", "resourcegroup": "<group-name>", "runtime_version": "python|3.13", "runtime_version_detected": "0.0", "sku": "FREE", "src_path": "<your-folder-location>" }
Note
The az webapp up
command does the following actions:
Create a default resource group.
Create a default App Service plan.
Create an app with the specified name.
Zip deploy all files from the current working directory, with build automation enabled.
Cache the parameters locally in the .azure/config file so that you don't need to specify them again when deploying later with az webapp up
or other az webapp
commands from the project folder. The cached values are used automatically by default.
To create Azure resources in VS Code, you must have the Azure Tools extension pack installed and be signed into Azure from VS Code.
Download Azure Tools extension pack
In the application folder, open VS Code:
code .
Sign in to the Azure portal and follow these steps to create your Azure App Service resources.
Instructions Screenshot In the Azure portal:For this example, under Dev/Test, select the Basic B1 plan. The Basic B1 plan will incur a small charge against your Azure account but is recommended for better performance over the Free F1 plan.
When finished, select Select to apply your changes.
On the main Create Web App page, select the Review + create at the bottom of the screen.This will take you to the Review page. Select Create to create your App Service.
Having issues? Let us know.
Deploy your application code to AzureAzure App Service supports multiple methods to deploy your application code to Azure, including GitHub Actions and all major CI/CD tools. This article focuses on how to deploy your code from your local workstation to Azure.
Since the az webapp up
command created the necessary resources and deployed your application in a single step, you can move on to the next step.
Since the previous step created the necessary resources and deployed your application in a single step, you can move on to the next step.
Applications can be deployed to Azure by creating and uploading a ZIP file of the application code to Azure. ZIP files can be uploaded to Azure using the Azure CLI or an HTTP client like cURL.
Enable build automationWhen deploying a ZIP file of your Python code, you need to set a flag to enable Azure build automation. The build automation will install any necessary requirements and package the application to run on Azure.
Build automation in Azure is enabled by setting the SCM_DO_BUILD_DURING_DEPLOYMENT
app setting in either the Azure portal or Azure CLI.
Use the az webapp config appsettings set command to set the SCM_DO_BUILD_DURING_DEPLOYMENT
setting to a value of true
.
# Change these values to the ones used to create the App Service.
RESOURCE_GROUP_NAME='msdocs-python-webapp-quickstart'
APP_SERVICE_NAME='msdocs-python-webapp-quickstart-123'
az webapp config appsettings set \
--resource-group $RESOURCE_GROUP_NAME \
--name $APP_SERVICE_NAME \
--settings SCM_DO_BUILD_DURING_DEPLOYMENT=true
# Change these values to the ones used to create the App Service.
$resourceGroupName='msdocs-python-webapp-quickstart'
$appServiceName='msdocs-python-webapp-quickstart-123'
az webapp config appsettings set `
--resource-group $resourceGroupName `
--name $appServiceName `
--settings SCM_DO_BUILD_DURING_DEPLOYMENT=true
Create a ZIP file of your application
Next, create a ZIP file of your application. You only need to include components of the application itself. You do not need to include any files or directories that start with a dot (.
) such as .venv
, .gitignore
, .github
, or .vscode
.
On Windows, use a program like 7-Zip to create a ZIP file needed to deploy the application.
On macOS or Linux, you can use the built-in zip
utility to create a ZIP file.
zip -r <file-name>.zip . -x '.??*'
Upload the ZIP file to Azure
Once you have a ZIP file, the file can be uploaded to Azure using either Azure CLI or an HTTP client like cURL.
The az webapp deploy command can be used to upload and deploy a zip file to Azure.
# Change these values to the ones used to create the App Service.
RESOURCE_GROUP_NAME='msdocs-python-webapp-quickstart'
APP_SERVICE_NAME='msdocs-python-webapp-quickstart-123'
az webapp deploy \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME \
--src-path <zip-file-path>
# Change these values to the ones used to create the App Service.
$resourceGroupName='msdocs-python-webapp-quickstart'
$appServiceName='msdocs-python-webapp-quickstart-123'
az webapp deploy `
--name $appServiceName `
--resource-group $resourceGroupName `
--src-path <zip-file-path>
To use cURL to upload your ZIP file to Azure, you will need the deployment username and password for your App Service. These credentials can be obtained from the Azure portal.
\
character that starts with a $
, for example $msdocs-python-webapp-quickstart-123
. These credentials will be needed in the cURL command.Run the following curl
command to upload your zip file to Azure and deploy your application. The username is the deployment username obtained in step 3. When this command is run, you will be prompted for the deployment password.
Get the <URL> from your Kudu Environment:
curl -X POST \
-H 'Content-Type: application/zip' \
-u '<deployment-user>' \
-T <zip-file-name> \
<URL>
For PowerShell, make sure to enclose the username in single quotes so PowerShell does not try to interpret the username as a PowerShell variable.
curl -X POST `
-H 'Content-Type: application/zip' `
-u '<deployment-user>' `
-T <zip-file-name> `
<URL>
Depending on your network bandwidth, files usually take between 10 and 30 seconds to upload to Azure.
Having issues? Refer first to the Troubleshooting guide. If that doesn't help, let us know.
Configure startup scriptBased on the presence of certain files in a deployment, App Service automatically detects whether an app is a Django or Flask app and performs default steps to run your app. For apps based on other web frameworks like FastAPI, you need to configure a startup script for App Service to run your app; otherwise, App Service runs a default read-only app located in the opt/defaultsite folder.
To learn more about how App Service runs Python apps and how you can configure and customize its behavior with your app, see Configure a Linux Python app for Azure App Service.
App Service automatically detects the presence of a Flask app. No additional configuration is needed for this quickstart.
App Service automatically detects the presence of a Django app. No additional configuration is needed for this quickstart.
For FastAPI, you must configure a custom startup command for App Service to run your app. The following command starts Gunicorn with 2 Uvicorn worker processes: gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000 main:app
.
First, configure the startup command using the az webapp config set command.
az webapp config set \
--startup-file "gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000 main:app" \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME
Next, restart the web app using the az webapp restart command.
az webapp restart \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME
App Service automatically detects the presence of a Flask app. No additional configuration is needed for this quickstart.
App Service automatically detects the presence of a Django app. No additional configuration is needed for this quickstart.
Use Azure CLI or the Azure portal to configure the startup command.
App Service automatically detects the presence of a Flask app. No additional configuration is needed for this quickstart.
App Service automatically detects the presence of a Django app. No additional configuration is needed for this quickstart.
For FastAPI, you must configure a custom startup command for App Service to run your app. The following command starts Gunicorn with 2 Uvicorn worker processes: gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000 main:app
.
Browse to the deployed application in your web browser. You can follow a link from the Azure portal. Go to the Overview page and select Default Domain. If you see a default app page, wait a minute and refresh the browser.
The Python sample code is running a Linux container in App Service using a built-in image.
Congratulations! You've deployed your Python app to App Service.
Having issues? Refer first to the Troubleshooting guide. If that doesn't help, let us know.
Stream logsAzure App Service captures all message output to the console to assist you in diagnosing issues with your application. The sample apps include print()
statements to demonstrate this capability.
@app.route('/')
def index():
print('Request for index page received')
return render_template('index.html')
@app.route('/favicon.ico')
def favicon():
return send_from_directory(os.path.join(app.root_path, 'static'),
'favicon.ico', mimetype='image/vnd.microsoft.icon')
@app.route('/hello', methods=['POST'])
def hello():
name = request.form.get('name')
if name:
print('Request for hello page received with name=%s' % name)
return render_template('hello.html', name = name)
else:
print('Request for hello page received with no name or blank name -- redirecting')
return redirect(url_for('index'))
def index(request):
print('Request for index page received')
return render(request, 'hello_azure/index.html')
@csrf_exempt
def hello(request):
if request.method == 'POST':
name = request.POST.get('name')
if name is None or name == '':
print("Request for hello page received with no name or blank name -- redirecting")
return redirect('index')
else:
print("Request for hello page received with name=%s" % name)
context = {'name': name }
return render(request, 'hello_azure/hello.html', context)
else:
@app.get("/", response_class=HTMLResponse)
async def index(request: Request):
print('Request for index page received')
return templates.TemplateResponse('index.html', {"request": request})
@app.get('/favicon.ico')
async def favicon():
file_name = 'favicon.ico'
file_path = './static/' + file_name
return FileResponse(path=file_path, headers={'mimetype': 'image/vnd.microsoft.icon'})
@app.post('/hello', response_class=HTMLResponse)
async def hello(request: Request, name: str = Form(...)):
if name:
print('Request for hello page received with name=%s' % name)
return templates.TemplateResponse('hello.html', {"request": request, 'name':name})
else:
print('Request for hello page received with no name or blank name -- redirecting')
return RedirectResponse(request.url_for("index"), status_code=status.HTTP_302_FOUND)
You can review the contents of the App Service diagnostic logs by using the Azure CLI, VS Code, or the Azure portal.
First, you need to configure Azure App Service to output logs to the App Service filesystem by using the az webapp log config command.
az webapp log config \
--web-server-logging filesystem \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME
az webapp log config `
--web-server-logging 'filesystem' `
--name $APP_SERVICE_NAME `
--resource-group $RESOURCE_GROUP_NAME
To stream logs, use the az webapp log tail command.
az webapp log tail \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME
az webapp log tail `
--name $APP_SERVICE_NAME `
--resource-group $RESOURCE_GROUP_NAME
Refresh the home page in the app or attempt other requests to generate some log messages. The output should look similar to the following.
Starting Live Log Stream ---
2021-12-23T02:15:52.740703322Z Request for index page received
2021-12-23T02:15:52.740740222Z 169.254.130.1 - - [23/Dec/2021:02:15:52 +0000] "GET / HTTP/1.1" 200 1360 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/hello" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
2021-12-23T02:15:52.841043070Z 169.254.130.1 - - [23/Dec/2021:02:15:52 +0000] "GET /static/bootstrap/css/bootstrap.min.css HTTP/1.1" 200 0 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
2021-12-23T02:15:52.884541951Z 169.254.130.1 - - [23/Dec/2021:02:15:52 +0000] "GET /static/images/azure-icon.svg HTTP/1.1" 200 0 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
2021-12-23T02:15:53.043211176Z 169.254.130.1 - - [23/Dec/2021:02:15:53 +0000] "GET /favicon.ico HTTP/1.1" 404 232 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
2021-12-23T02:16:01.304306845Z Request for hello page received with name=David
2021-12-23T02:16:01.304335945Z 169.254.130.1 - - [23/Dec/2021:02:16:01 +0000] "POST /hello HTTP/1.1" 200 695 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
2021-12-23T02:16:01.398399251Z 169.254.130.1 - - [23/Dec/2021:02:16:01 +0000] "GET /static/bootstrap/css/bootstrap.min.css HTTP/1.1" 304 0 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/hello" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
2021-12-23T02:16:01.430740060Z 169.254.130.1 - - [23/Dec/2021:02:16:01 +0000] "GET /static/images/azure-icon.svg HTTP/1.1" 304 0 "https://msdocs-python-webapp-quickstart-123.azurewebsites.net/hello" "Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:95.0) Gecko/20100101 Firefox/95.0"
Instructions Screenshot First, you need to enable streaming logs in Azure App Service.
In the App Service section of the Azure Tools for VS Code extension, right-click on your App Service instance and select Start Streaming Logs from the menu.
The console logs appear in the VS Code Output window. Refresh the home page in the app or attempt other requests to generate some log messages.You'll see any log messages generated by your app as well as other messages generated by the service in the output.
Instructions Screenshot First, you need to enable streaming logs in Azure App Service. Navigate to the page for the App Service instance in the Azure portal.You'll see any log messages generated by your app and messages generated by the service in the output.
Having issues? Refer first to the Troubleshooting guide. If that doesn't help, let us know.
Clean up resourcesWhen you're finished with the sample app, you can remove all of the resources for the app from Azure. Removing the resource group ensures that you don't incur extra charges and helps keep your Azure subscription uncluttered. Removing the resource group also removes all resources in the resource group and is the fastest way to remove all Azure resources for your app.
Delete the resource group by using the az group delete command.
az group delete \
--name msdocs-python-webapp-quickstart \
--no-wait
The --no-wait
argument allows the command to return before the operation is complete.
Follow these steps while signed-in to the Azure portal to delete a resource group.
Having issues? Let us know.
Next stepsTutorial: Python (Flask) web app with PostgreSQL
Tutorial: Python (Django) web app with PostgreSQL
Add user sign-in to a Python web app
Tutorial: Run a Python app in a custom container
Secure an app with a custom domain and certificate
RetroSearch is an open source project built by @garambo | Open a GitHub Issue
Search and Browse the WWW like it's 1997 | Search results from DuckDuckGo
HTML:
3.2
| Encoding:
UTF-8
| Version:
0.7.4