共用方式為


教學課程:建立和發行產品

適用於:所有 APIM 層

在 Azure API 管理中,一項產品會包含一或多個 API、使用量配額和使用規定。 產品發行後,開發人員即可訂閱產品,並開始使用產品的 API。

在本教學課程中,您會了解如何:

  • 建立和發佈產品
  • 將 API 新增至產品
  • 存取產品 API

入口網站中的 API 管理產品

必要條件

建立和發佈產品

  1. 登入 Azure 入口網站,然後瀏覽至您的 API 管理執行個體。

  2. 在左側瀏覽窗格中,選取 [產品]>[+ 新增]。

    在 Azure 入口網站新增產品

  3. 在 [新增產品] 視窗中,輸入下表所述的值,以建立您的產品。

    新增產品視窗

    名稱 描述
    Display name 您想要其顯示在開發人員入口網站中的名稱。
    描述 提供產品的相關資訊,例如用途、提供存取權的 API,以及其他詳細資料。
    州/省 如果您想要將產品發佈至開發人員入口網站,請選取 [已發佈]。 必須先發佈產品,開發人員才能探索到產品中的 API。 新產品會預設為未發佈。
    需要訂用帳戶 選取使用者是否需要訂閱才能使用產品 (產品受到「保護」),而且必須使用訂閱金鑰存取產品的 API。 如果不需訂閱 (產品是「開放」的),便不必使用訂閱金鑰存取產品的 API。 請參閱本文稍後的存取產品 API
    需要核准 如果您希望管理員檢閱並接受或拒絕對此產品的訂閱嘗試,請加以選取。 如果未選取,將會自動核准訂閱嘗試。
    訂閱計數限制 可選擇限制多個同時訂閱的總數。 最小值:1
    法律條款 您可以包含訂閱者必須接受才可使用產品的產品使用規定。
    API 選取一或多個 API。 您也可以在建立產品之後新增 API。 如需詳細資訊,請參閱本文稍後的將API 新增至產品

    如果產品是開放的 (無須訂閱),您只能新增與另一個開放式產品沒有關聯的 API。
  4. 選取 [建立] 建立新產品。

警告

設定不需要訂閱的產品時,請格外小心。 此設定可能過於寬鬆,而且可能會讓產品的 API 更容易遭受特定的 API 安全性威脅

新增更多設定

儲存之後,繼續設定產品。 在您的 API 管理執行個體中,從 [產品] 視窗中選取產品。 新增或更新:

項目 說明
設定 產品中繼資料和狀態
API 與產品相關聯的 API
原則 套用至產品 API 的原則
存取控制 開發人員或來賓的產品可見度
訂用帳戶 產品訂閱者

將 API 新增至產品中

產品是一或多個 API 的關聯。 您可以包含多個 API,並透過開發人員入口網站將其提供給開發人員。 在產品建立期間,您可以新增一或多個現有的 API。 您可以在之後將 API 新增至產品中,可以從產品的 [設定] 頁面或建立 API 時進行新增。

將 API 新增至現有的產品

  1. 在 API 管理執行個體的左側導覽中,選取 [產品]
  2. 選取產品,然後選取 [API]
  3. 選取 [+ 新增 API]
  4. 選取一或多個 API,然後選取 [選取]

將 API 新增至現有的產品

存取產品 API

發行產品後,開發人員即可存取 API。 視產品設定方式而定,開發人員可能需要訂閱產品才能存取。

  • 受保護的產品 - 開發人員必須先訂閱受保護的產品,才能存取產品的 API。 訂閱後,開發人員即可取得訂閱金鑰,存取該產品中任何 API。 如果您建立了 APIM 執行個體,您就已經是系統管理員,因此根據預設,您已訂閱每一個產品。 如需詳細資訊,請參閱 Azure API 管理中的訂閱

    在用戶端使用有效的產品訂閱金鑰提出 API 要求時,API 管理會處理要求,並允許就產品的內容進行存取。 為產品所設定的原則和存取控制規則亦可加以套用。

    提示

    您可以透過 REST API 或 PowerShell 命令,使用自訂的訂用帳戶金鑰建立或更新使用者的產品訂用帳戶。

  • 開放式產品 - 開發人員不必使用訂閱金鑰,即可存取開放式產品的 API。 但您可以設定其他機制來保護用戶端對 API 的存取,包括 OAuth 2.0用戶端憑證,及限制呼叫者 IP 位址

    注意

    開發人員入口網站中並未列出開放式產品,以便讓開發人員能夠了解或訂閱。 只有系統管理員群組才能看到它們。 您必須使用另一個機制來通知開發人員,關於哪些 API 不需訂用帳戶金鑰即可存取的資訊。

    在沒有訂閱金鑰的用戶端提出 API 要求時:

    • API 管理會檢查 API 是否與開放式產品相關。 API 最多可以與一個開放產品相關聯。

    • 如果有開放式產品,API 管理即會就開放式產品的內容來處理要求。 為開放式產品設定的原則和存取控制規則亦可加以套用。

如需詳細資訊,請參閱 API 管理如何處理具備或未具備訂閱金鑰的要求

下一步

在本教學課程中,您已了解如何:

  • 建立和發佈產品
  • 將 API 新增至產品
  • 存取產品 API

前進到下一個教學課程:

在本文中,您會使用 Terraform 來建立 Azure API 管理 實例、API、產品、群組,以及產品與 API 之間的關聯,以及產品和群組。

Terraform 可讓您定義、預覽和部署雲端基礎結構。 使用 Terraform 時,您可以使用 HCL 語法來建立設定檔。 HCL 語法可讓您指定雲端提供者 (例如 Azure) 和構成雲端基礎結構的元素。 建立設定檔之後,您可以建立執行計畫,讓您先預覽基礎結構變更,之後再部署。 驗證變更之後,您可以套用執行計畫來部署基礎結構。

  • 指定必要的 Terraform 版本和必要的提供者。
  • 定義資源組名前置詞、資源群組位置,以及 API 定義匯入的內容格式和值變數。
  • 使用隨機名稱建立資源群組。
  • 使用隨機名稱建立 API 管理 服務。
  • 建立具有隨機名稱的 API。
  • 在 API 管理 服務中建立具有隨機名稱的產品。
  • 建立具有隨機名稱的群組。
  • 將 API 與產品產生關聯。
  • 將群組與產品產生關聯。
  • 輸出隨機值,例如資源群組的名稱、API 管理 服務、API、產品和群組。

必要條件

實作 Terraform 程式碼

  1. 建立目錄,然後在目錄中測試並執行範例 Terraform 程式碼,且設為目前的目錄。

  2. 建立名為 main.tf的檔案,並插入下列程序代碼:

    resource "random_pet" "rg_name" {
      prefix = var.resource_group_name_prefix
    }
    
    resource "azurerm_resource_group" "rg" {
      location = var.resource_group_location
      name     = random_pet.rg_name.id
    }
    
    resource "random_string" "apim_service_name" {
      length  = 8
      lower   = true
      numeric = false
      special = false
      upper   = false
    }
    
    resource "azurerm_api_management" "apim_service" {
      name                = "${random_string.apim_service_name.result}-apim-service"
      location            = azurerm_resource_group.rg.location
      resource_group_name = azurerm_resource_group.rg.name
      publisher_name      = "Example Publisher"
      publisher_email     = "publisher@example.com"
      sku_name            = "Developer_1"
      tags = {
        Environment = "Example"
      }
      policy {
        xml_content = <<XML
        <policies>
          <inbound />
          <backend />
          <outbound />
          <on-error />
        </policies>
    XML
      }
    }
    
    resource "random_string" "api_name" {
      length  = 8
      lower   = true
      numeric = false
      special = false
      upper   = false
    }
    
    resource "random_string" "content_value" {
      length  = 8
      lower   = true
      numeric = false
      special = false
      upper   = false
    }
    
    resource "azurerm_api_management_api" "api" {
      name                = "${random_string.api_name.result}-api"
      resource_group_name = azurerm_resource_group.rg.name
      api_management_name = azurerm_api_management.apim_service.name
      revision            = "1"
      display_name        = "${random_string.api_name.result}-api"
      path                = "example"
      protocols           = ["https", "http"]
      description         = "An example API"
      import {
        content_format = var.open_api_spec_content_format
        content_value  = var.open_api_spec_content_value
      }
    }
    
    resource "random_string" "product_name" {
      length  = 8
      lower   = true
      numeric = false
      special = false
      upper   = false
    }
    
    resource "azurerm_api_management_product" "product" {
      product_id            = "${random_string.product_name.result}-product"
      resource_group_name   = azurerm_resource_group.rg.name
      api_management_name   = azurerm_api_management.apim_service.name
      display_name          = "${random_string.product_name.result}-product"
      subscription_required = true
      approval_required     = false
      published             = true
      description           = "An example Product"
    }
    
    resource "random_string" "group_name" {
      length  = 8
      lower   = true
      numeric = false
      special = false
      upper   = false
    }
    
    resource "azurerm_api_management_group" "group" {
      name                = "${random_string.group_name.result}-group"
      resource_group_name = azurerm_resource_group.rg.name
      api_management_name = azurerm_api_management.apim_service.name
      display_name        = "${random_string.group_name.result}-group"
      description         = "An example group"
    }
    
    resource "azurerm_api_management_product_api" "product_api" {
      resource_group_name = azurerm_resource_group.rg.name
      api_management_name = azurerm_api_management.apim_service.name
      product_id          = azurerm_api_management_product.product.product_id
      api_name            = azurerm_api_management_api.api.name
    }
    
    resource "azurerm_api_management_product_group" "product_group" {
      resource_group_name = azurerm_resource_group.rg.name
      api_management_name = azurerm_api_management.apim_service.name
      product_id          = azurerm_api_management_product.product.product_id
      group_name          = azurerm_api_management_group.group.name
    }
    
  3. 建立名為 outputs.tf的檔案,並插入下列程序代碼:

    output "resource_group_name" {
      value = azurerm_resource_group.rg.name
    }
    
    output "apim_service_name" {
      value = azurerm_api_management.apim_service.name
    }
    
    output "api_name" {
      value = azurerm_api_management_api.api.name
    }
    
    output "product_name" {
      value = azurerm_api_management_product.product.product_id
    }
    
    output "group_name" {
      value = azurerm_api_management_group.group.name
    }
    
    output "service_id" {
      description = "The ID of the API Management Service created"
      value       = azurerm_api_management.apim_service.id
    }
    
    output "gateway_url" {
      description = "The URL of the Gateway for the API Management Service"
      value       = azurerm_api_management.apim_service.gateway_url
    }
    
    output "service_public_ip_addresses" {
      description = "The Public IP addresses of the API Management Service"
      value       = azurerm_api_management.apim_service.public_ip_addresses
    }
    
    output "api_outputs" {
      description = "The IDs, state, and version outputs of the APIs created"
      value = {
        id             = azurerm_api_management_api.api.id
        is_current     = azurerm_api_management_api.api.is_current
        is_online      = azurerm_api_management_api.api.is_online
        version        = azurerm_api_management_api.api.version
        version_set_id = azurerm_api_management_api.api.version_set_id
      }
    }
    
    output "product_id" {
      description = "The ID of the Product created"
      value       = azurerm_api_management_product.product.id
    }
    
    output "product_api_id" {
      description = "The ID of the Product/API association created"
      value       = azurerm_api_management_product_api.product_api.id
    }
    
    output "product_group_id" {
      description = "The ID of the Product/Group association created"
      value       = azurerm_api_management_product_group.product_group.id
    }
    
  4. 建立名為 providers.tf的檔案,並插入下列程序代碼:

    terraform {
      required_version = ">=1.0"
      
      required_providers {
        azurerm = {
          source  = "hashicorp/azurerm"
          version = "~>3.0"
        }
        random = {
          source  = "hashicorp/random"
          version = "~>3.0"
        }
      }
    }
    
    provider "azurerm" {
      features {}
    }
    
  5. 建立名為 variables.tf的檔案,並插入下列程序代碼:

    variable "resource_group_name_prefix" {
      type        = string
      default     = "rg"
      description = "Prefix of the resource group name that's combined with a random ID so name is unique in your Azure subscription."
    }
    
    variable "resource_group_location" {
      type        = string
      default     = "eastus"
      description = "Location of the resource group."
    }
    
    variable "open_api_spec_content_format" {
      type        = string
      default     = "swagger-link-json"
      description = "The format of the content from which the API Definition should be imported. Possible values are: openapi, openapi+json, openapi+json-link, openapi-link, swagger-json, swagger-link-json, wadl-link-json, wadl-xml, wsdl and wsdl-link."
      validation {
        condition     = contains(["openapi", "openapi+json", "openapi+json-link", "openapi-link", "swagger-json", "swagger-link-json", "wadl-link-json", "wadl-xml", "wsdl", "wsdl-link"], var.open_api_spec_content_format)
        error_message = "open_api_spec_content_format must be one of the following: openapi, openapi+json, openapi+json-link, openapi-link, swagger-json, swagger-link-json, wadl-link-json, wadl-xml, wsdl and wsdl-link."
      }
    }
    
    variable "open_api_spec_content_value" {
      type        = string
      default     = "https://petstore3.swagger.io/api/v3/openapi.json"
      description = "The Content from which the API Definition should be imported. When a content_format of *-link-* is specified this must be a URL, otherwise this must be defined inline."
    }
    

初始化 Terraform

執行 terraform init 來初始化 Terraform 部署。 此命令會下載管理 Azure 資源所需的 Azure 提供者。

terraform init -upgrade

重點︰

  • -upgrade 參數會將必要的提供者外掛程式升級至符合設定版本條件約束的最新版本。

建立 Terraform 執行計畫

執行 terraform plan 以建立執行計畫。

terraform plan -out main.tfplan

重點︰

  • terraform plan 命令會建立執行計畫,但不會執行。 相反地,其會決定要在您指定的設定檔中建立設定所需的動作。 此模式可讓您在對實際資源進行任何變更之前,先確認執行方案是否符合您的預期。
  • 選用的 -out 參數可讓您指定計畫的輸出檔。 使用 -out 參數可確保您所檢閱的方案就是所套用的方案。

套用 Terraform 執行計畫

執行 terraform apply 將執行計畫套用至您的雲端基礎結構。

terraform apply main.tfplan

重點︰

  • 範例 terraform apply 命令假設您之前已執行過 terraform plan -out main.tfplan
  • 如果您為 -out 參數指定了不同的檔案名稱,請在呼叫 terraform apply 時使用該檔案名稱。
  • 若您未使用 -out 參數,請呼叫 terraform apply,不需要使用參數。

驗證結果

執行 az apim show 以檢視 Azure API 管理:


az apim show --<apim_service_name> --<resource_group_name>

清除資源

當您不再需要透過 Terraform 建立的資源時,請執行下列步驟:

  1. 執行 terraform plan 並指定 destroy 旗標。

    terraform plan -destroy -out main.destroy.tfplan
    

    重點︰

    • terraform plan 命令會建立執行計畫,但不會執行。 相反地,其會決定要在您指定的設定檔中建立設定所需的動作。 此模式可讓您在對實際資源進行任何變更之前,先確認執行方案是否符合您的預期。
    • 選用的 -out 參數可讓您指定計畫的輸出檔。 使用 -out 參數可確保您所檢閱的方案就是所套用的方案。
  2. 執行 terraform apply 以套用執行方案。

    terraform apply main.destroy.tfplan
    

對 Azure 上的 Terraform 進行疑難排解

針對在 Azure 上使用 Terraform 時的常見問題進行疑難排解。

下一步