빠른 시작: Azure App Service에 Python(Django, Flask 또는 FastAPI) 웹앱 배포
아티클
참고 항목
2024년 6월 1일부터, 새로 만들어진 모든 App Service 앱에는 명명 규칙 <app-name>-<random-hash>.<region>.azurewebsites.net을 사용하여 고유한 기본 호스트 이름을 생성할 수 있는 옵션이 제공됩니다. 기존 앱 이름은 변경되지 않은 상태로 유지됩니다.
웹앱 및 기타 리소스를 만든 다음, az webapp up을 사용하여 Azure에 코드를 배포합니다.
az webapp up --runtime PYTHON:3.9 --sku B1 --logs
--runtime 매개 변수는 앱이 실행 중인 Python 버전을 지정합니다. 이 예제에서는 Python 3.9를 사용합니다. 사용 가능한 모든 런타임을 나열하려면 명령 az webapp list-runtimes --os linux --output table을 사용합니다.
--sku 매개 변수는 App Service 요금제의 크기(CPU, 메모리) 및 비용을 정의합니다. 이 예제에서는 Azure 구독에 약간의 비용이 발생하는 B1(기본) 서비스 요금제를 사용합니다. App Service 요금제의 전체 목록은 App Service 가격 책정 페이지를 참조하세요.
--logs 플래그는 웹앱을 시작한 직후 로그 스트림을 볼 수 있도록 하는 데 필요한 기본 로깅을 구성합니다.
필요에 따라 인수 --name <app-name>을 사용하여 이름을 지정할 수 있습니다. 이름을 제공하지 않으면 이름이 자동으로 생성됩니다.
선택적으로 인수 --location <location-name>을 포함할 수 있습니다. 여기서 <location_name>은 사용 가능한 Azure 지역입니다. Azure 계정에 허용되는 지역 목록은 az appservice list-locations 명령을 실행하여 검색할 수 있습니다.
이 명령을 완료하는 데 몇 분 정도 걸릴 수 있습니다. 명령이 실행되는 동안 리소스 그룹, App Service 요금제 및 앱 리소스 만들기, 로깅 구성, ZIP 배포 수행에 대한 메시지가 제공됩니다. 그런 다음, "http://<app-name>.azurewebsites.net에서 앱을 시작할 수 있습니다."라는 메시지를 제공합니다. 이 메시지는 Azure에서 앱의 URL입니다.
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 http://<app-name>.azurewebsites.net
{
"URL": "http://<app-name>.azurewebsites.net",
"appserviceplan": "<app-service-plan-name>",
"location": "centralus",
"name": "<app-name>",
"os": "<os-type>",
"resourcegroup": "<group-name>",
"runtime_version": "python|3.9",
"runtime_version_detected": "0.0",
"sku": "FREE",
"src_path": "<your-folder-location>"
}
한 단계로 az webapp up 명령을 사용해서 필요한 리소스를 만들고 애플리케이션을 배포했기 때문에 다음 단계로 넘어갈 수 있습니다.
이전 단계에서 필요한 리소스를 만들고 애플리케이션을 배포했기 때문에 다음 단계로 넘어갈 수 있습니다.
코드를 푸시하려는 리포지토리를 가리키는 로컬 리포지토리에서 Git 원격을 구성하여 로컬 Git 리포지토리에서 Azure로 애플리케이션 코드를 배포할 수 있습니다. 구성에 필요한 원격 리포지토리 및 Git 자격 증명의 URL은 Azure Portal 또는 Azure CLI를 사용하여 검색할 수 있습니다.
이 값은 이후 단계에서 Git 원격을 설정하는 데 사용되므로 Git Clone Uri의 값을 복사합니다.
배포 센터 페이지에서 다음을 수행합니다.
로컬 Git/FTPS 자격 증명 탭으로 이동합니다.
애플리케이션 범위 자격 증명에서 로컬 Git 사용자 이름과 암호를 찾습니다.
원격 리포지토리에 코드를 배포할 때 이러한 자격 증명을 일시적으로 복사할 수 있도록 이 화면을 열어두세요. $로 시작하는 로컬 git 사용자 이름(예: $msdocs-python-webapp-quickstart-123)을 복사해야 합니다.
처음으로 원격 Git 리포지토리에 코드를 푸시하는 경우 원격 리포지토리에 인증하려면 이러한 자격 증명이 필요합니다.
다음으로, 애플리케이션의 루트 디렉터리에서 이전 단계에서 가져온 Azure 원격의 Git URL을 사용하여 Azure를 가리키는 Git 원격을 구성합니다.
git remote add azure <git-deployment-url>
이제 방금 구성한 Git 원격을 사용하여 로컬 Git 리포지토리에서 Azure로 코드를 푸시할 수 있습니다. App Service의 기본 배포 분기는 master(이)지만, 많은 Git 리포지토리가 master에서 main을(를) 사용합니다. 아래와 같이 로컬 분기 이름에서 원격 분기 이름으로 매핑을 푸시에서 지정하거나 앱 설정DEPLOYMENT_BRANCH을 구성할 수 있습니다.
git push azure main:master
코드를 Azure에 처음 푸시할 때 Git은 이전 단계에서 얻은 Azure 배포 자격 증명을 묻는 메시지를 표시합니다. 그러면 Git에서 이러한 자격 증명을 캐시하므로 후속 배포에 자격 증명을 다시 입력할 필요가 없습니다.
먼저, az webapp deployment source 명령을 사용하여 웹앱의 배포 원본을 로컬 Git으로 구성합니다. 이 명령은 코드를 푸시할 원격 Git 리포지토리의 URL을 출력합니다. 이후 단계에서 필요하므로 이 값의 복사본을 만듭니다.
# 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 deployment source config-local-git \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME \
--output tsv
# 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 deployment source config-local-git `
--name $APP_SERVICE_NAME `
--resource-group $RESOURCE_GROUP_NAME `
--output tsv
애플리케이션에 대한 배포 자격 증명을 검색합니다. 이후 단계에서 Azure에 코드를 푸시할 때 Azure에 인증하려면 Git이 필요합니다.
다음으로, 애플리케이션의 루트 디렉터리에서 이전 단계에서 가져온 Azure 원격의 Git URL을 사용하여 Azure를 가리키는 Git 원격을 구성합니다.
git remote add azure <git-deployment-url>
이제 방금 구성한 Git 원격을 사용하여 로컬 Git 리포지토리에서 Azure로 코드를 푸시할 수 있습니다. App Service의 기본 배포 분기는 master(이)지만, 많은 Git 리포지토리가 master에서 main을(를) 사용합니다. 아래와 같이 로컬 분기 이름에서 원격 분기 이름으로 매핑을 푸시에서 지정하거나 앱 설정DEPLOYMENT_BRANCH을 구성할 수 있습니다.
git push azure main:master
코드를 Azure에 처음 푸시할 때 Git은 이전 단계에서 얻은 Azure 배포 자격 증명을 묻는 메시지를 표시합니다. 그러면 Git에서 이러한 자격 증명을 캐시하므로 후속 배포에서 다시 입력할 필요가 없습니다.
애플리케이션 코드의 ZIP 파일을 만들고 Azure에 업로드하여 애플리케이션을 Azure에 배포할 수 있습니다. ZIP 파일은 Azure CLI 또는 cURL과 같은 HTTP 클라이언트를 사용하여 Azure에 업로드할 수 있습니다.
빌드 자동화 사용
Python 코드의 ZIP 파일을 배포할 때 Azure의 빌드 자동화를 사용하도록 플래그를 설정해야 합니다. 빌드 자동화는 필요한 요구 사항을 설치하고 Azure에서 실행되도록 애플리케이션을 패키지합니다.
Azure에서 빌드 자동화는 Azure Portal 또는 Azure CLI에서 SCM_DO_BUILD_DURING_DEPLOYMENT 앱 설정을 설정하여 사용하도록 설정됩니다.
# 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
애플리케이션의 ZIP 파일 만들기
다음으로, 애플리케이션의 ZIP 파일을 만듭니다. 애플리케이션 자체의 구성 요소만 포함하면 됩니다. 점(.)(예: .venv, .gitignore, .github 또는 .vscode)로 시작하는 파일 또는 디렉터리를 포함할 필요가 없습니다.
# 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>
cURL을 사용하여 ZIP 파일을 Azure에 업로드하려면 App Service에 대한 배포 사용자 이름 및 암호가 필요합니다. 이러한 자격 증명은 Azure Portal에서 가져올 수 있습니다.
웹앱 페이지에서 페이지 왼쪽에 있는 메뉴에서 배포 센터를 선택합니다.
FTPS 자격 증명 탭을 선택합니다.
사용자 이름 및 암호는 애플리케이션 범위 제목 아래에 표시됩니다. ZIP 파일 배포의 경우 $로 시작하는 \ 문자 뒤의 사용자 이름 부분만 사용합니다. 예를 들면 $msdocs-python-webapp-quickstart-123입니다. 이러한 자격 증명은 cURL 명령에 필요합니다.
다음 curl 명령을 실행하여 ZIP 파일을 Azure에 업로드하고 애플리케이션을 배포합니다. 사용자 이름은 3단계에서 얻은 배포 사용자 이름입니다. 이 명령을 실행하면 배포 암호를 묻는 메시지가 표시됩니다.
배포에 특정 파일이 있는지에 따라, App Service는 앱이 Django 앱인지 또는 Flask 앱인지를 자동으로 감지하고 기본 단계를 수행하여 앱을 실행합니다. FastAPI 등의 다른 웹 프레임워크를 기준으로 하는 앱의 경우 App Service에서 앱을 실행하도록 시작 스크립트를 구성해야 합니다. 그렇지 않으면 App Service는 opt/defaultsite 폴더에 있는 기본 읽기 전용 앱을 실행합니다.
App Service는 Flask 앱의 존재를 자동으로 감지합니다. 이 빠른 시작을 위해 추가 구성이 필요하지 않습니다.
App Service는 Django 앱의 존재를 자동으로 감지합니다. 이 빠른 시작을 위해 추가 구성이 필요하지 않습니다.
FastAPI의 경우 App Service에서 앱을 실행하도록 사용자 지정 시작 명령을 구성해야 합니다. 다음 명령은 2개의 Uvicorn 작업자 프로세스 gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000 main:app을 사용하여 Gunicorn을 시작합니다.
az webapp restart \
--name $APP_SERVICE_NAME \
--resource-group $RESOURCE_GROUP_NAME
App Service는 Flask 앱의 존재를 자동으로 감지합니다. 이 빠른 시작을 위해 추가 구성이 필요하지 않습니다.
App Service는 Django 앱의 존재를 자동으로 감지합니다. 이 빠른 시작을 위해 추가 구성이 필요하지 않습니다.
Azure CLI 또는 Azure Portal을 사용하여 시작 명령을 구성합니다.
App Service는 Flask 앱의 존재를 자동으로 감지합니다. 이 빠른 시작을 위해 추가 구성이 필요하지 않습니다.
App Service는 Django 앱의 존재를 자동으로 감지합니다. 이 빠른 시작을 위해 추가 구성이 필요하지 않습니다.
FastAPI의 경우 App Service에서 앱을 실행하도록 사용자 지정 시작 명령을 구성해야 합니다. 다음 명령은 2개의 Uvicorn 작업자 프로세스 gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000 main:app을 사용하여 Gunicorn을 시작합니다.
지침
스크린샷
먼저 Azure App Service에서 시작 명령을 구성합니다. Azure Portal에서 App Service 인스턴스의 페이지로 이동합니다.
페이지 왼쪽 메뉴의 설정 제목 아래에서 구성을 선택합니다.
일반 설정 탭이 선택되어 있는지 확인합니다.
시작 명령 필드에 gunicorn -w 2 -k uvicorn.workers.UvicornWorker -b 0.0.0.0:8000 main:app을 입력합니다.
저장을 선택하여 변경 내용을 저장합니다.
계속하기 전에 설정이 업데이트되었다는 알림을 기다립니다.
다음으로, 웹앱을 다시 시작합니다.
페이지 왼쪽의 메뉴에서 개요를 선택합니다.
위쪽 메뉴에서 다시 시작을 선택합니다.
앱으로 이동
URL http://<app-name>.azurewebsites.net을(를) 사용하여 웹 브라우저에서 배포된 애플리케이션으로 이동합니다. 기본 앱 페이지가 보이면 1분을 기다렸다가 브라우저를 새로 고칩니다.
Python 샘플 코드가 기본 제공 이미지를 사용하여 App Service에서 Linux 컨테이너를 실행 중입니다.
@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)
Azure CLI, VS Code 또는 Azure Portal을 사용하여 App Service 진단 로그의 내용을 검토할 수 있습니다.
샘플 앱을 마쳤으면 Azure에서 앱에 대한 모든 리소스를 제거해도 됩니다. 리소스 그룹을 제거하면 추가 요금이 발생하지 않으며 Azure 구독을 깔끔하게 유지하는 데 도움이 됩니다. 리소스 그룹을 제거하면 리소스 그룹의 모든 리소스도 제거되며 이것이 앱에 대한 모든 Azure 리소스를 제거하는 가장 빠른 방법입니다.