你当前正在访问 Microsoft Azure Global Edition 技术文档网站。 如果需要访问由世纪互联运营的 Microsoft Azure 中国技术文档网站,请访问 https://docs.azure.cn

教程:为 Azure 容器实例上的机密容器准备部署

在 Azure 容器实例中,你可以使用无服务器平台上的机密容器在基于硬件的、经过证明的受信任执行环境 (TEE) 中运行容器应用。 此功能可帮助保护使用中的数据,并通过安全嵌套分页提供内存加密。

本教程介绍如何执行下列操作:

  • 为机密容器组创建 Azure 资源管理器模板(ARM 模板)。
  • 生成机密计算强制执行(CCE)策略。
  • 将机密容器组部署到 Azure。

先决条件

若要完成本教程,必须满足以下要求:

  • Azure CLI:必须在本地计算机上安装 Azure CLI 版本 2.44.1 或更高版本。 若要查看自己的版本,请运行 az --version。 如需进行安装或升级,请参阅安装 Azure CLI

  • Azure CLI confcom 扩展:必须安装 Azure CLI confcom 扩展版本 0.30+ 以生成机密计算强制执行策略。

    az extension add -n confcom
    
  • Docker:需要在本地安装 Docker。 Docker 提供用于在 macOSWindowsLinux 上配置 Docker 环境的包。

    本教程假设读者基本了解核心 Docker 概念,如容器、容器映像和基本的 docker 命令。 有关 Docker 和容器的基础知识,请参阅 Docker 概述

重要

由于 Azure Cloud Shell 不包含 Docker 守护程序,因此,必须在本地计算机上安装 Azure CLI 和 Docker 引擎才能完成本教程。 不能在本教程中使用 Azure Cloud Shell。

为容器实例容器组创建 ARM 模板

在本教程中,你会部署生成硬件证明报告的 Hello World 应用程序。 首先,使用容器组资源创建 ARM 模板,从而定义此应用程序的属性。 然后,将此 ARM 模板与 Azure CLI confcom 工具配合使用以生成用于证明的 CCE 策略。

本教程使用此 ARM 模板作为示例。 若要查看此应用程序的源代码,请参阅 Azure 机密容器实例 Hello World

示例模板将两个属性添加到容器实例资源定义,以将容器组保密:

  • sku:允许在机密容器组部署和标准容器组部署之间进行选择。 如果不将此属性添加到资源,容器组将采用标准部署。
  • confidentialComputeProperties:允许传入自定义 CCE 策略来证明容器组。 如果不将此对象添加到资源,则不会验证容器组中运行的软件组件。

注意

confidentialComputeProperties 下的 ccePolicy 参数是空白的。 稍后在本教程中生成策略时,你将填写此内容。

使用首选文本编辑器将本地计算机上的此 ARM 模板保存为 template.json

{
    "$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
    "contentVersion": "1.0.0.0",
    "parameters": {
      "name": {
        "type": "string",
        "defaultValue": "helloworld",
        "metadata": {
          "description": "Name for the container group"
        }
      },
      "location": {
        "type": "string",
        "defaultValue": "North Europe",
        "metadata": {
          "description": "Location for all resources."
        }
      },
      "image": {
        "type": "string",
        "defaultValue": "mcr.microsoft.com/acc/samples/aci/helloworld:2.8",
        "metadata": {
          "description": "Container image to deploy. Should be of the form repoName/imagename:tag for images stored in public Docker Hub, or a fully qualified URI for other registries. Images from private registries require additional registry credentials."
        }
      },
      "port": {
        "type": "int",
        "defaultValue": 80,
        "metadata": {
          "description": "Port to open on the container and the public IP address."
        }
      },
      "cpuCores": {
        "type": "int",
        "defaultValue": 1,
        "metadata": {
          "description": "The number of CPU cores to allocate to the container."
        }
      },
      "memoryInGb": {
        "type": "int",
        "defaultValue": 1,
        "metadata": {
          "description": "The amount of memory to allocate to the container in gigabytes."
        }
      },
      "restartPolicy": {
        "type": "string",
        "defaultValue": "Never",
        "allowedValues": [
          "Always",
          "Never",
          "OnFailure"
        ],
        "metadata": {
          "description": "The behavior of Azure runtime if container has stopped."
        }
      }
    },
    "resources": [
      {
        "type": "Microsoft.ContainerInstance/containerGroups",
        "apiVersion": "2023-05-01",
        "name": "[parameters('name')]",
        "location": "[parameters('location')]",
        "properties": {
          "confidentialComputeProperties": {
            "ccePolicy": ""
          },
          "containers": [
            {
              "name": "[parameters('name')]",
              "properties": {
                "image": "[parameters('image')]",
                "ports": [
                  {
                    "port": "[parameters('port')]",
                    "protocol": "TCP"
                  }
                ],
                "resources": {
                  "requests": {
                    "cpu": "[parameters('cpuCores')]",
                    "memoryInGB": "[parameters('memoryInGb')]"
                  }
                }
              }
            }
          ],
          "sku": "Confidential",
          "osType": "Linux",
          "restartPolicy": "[parameters('restartPolicy')]",
          "ipAddress": {
            "type": "Public",
            "ports": [
              {
                "port": "[parameters('port')]",
                "protocol": "TCP"
              }
            ]
          }
        }
      }
    ],
    "outputs": {
      "containerIPv4Address": {
        "type": "string",
        "value": "[reference(resourceId('Microsoft.ContainerInstance/containerGroups', parameters('name'))).ipAddress.ip]"
      }
    }
  }

创建自定义 CCE 策略

使用已创建的 ARM 模板和 Azure CLI confcom 扩展,可以生成自定义 CCE 策略。 CCE 策略用于证明。 该工具将 ARM 模板用作输入以生成策略。 该策略强制执行特定的容器映像、环境变量、装载和命令,然后在容器组启动时验证这些内容。 有关 Azure CLI confcom 扩展的详细信息,请参阅 GitHub 上的文档

  1. 若要生成 CCE 策略,请运行以下命令并将 ARM 模板用作输入:

    az confcom acipolicygen -a .\template.json
    

    此命令完成后,作为输出生成的 Base64 字符串将自动显示在 ARM 模板的 ccePolicy 属性中。

部署模板

在以下步骤中,你将使用 Azure 门户来部署模板。 也可以使用 Azure PowerShell、Azure CLI 或 REST API。 若要了解其他部署方法,请参阅部署模板

  1. 选择“部署到 Azure”按钮以登录到 Azure 并开始容器实例部署

    用于将资源管理器模板部署到 Azure 的按钮。

  2. 选择“在编辑器中生成自己的模板”。

    编辑器中创建自定义模板的按钮的屏幕截图。

    显示的模板 JSON 大部分是空白的。

  3. 选择“加载文件”,并上传在前面步骤中通过添加 CCE 策略修改过的 template.json

    用于上传文件的按钮的屏幕截图。

  4. 选择“保存”。

  5. 选择或输入以下值:

    • 订阅:选择 Azure 订阅。
    • 资源组:选择“新建”,输入资源组的唯一名称,然后选择“确定”。
    • 名称:接受为实例生成的名称,或者输入一个名称
    • 位置:选择资源组的位置。 选择支持机密容器的区域。 示例:北欧
    • 映像:接受默认映像名称。 此示例 Linux 映像显示硬件证明。

    接受其余属性的默认值,然后选择“查看 + 创建”

    自定义 ARM 模板部署的详细信息的屏幕截图。

  6. 查看条款和条件。 如果你同意,请选择“我同意上述条款和条件”。

  7. 等待“部署成功”通知出现。 出现此通知表明已成功创建实例。

    成功部署的门户通知的屏幕截图。

查看已部署的资源

在以下步骤中,你将使用 Azure 门户查看容器实例的属性。 也可以使用 Azure CLI 等工具。

  1. 在门户中搜索“容器实例”,然后选择你创建的容器实例

  2. 在“概述”页上,记下实例的状态及其 IP 地址

    容器组实例概述页面的屏幕截图。

  3. 当实例的状态变为“正在运行”时,请在浏览器中转到该 IP 地址

    通过 Azure 容器实例部署的应用的浏览器视图的屏幕截图。

    Azure 容器实例徽标下方的证明报告确认运行容器的硬件支持 TEE。

    如果部署到不支持 TEE 的硬件(例如,选择机密容器实例不可用的区域),则不会显示证明报告。

现在,你已在容器实例上部署机密容器组,可以详细了解如何强制执行策略: