Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Dalam posting ini kita akan membahas penyebaran otomatis ujung ke ujung dari API web yang dibuat dengan python menggunakan Fungsi Azure dan Azure DevOps. Kami akan meliput

Show
  • Apa itu Fungsi Azure?
  • Membuat Fungsi Azure
  • Membuat Templat ARM Fungsi Azure
  • Membuat file yml Azure Pipelines untuk pengiriman berkelanjutan
  • Menyiapkan Pipeline Azure di Azure DevOps
    • Membuat grup sumber daya di Azure
    • Membuat koneksi layanan di Azure DevOps
    • Membuat grup variabel di Azure DevOps
    • Membuat saluran pipa Anda di Azure DevOps
    • Menguji API Fungsi Azure yang diterapkan

Fokusnya akan lebih pada penerapan daripada pembuatan aplikasi web, meskipun kami akan membahasnya secara singkat

Repositori untuk menyertai posting blog ini dapat ditemukan di sini

Anda dapat mengikuti dengan mem-forking repositori ini ke Proyek Anda sendiri dan mengikuti langkah-langkah di bawah ini. Tutorial ini mengasumsikan beberapa keakraban dengan platform Azure Public Cloud

Penafian cepat. Pada saat penulisan, saya saat ini adalah Karyawan Microsoft

Apa itu Fungsi Azure?

Azure Functions menyediakan komputasi tanpa server untuk Azure

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Anda dapat menggunakan Fungsi untuk

  • membangun API web
  • menanggapi perubahan basis data
  • memproses aliran IoT
  • mengelola antrian pesan
    dan banyak lagi

Dalam posting ini kami akan menggunakan Fungsi Azure untuk menggunakan API web yang ditulis dengan python

Membuat Fungsi Azure

Cara paling mudah untuk membuat aplikasi web Azure Function adalah dengan menggunakan ekstensi Azure Functions Visual Studio Code

Jika Anda ingin menjalankan fungsi Azure secara lokal, Anda dapat mengkloning repositori ke direktori lokal Anda dan menggunakan ekstensi kode Visual Studio untuk menjalankan fungsi secara lokal. Ini opsional untuk posting blog ini dan Anda dapat menjalankan sisa posting blog ini hanya dengan membagi repositori ke Proyek Azure DevOps Anda sendiri

Microsoft menyediakan tutorial untuk ini di sini. Anda harus mengikuti petunjuk untuk "Konfigurasi lingkungan Anda" dan kemudian "Jalankan fungsi secara lokal"

Saat dijalankan, Anda akan dapat membuat permintaan ke API Fungsi Azure yang berjalan secara lokal

Dalam [1]

import requests

url = "http://localhost:7071/api/sample_azure_function"
response = requests.get(url, json={'name': 'Ben Keen'})

response.text

Keluar[1]

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_

Membuat Templat ARM Fungsi Azure

Agar tetap sederhana, kami akan membuat template JSON ARM (Azure Resource Manager) untuk persyaratan minimum untuk menghosting Fungsi kami di Azure

Templat ARM digunakan untuk penerapan otomatis sumber daya ke Langganan Azure Anda menggunakan infrastruktur sebagai kode (IaC), untuk membantu Anda melakukan iterasi dan penerapan dengan cepat. Untuk informasi lebih lanjut tentang template ARM, lihat dokumentasinya di sini

Itu berarti kami akan menyebarkan

  • Paket Hosting Aplikasi Azure
  • Aplikasi Web Azure
  • Akun Penyimpanan Azure

Microsoft merekomendasikan juga menyertakan Wawasan Aplikasi saat menerapkan ke Fungsi tetapi saya akan membiarkannya sebagai latihan untuk pembaca

Template JSON ini ada di bawah, file ini dapat ditemukan di root repositori sebagai

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
7

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}

Mari kita lihat beberapa aspek dari template ARM ini

Parameter

Kami menentukan 3 parameter yang akan kami berikan saat menerapkan menggunakan saluran penerapan berkelanjutan kami. Mereka

  • 'Hello, Ben Keen. This HTTP triggered function executed successfully.'
    _8
    • Nama aplikasi web fungsi yang akan dibuat
  • 'Hello, Ben Keen. This HTTP triggered function executed successfully.'
    _9
    • Nama Akun Penyimpanan Azure yang akan dibuat
  • {
        "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
        "contentVersion": "1.0.0.0",
        "parameters": {
            "appName": {
                "type": "string",
                "metadata": {
                    "description": "The name of the function web app to create."
                }
            },
            "storageAcctName": {
                "type": "string",
                "metadata": {
                    "description": "The name of the Azure Storage Account to create."
                }
            },
            "hostingPlanName": {
                "type": "string",
                "metadata": {
                    "description": "The name of the Hosting Plan to create."
                }
            }
        },
        "functions": [],
        "variables": {},
        "resources": [
            {
                "type": "Microsoft.Storage/storageAccounts",
                "name": "[parameters('storageAcctName')]",
                "apiVersion": "2019-06-01",
                "location": "[resourceGroup().location]",
                "kind": "StorageV2",
                "sku": {
                    "name": "Standard_LRS",
                    "tier": "Standard"
                }
            },
            {
                "type": "Microsoft.Web/serverfarms",
                "apiVersion": "2018-02-01",
                "name": "[parameters('hostingPlanName')]",
                "location": "[resourceGroup().location]",
                "kind": "Linux",
                "sku": {
                    "name": "S1",
                    "tier": "Standard",
                    "size": "S1",
                    "family": "S",
                    "capacity": 1
                },
                "properties": {
                    "reserved": true
                }
            },
            {
                "type": "Microsoft.Web/sites",
                "apiVersion": "2020-06-01",
                "name": "[parameters('appName')]",
                "location": "[resourceGroup().location]",
                "kind": "functionapp,linux",
                "dependsOn": [
                    "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                    "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
                ],
                "properties": {
                    "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                    "siteConfig": {
                        "linuxFxVersion": "PYTHON|3.7",
                        "appSettings": [
                            {
                            "name": "AzureWebJobsStorage",
                            "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                            },
                            {
                            "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                            "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                            },
                            {
                            "name": "WEBSITE_CONTENTSHARE",
                            "value": "[toLower(parameters('appName'))]"
                            },
                            {
                            "name": "FUNCTIONS_EXTENSION_VERSION",
                            "value": "~3"
                            },
                            {
                            "name": "WEBSITE_NODE_DEFAULT_VERSION",
                            "value": "~10"
                            },
                            {
                            "name": "FUNCTIONS_WORKER_RUNTIME",
                            "value": "python"
                            }
                        ]
                    }
                }
            }
        ],
        "outputs": {}
    }
    
    0
    • Nama Paket Hosting yang akan dibuat

Sumber daya

Kami membuat 3 sumber daya dalam template ARM ini

  • Microsoft. Penyimpanan/Akun penyimpanan
    • Ini adalah Akun Penyimpanan Azure
    • Kami menggunakan akun penyimpanan tingkat V2 standar di sini
  • Microsoft. Web/serverfarm
    • Ini adalah Akun Hosting Aplikasi
    • Aplikasi Web Python hanya didukung oleh Fungsi Azure di Akun Hosting Aplikasi Linux
    • Kami telah menggunakan akun hosting aplikasi tingkat standar dalam hal ini, dengan komputasi yang dicadangkan
  • Microsoft. Web/situs
    • Ini adalah Aplikasi Web kami sendiri
    • Perhatikan lagi bahwa ini adalah aplikasi web linux dan "linuxFxVersion" diatur ke "PYTHON. 3. 7”
    • Kami menyediakan string koneksi untuk menghubungkan aplikasi ke akun penyimpanan di
      {
          "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
          "contentVersion": "1.0.0.0",
          "parameters": {
              "appName": {
                  "type": "string",
                  "metadata": {
                      "description": "The name of the function web app to create."
                  }
              },
              "storageAcctName": {
                  "type": "string",
                  "metadata": {
                      "description": "The name of the Azure Storage Account to create."
                  }
              },
              "hostingPlanName": {
                  "type": "string",
                  "metadata": {
                      "description": "The name of the Hosting Plan to create."
                  }
              }
          },
          "functions": [],
          "variables": {},
          "resources": [
              {
                  "type": "Microsoft.Storage/storageAccounts",
                  "name": "[parameters('storageAcctName')]",
                  "apiVersion": "2019-06-01",
                  "location": "[resourceGroup().location]",
                  "kind": "StorageV2",
                  "sku": {
                      "name": "Standard_LRS",
                      "tier": "Standard"
                  }
              },
              {
                  "type": "Microsoft.Web/serverfarms",
                  "apiVersion": "2018-02-01",
                  "name": "[parameters('hostingPlanName')]",
                  "location": "[resourceGroup().location]",
                  "kind": "Linux",
                  "sku": {
                      "name": "S1",
                      "tier": "Standard",
                      "size": "S1",
                      "family": "S",
                      "capacity": 1
                  },
                  "properties": {
                      "reserved": true
                  }
              },
              {
                  "type": "Microsoft.Web/sites",
                  "apiVersion": "2020-06-01",
                  "name": "[parameters('appName')]",
                  "location": "[resourceGroup().location]",
                  "kind": "functionapp,linux",
                  "dependsOn": [
                      "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                      "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
                  ],
                  "properties": {
                      "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                      "siteConfig": {
                          "linuxFxVersion": "PYTHON|3.7",
                          "appSettings": [
                              {
                              "name": "AzureWebJobsStorage",
                              "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                              },
                              {
                              "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                              "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                              },
                              {
                              "name": "WEBSITE_CONTENTSHARE",
                              "value": "[toLower(parameters('appName'))]"
                              },
                              {
                              "name": "FUNCTIONS_EXTENSION_VERSION",
                              "value": "~3"
                              },
                              {
                              "name": "WEBSITE_NODE_DEFAULT_VERSION",
                              "value": "~10"
                              },
                              {
                              "name": "FUNCTIONS_WORKER_RUNTIME",
                              "value": "python"
                              }
                          ]
                      }
                  }
              }
          ],
          "outputs": {}
      }
      
      1

Membuat file yml Azure Pipelines untuk pengiriman berkelanjutan

Azure Pipelines digunakan untuk menjalankan continuous integration (CI) dan continuous delivery (CD) untuk memungkinkan tim melakukan iterasi cepat pada produk mereka dengan cara yang kuat. Di sini kami akan berfokus pada penerapan, tetapi jika Anda tertarik dengan pipeline CI, lihat postingan blog terkait saya di sini

Azure Pipelines menggunakan templat yaml di repositori kode Anda untuk menjalankan pipeline dan file yaml Azure Pipelines kami dapat ditemukan di root repositori di

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
2

Di sini kami akan membangun Aplikasi Fungsi Azure kami, membuat sumber daya kami menggunakan template ARM kami, dan menerapkan aplikasi kami ke Azure

Mari kita lihat dulu file yaml ini secara keseluruhan, kemudian kita akan membahasnya step by step

trigger:
  branches:
    include:
      - 'master'

variables:
  - group: 'AzFunctionsAppVariableGroup'

pool:
  vmImage: ubuntu-18.04

steps:
- task: UsePythonVersion@0
  displayName: "Setting python version to 3.7"
  inputs:
    versionSpec: '3.7'
    architecture: 'x64'

- bash: |
    pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
  displayName: 'Install app requirements'

- task: ArchiveFiles@2
  displayName: "Archive files"
  inputs:
    rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
    includeRootFolder: false
    archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"

- task: PublishBuildArtifacts@1
  inputs:
    PathtoPublish: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
    artifactName: 'drop'

- task: AzureResourceManagerTemplateDeployment@3
  displayName: 'ARM Template deployment: Resource Group scope'
  inputs:
    azureResourceManagerConnection: $(serviceConnectionName)
    subscriptionId: $(subscriptionId)
    resourceGroupName: $(resourceGroupName)
    location: $(resourceGroupLocation)
    csmFile: 'deployment_template.json'
    overrideParameters: '-appName $(appName) -storageAcctName $(storageAcctName) -hostingPlanName $(hostingPlanName)'

- task: AzureFunctionApp@1
  inputs:
    azureSubscription: $(serviceConnectionName)
    appType: functionAppLinux
    appName: $(appName)
    package: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
_

Mari kita lalui langkah demi langkah sekarang

Pemicu

Setiap kali kode digabungkan ke dalam cabang

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
3, pipeline CD ini akan berjalan. ketika secara aktif mengembangkan untuk produksi, Anda mungkin akan menerapkan ini secara otomatis ke lingkungan pengembangan Anda dan menerapkan penurunan sesuai permintaan ke lingkungan Anda yang lebih tinggi

trigger:
  branches:
    include:
      - 'master'

Variabel

Dalam template ini kita akan menggunakan beberapa variabel yang akan kita simpan di "Grup Variabel" di Azure DevOps bernama

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
4. Kami akan menyiapkannya di langkah berikutnya

variables:
  - group: 'AzFunctionsAppVariableGroup'

Kolam

Pipa ini akan berjalan di Ubuntu 18. 04 VM

pool:
  vmImage: ubuntu-18.04

Langkah

Aplikasi Fungsi Azure kami berjalan di python 3. 7, jadi kita perlu menyetel versi python Anda ke 3. 7

steps:
- task: UsePythonVersion@0
  displayName: "Setting python version to 3.7"
  inputs:
    versionSpec: '3.7'
    architecture: 'x64'

Kami kemudian menginstal persyaratan Aplikasi Fungsi Azure, yang dapat ditemukan di file

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
5 di root repositori kami. Karena kesederhanaan aplikasi ini, kami hanya menginstal "fungsi-azure" tetapi, untuk aplikasi yang lebih kompleks, kami mungkin memiliki lebih banyak persyaratan

- bash: |
    pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
  displayName: 'Install app requirements'

Kami kemudian meng-zip file yang siap dipublikasikan sebagai artefak build dan untuk penerapan. Kami meng-zip keseluruhan repositori kami (variabel default bernama

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
6 dan file dibuat dengan ID build unik

- task: ArchiveFiles@2
  displayName: "Archive files"
  inputs:
    rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
    includeRootFolder: false
    archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"

Kami memublikasikan artefak build kami sehingga artefak build ini nantinya dapat diterapkan ke lingkungan yang lebih tinggi (pengujian, UAT, produksi) jika kami senang dengannya di lingkungan pengembangan

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_0

Selanjutnya kami membuat sumber daya kami di Azure menggunakan template ARM yang kami tentukan di atas. Tidak ada yang dibuat jika sumber daya sudah ada. Perhatikan bahwa sejumlah variabel dari Grup Variabel kami digunakan di sini (mis. g.

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
7), kami akan menunjukkan cara mengatur grup variabel nanti

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_1

Akhirnya kami menyebarkan aplikasi kami ke Fungsi Azure menggunakan file Zip paket kami

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_2

Anda belum perlu melakukan apa pun dengan file ini, kami akan menggunakannya saat menyiapkan Azure Pipeline di Azure DevOps

Menyiapkan Pipeline Azure di Azure DevOpsGrup sumber daya adalah pengelompokan logis sumber daya di Azure. Anda harus membuatnya, jika Anda belum memiliki yang ingin Anda gunakan, untuk pekerjaan ini. Untuk informasi tentang cara melakukannya menggunakan Portal Azure,. Ini juga dapat dilakukan di Azure CLI dengan menjalankan'Hello, Ben Keen. This HTTP triggered function executed successfully.'_3Untuk tutorial ini saya telah membuat satu nama { "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#", "contentVersion": "1.0.0.0", "parameters": { "appName": { "type": "string", "metadata": { "description": "The name of the function web app to create." } }, "storageAcctName": { "type": "string", "metadata": { "description": "The name of the Azure Storage Account to create." } }, "hostingPlanName": { "type": "string", "metadata": { "description": "The name of the Hosting Plan to create." } } }, "functions": [], "variables": {}, "resources": [ { "type": "Microsoft.Storage/storageAccounts", "name": "[parameters('storageAcctName')]", "apiVersion": "2019-06-01", "location": "[resourceGroup().location]", "kind": "StorageV2", "sku": { "name": "Standard_LRS", "tier": "Standard" } }, { "type": "Microsoft.Web/serverfarms", "apiVersion": "2018-02-01", "name": "[parameters('hostingPlanName')]", "location": "[resourceGroup().location]", "kind": "Linux", "sku": { "name": "S1", "tier": "Standard", "size": "S1", "family": "S", "capacity": 1 }, "properties": { "reserved": true } }, { "type": "Microsoft.Web/sites", "apiVersion": "2020-06-01", "name": "[parameters('appName')]", "location": "[resourceGroup().location]", "kind": "functionapp,linux", "dependsOn": [ "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]", "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]" ], "properties": { "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]", "siteConfig": { "linuxFxVersion": "PYTHON|3.7", "appSettings": [ { "name": "AzureWebJobsStorage", "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]" }, { "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING", "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]" }, { "name": "WEBSITE_CONTENTSHARE", "value": "[toLower(parameters('appName'))]" }, { "name": "FUNCTIONS_EXTENSION_VERSION", "value": "~3" }, { "name": "WEBSITE_NODE_DEFAULT_VERSION", "value": "~10" }, { "name": "FUNCTIONS_WORKER_RUNTIME", "value": "python" } ] } } } ], "outputs": {} } 8

Membuat koneksi layanan di Azure DevOps

Hal pertama yang perlu kami lakukan di Azure DevOps adalah membuat koneksi layanan ke Grup Sumber Daya Azure kami untuk memungkinkan kami menyebarkan sumber daya ke Grup Sumber Daya Azure kami dari Azure DevOps

Arahkan ke Pengaturan Proyek di sudut kiri bawah halaman di Proyek Azure DevOps Anda

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Kemudian di bawah "Pipelines" di bilah pengaturan proyek, pilih "Koneksi layanan"

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Anda akan disambut oleh halaman koneksi layanan, buat koneksi layanan baru dengan mengklik tombol di kanan atas

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Kemudian ikuti alur kerja yang ditunjukkan di bawah – pastikan Anda memilih “Azure Resource Manager” untuk koneksi layanan Anda. Pada langkah terakhir, pilih langganan Azure yang dapat Anda akses, berikan nama grup sumber daya Anda dan nama untuk koneksi layanan Anda – Saya telah memilih

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
9

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Membuat grup variabel di Azure DevOps

Selanjutnya kita perlu membuat grup variabel di Azure DevOps untuk menyimpan variabel yang kita gunakan di Azure Pipeline, seperti yang ditunjukkan pada file yaml kita di atas

Anda dapat membuat grup Variabel dengan menggunakan panel navigasi sebelah kiri untuk mengklik "Library" di bawah "Pipelines"

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Kemudian pilih tombol untuk "+ Grup variabel"

Anda harus menamai grup variabel ini

{
    "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
        "appName": {
            "type": "string",
            "metadata": {
                "description": "The name of the function web app to create."
            }
        },
        "storageAcctName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Azure Storage Account to create."
            }
        },
        "hostingPlanName": {
            "type": "string",
            "metadata": {
                "description": "The name of the Hosting Plan to create."
            }
        }
    },
    "functions": [],
    "variables": {},
    "resources": [
        {
            "type": "Microsoft.Storage/storageAccounts",
            "name": "[parameters('storageAcctName')]",
            "apiVersion": "2019-06-01",
            "location": "[resourceGroup().location]",
            "kind": "StorageV2",
            "sku": {
                "name": "Standard_LRS",
                "tier": "Standard"
            }
        },
        {
            "type": "Microsoft.Web/serverfarms",
            "apiVersion": "2018-02-01",
            "name": "[parameters('hostingPlanName')]",
            "location": "[resourceGroup().location]",
            "kind": "Linux",
            "sku": {
                "name": "S1",
                "tier": "Standard",
                "size": "S1",
                "family": "S",
                "capacity": 1
            },
            "properties": {
                "reserved": true
            }
        },
        {
            "type": "Microsoft.Web/sites",
            "apiVersion": "2020-06-01",
            "name": "[parameters('appName')]",
            "location": "[resourceGroup().location]",
            "kind": "functionapp,linux",
            "dependsOn": [
                "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
            ],
            "properties": {
                "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                "siteConfig": {
                    "linuxFxVersion": "PYTHON|3.7",
                    "appSettings": [
                        {
                        "name": "AzureWebJobsStorage",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                        "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                        },
                        {
                        "name": "WEBSITE_CONTENTSHARE",
                        "value": "[toLower(parameters('appName'))]"
                        },
                        {
                        "name": "FUNCTIONS_EXTENSION_VERSION",
                        "value": "~3"
                        },
                        {
                        "name": "WEBSITE_NODE_DEFAULT_VERSION",
                        "value": "~10"
                        },
                        {
                        "name": "FUNCTIONS_WORKER_RUNTIME",
                        "value": "python"
                        }
                    ]
                }
            }
        }
    ],
    "outputs": {}
}
_4 agar sesuai dengan definisi di file yaml Azure Pipelines

Variabel yang perlu Anda berikan adalah

  • 'Hello, Ben Keen. This HTTP triggered function executed successfully.'
    _8
    • Nama Aplikasi Fungsi Azure Anda (Pilih sesuatu yang unik)
  • {
        "$schema": "https://schema.management.azure.com/schemas/2019-08-01/managementGroupDeploymentTemplate.json#",
        "contentVersion": "1.0.0.0",
        "parameters": {
            "appName": {
                "type": "string",
                "metadata": {
                    "description": "The name of the function web app to create."
                }
            },
            "storageAcctName": {
                "type": "string",
                "metadata": {
                    "description": "The name of the Azure Storage Account to create."
                }
            },
            "hostingPlanName": {
                "type": "string",
                "metadata": {
                    "description": "The name of the Hosting Plan to create."
                }
            }
        },
        "functions": [],
        "variables": {},
        "resources": [
            {
                "type": "Microsoft.Storage/storageAccounts",
                "name": "[parameters('storageAcctName')]",
                "apiVersion": "2019-06-01",
                "location": "[resourceGroup().location]",
                "kind": "StorageV2",
                "sku": {
                    "name": "Standard_LRS",
                    "tier": "Standard"
                }
            },
            {
                "type": "Microsoft.Web/serverfarms",
                "apiVersion": "2018-02-01",
                "name": "[parameters('hostingPlanName')]",
                "location": "[resourceGroup().location]",
                "kind": "Linux",
                "sku": {
                    "name": "S1",
                    "tier": "Standard",
                    "size": "S1",
                    "family": "S",
                    "capacity": 1
                },
                "properties": {
                    "reserved": true
                }
            },
            {
                "type": "Microsoft.Web/sites",
                "apiVersion": "2020-06-01",
                "name": "[parameters('appName')]",
                "location": "[resourceGroup().location]",
                "kind": "functionapp,linux",
                "dependsOn": [
                    "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                    "[resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName'))]"
                ],
                "properties": {
                    "serverFarmId": "[resourceId('Microsoft.Web/serverfarms', parameters('hostingPlanName'))]",
                    "siteConfig": {
                        "linuxFxVersion": "PYTHON|3.7",
                        "appSettings": [
                            {
                            "name": "AzureWebJobsStorage",
                            "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                            },
                            {
                            "name": "WEBSITE_CONTENTAZUREFILECONNECTIONSTRING",
                            "value": "[concat('DefaultEndpointsProtocol=https;AccountName=', parameters('storageAcctName'), ';EndpointSuffix=', environment().suffixes.storage, ';AccountKey=',listKeys(resourceId('Microsoft.Storage/storageAccounts', parameters('storageAcctName')), '2019-06-01').keys[0].value)]"
                            },
                            {
                            "name": "WEBSITE_CONTENTSHARE",
                            "value": "[toLower(parameters('appName'))]"
                            },
                            {
                            "name": "FUNCTIONS_EXTENSION_VERSION",
                            "value": "~3"
                            },
                            {
                            "name": "WEBSITE_NODE_DEFAULT_VERSION",
                            "value": "~10"
                            },
                            {
                            "name": "FUNCTIONS_WORKER_RUNTIME",
                            "value": "python"
                            }
                        ]
                    }
                }
            }
        ],
        "outputs": {}
    }
    
    0
    • Nama Paket Hosting Azure Functions Linux Anda
  • trigger:
      branches:
        include:
          - 'master'
    
    variables:
      - group: 'AzFunctionsAppVariableGroup'
    
    pool:
      vmImage: ubuntu-18.04
    
    steps:
    - task: UsePythonVersion@0
      displayName: "Setting python version to 3.7"
      inputs:
        versionSpec: '3.7'
        architecture: 'x64'
    
    - bash: |
        pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
      displayName: 'Install app requirements'
    
    - task: ArchiveFiles@2
      displayName: "Archive files"
      inputs:
        rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
        includeRootFolder: false
        archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"
    
    - task: PublishBuildArtifacts@1
      inputs:
        PathtoPublish: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
        artifactName: 'drop'
    
    - task: AzureResourceManagerTemplateDeployment@3
      displayName: 'ARM Template deployment: Resource Group scope'
      inputs:
        azureResourceManagerConnection: $(serviceConnectionName)
        subscriptionId: $(subscriptionId)
        resourceGroupName: $(resourceGroupName)
        location: $(resourceGroupLocation)
        csmFile: 'deployment_template.json'
        overrideParameters: '-appName $(appName) -storageAcctName $(storageAcctName) -hostingPlanName $(hostingPlanName)'
    
    - task: AzureFunctionApp@1
      inputs:
        azureSubscription: $(serviceConnectionName)
        appType: functionAppLinux
        appName: $(appName)
        package: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
    
    _3
    • Lokasi grup sumber daya Anda
  • trigger:
      branches:
        include:
          - 'master'
    
    variables:
      - group: 'AzFunctionsAppVariableGroup'
    
    pool:
      vmImage: ubuntu-18.04
    
    steps:
    - task: UsePythonVersion@0
      displayName: "Setting python version to 3.7"
      inputs:
        versionSpec: '3.7'
        architecture: 'x64'
    
    - bash: |
        pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
      displayName: 'Install app requirements'
    
    - task: ArchiveFiles@2
      displayName: "Archive files"
      inputs:
        rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
        includeRootFolder: false
        archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"
    
    - task: PublishBuildArtifacts@1
      inputs:
        PathtoPublish: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
        artifactName: 'drop'
    
    - task: AzureResourceManagerTemplateDeployment@3
      displayName: 'ARM Template deployment: Resource Group scope'
      inputs:
        azureResourceManagerConnection: $(serviceConnectionName)
        subscriptionId: $(subscriptionId)
        resourceGroupName: $(resourceGroupName)
        location: $(resourceGroupLocation)
        csmFile: 'deployment_template.json'
        overrideParameters: '-appName $(appName) -storageAcctName $(storageAcctName) -hostingPlanName $(hostingPlanName)'
    
    - task: AzureFunctionApp@1
      inputs:
        azureSubscription: $(serviceConnectionName)
        appType: functionAppLinux
        appName: $(appName)
        package: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
    
    _4
    • Nama grup sumber daya Anda
  • trigger:
      branches:
        include:
          - 'master'
    
    variables:
      - group: 'AzFunctionsAppVariableGroup'
    
    pool:
      vmImage: ubuntu-18.04
    
    steps:
    - task: UsePythonVersion@0
      displayName: "Setting python version to 3.7"
      inputs:
        versionSpec: '3.7'
        architecture: 'x64'
    
    - bash: |
        pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
      displayName: 'Install app requirements'
    
    - task: ArchiveFiles@2
      displayName: "Archive files"
      inputs:
        rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
        includeRootFolder: false
        archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"
    
    - task: PublishBuildArtifacts@1
      inputs:
        PathtoPublish: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
        artifactName: 'drop'
    
    - task: AzureResourceManagerTemplateDeployment@3
      displayName: 'ARM Template deployment: Resource Group scope'
      inputs:
        azureResourceManagerConnection: $(serviceConnectionName)
        subscriptionId: $(subscriptionId)
        resourceGroupName: $(resourceGroupName)
        location: $(resourceGroupLocation)
        csmFile: 'deployment_template.json'
        overrideParameters: '-appName $(appName) -storageAcctName $(storageAcctName) -hostingPlanName $(hostingPlanName)'
    
    - task: AzureFunctionApp@1
      inputs:
        azureSubscription: $(serviceConnectionName)
        appType: functionAppLinux
        appName: $(appName)
        package: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
    
    _5
    • Nama koneksi layanan Anda yang telah disiapkan di langkah sebelumnya
  • 'Hello, Ben Keen. This HTTP triggered function executed successfully.'
    _9
    • Nama akun penyimpanan Anda
  • trigger:
      branches:
        include:
          - 'master'
    
    variables:
      - group: 'AzFunctionsAppVariableGroup'
    
    pool:
      vmImage: ubuntu-18.04
    
    steps:
    - task: UsePythonVersion@0
      displayName: "Setting python version to 3.7"
      inputs:
        versionSpec: '3.7'
        architecture: 'x64'
    
    - bash: |
        pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
      displayName: 'Install app requirements'
    
    - task: ArchiveFiles@2
      displayName: "Archive files"
      inputs:
        rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
        includeRootFolder: false
        archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"
    
    - task: PublishBuildArtifacts@1
      inputs:
        PathtoPublish: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
        artifactName: 'drop'
    
    - task: AzureResourceManagerTemplateDeployment@3
      displayName: 'ARM Template deployment: Resource Group scope'
      inputs:
        azureResourceManagerConnection: $(serviceConnectionName)
        subscriptionId: $(subscriptionId)
        resourceGroupName: $(resourceGroupName)
        location: $(resourceGroupLocation)
        csmFile: 'deployment_template.json'
        overrideParameters: '-appName $(appName) -storageAcctName $(storageAcctName) -hostingPlanName $(hostingPlanName)'
    
    - task: AzureFunctionApp@1
      inputs:
        azureSubscription: $(serviceConnectionName)
        appType: functionAppLinux
        appName: $(appName)
        package: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
    
    _7
    • Nama langganan yang akan digunakan

Seharusnya terlihat seperti ini

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Membuat saluran pipa Anda di Azure DevOps

Sekarang saatnya membuat pipeline penerapan kami di Azure DevOps, kami akan menggunakan file yaml yang kami lihat sebelumnya di postingan ini untuk melakukan ini

Arahkan ke jalur pipa di blade sebelah kiri di Azure DevOps dan klik tombol Jalur Pipa Baru

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Anda kemudian akan ditanya di mana kode Anda, klik Azure Repos Git (gambar kiri di bawah). Kemudian Anda akan diminta untuk memilih repositori, pilih repositori bercabang Anda

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Setelah ini, Anda harus memilih "File YAML Azure Pipelines yang Ada" karena kami akan menggunakan file yaml di repositori untuk menentukan pipeline kami dan kemudian memilih file

trigger:
  branches:
    include:
      - 'master'

variables:
  - group: 'AzFunctionsAppVariableGroup'

pool:
  vmImage: ubuntu-18.04

steps:
- task: UsePythonVersion@0
  displayName: "Setting python version to 3.7"
  inputs:
    versionSpec: '3.7'
    architecture: 'x64'

- bash: |
    pip install --target="./.python_packages/lib/site-packages" -r ./requirements.txt
  displayName: 'Install app requirements'

- task: ArchiveFiles@2
  displayName: "Archive files"
  inputs:
    rootFolderOrFile: "$(System.DefaultWorkingDirectory)"
    includeRootFolder: false
    archiveFile: "$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip"

- task: PublishBuildArtifacts@1
  inputs:
    PathtoPublish: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
    artifactName: 'drop'

- task: AzureResourceManagerTemplateDeployment@3
  displayName: 'ARM Template deployment: Resource Group scope'
  inputs:
    azureResourceManagerConnection: $(serviceConnectionName)
    subscriptionId: $(subscriptionId)
    resourceGroupName: $(resourceGroupName)
    location: $(resourceGroupLocation)
    csmFile: 'deployment_template.json'
    overrideParameters: '-appName $(appName) -storageAcctName $(storageAcctName) -hostingPlanName $(hostingPlanName)'

- task: AzureFunctionApp@1
  inputs:
    azureSubscription: $(serviceConnectionName)
    appType: functionAppLinux
    appName: $(appName)
    package: '$(System.DefaultWorkingDirectory)/build$(Build.BuildId).zip'
8 di cabang master. Anda kemudian akan dibawa ke halaman di mana Anda dapat meninjau saluran Anda dan mengklik tombol "Jalankan".

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Jalankan Pipa

Pipa sekarang akan berjalan dan Anda dapat melacak progresnya, pada awalnya pekerjaan akan diantrekan

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Maka itu akan berjalan

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Dan, jika semuanya berjalan dengan baik, itu akan berhasil diselesaikan

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Anda dapat mengklik pekerjaan tersebut dan melihat setiap tahapan yang dijalankan. Jika pipeline Anda gagal, Anda juga dapat melihat pada titik mana gagalnya

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Menguji API Fungsi Azure yang diterapkan

Fungsi Anda sekarang diterapkan ke Azure. Jadi mari kita coba. Pertama kita harus pergi dan mendapatkan URL. Arahkan ke grup sumber daya Anda di Portal Azure dan Anda akan melihat sumber daya yang diterapkan

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Arahkan ke sumber daya Aplikasi Fungsi di Portal Azure dan klik Fungsi di blade sebelah kiri

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Sekarang pilih tombol yang mengatakan "Dapatkan Fungsi Url"

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Dan catat URL Anda. Anda kemudian dapat membuat permintaan GET atau POST HTTP ke URL ini dengan payload JSON

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_4

Seperti yang ditunjukkan di sini di Postman

Bagaimana Anda menulis python rest api tanpa server dengan fungsi azure?

Atau kita bisa mencobanya dengan Python

Di [2]

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_5

Keluar[2]

'Hello, Ben Keen. This HTTP triggered function executed successfully.'
_

Kesimpulan

Jadi begitulah – pipeline penerapan yang akan berjalan setiap kali Anda menggabungkan kode ke cabang master dan menerapkannya ke lingkungan pengembangan

Jika Anda ingin memiliki lingkungan yang lebih tinggi, Anda dapat mendaftarkan artefak file zip "Jatuhkan" ke Azure Artefak yang siap diterapkan ke lingkungan yang lebih tinggi jika Anda puas dengan penerapan saat ini dan siap untuk digunakan – Anda pasti ingin membuat

Bagaimana cara membuat API tanpa server dengan Fungsi Azure?

Bangun API tanpa server .
Klik tombol Buat sumber daya (tanda tambah di pojok kiri atas)
Cari Fungsi, pilih hasil "Aplikasi Fungsi" dan klik Buat. Ini membawa Anda ke bilah Buat Aplikasi Fungsi. Pilih Grup Sumber Daya. Isi Nama untuk layanan

Bisakah kita menulis kode Python dalam fungsi Azure?

Python dapat digunakan untuk skrip, pengembangan web backend, Ilmu Data, AI dan Pembelajaran Mesin, IoT, dll. Python digunakan di beberapa Layanan Azure termasuk aplikasi web, fungsi, penyimpanan, database, AI, dll.

Bisakah saya memanggil API dari fungsi Azure?

Ya, Anda dapat membuat dan menyesuaikan API di Fungsi Azure . Jika Anda menggunakan aplikasi fungsi bahasa C#, Anda dapat membuat objek HttpClient untuk melakukan panggilan HTTP dari fungsi Azure. Anda dapat menggunakan salah satu pemicu yang didukung untuk memicu aplikasi fungsi Anda, dan aplikasi fungsi Anda akan melakukan panggilan HTTP atau panggilan api.

Bagaimana cara memanggil Azure rest API dengan Python?

Panggilan REST Azure Resource Manager dari Python .
Buat Aplikasi Direktori Aktif Azure
Buat Prinsipal Layanan ("pengguna" Direktori Aktif yang mewakili aplikasi otomatis) dan berikan izin
Buat objek kredensial dan dapatkan ID penyewa