全部产品
Search
文档中心

密钥管理服务:将用户主密钥从KMS默认实例迁移至您独享的KMS实例

更新时间:Jan 08, 2024

如果您使用的是KMS默认实例中的用户主密钥,当密钥配额以及QPS不能满足业务要求时,可以购买KMS软件密钥管理实例或硬件密钥管理实例,并将密钥迁移到实例中。本文介绍如何迁移用户主密钥。

迁移前须知

  • 仅KMS默认实例中的用户主密钥(简称主密钥)需要迁移,服务密钥以及专属KMS实例中的主密钥不需要迁移。密钥在控制台的位置,请参见密钥在新旧控制台的位置

  • 主密钥迁移后,使用该密钥加密的数据,仍旧可以通过该密钥解密。

  • 如果您不迁移主密钥,在旧版KMS中也可以继续使用,但您将无法提高密钥配额。

  • 不支持迁移的场景:

    • 自行导入密钥材料(即BYOK方式)的主密钥

    • 开启了自动轮转的主密钥

      重要

      如果您的密钥开启了自动轮转,但只有一个密钥版本,关闭自动轮转后支持迁移。

    • 有多个密钥版本的主密钥

  • 本文适用于应用部署在阿里云上,如果您的应用部署在阿里云外,请通过工单联系技术支持人员。

  • 迁移前请您先了解KMS软件密钥管理实例以及硬件密钥管理实例支持的能力。详细信息,请参见产品选型

迁移场景

场景一:使用主密钥(密钥材料由KMS生成)进行云产品服务端加密

  1. 判断密钥是否可以迁移。

    1. 登录旧版密钥管理控制台

    2. 单击用户主密钥页面,在页面的上方单击用户主密钥迁移判断工具

    3. 仔细阅读提示信息后单击确定,工具会给出是否可以迁移的判断结果。

  2. 购买KMS软件密钥管理实例或硬件密钥管理实例。

    具体操作,请参见购买KMS实例。关于如何选择KMS实例,请参见产品选型

  3. 联系技术支持人员迁移密钥。

    请通过工单联系技术支持人员,并提供如下信息:需要迁移的密钥ID、迁移时间窗口(建议在业务低峰期进行迁移)、目标KMS实例。

    说明

    阿里云会在迁移时间窗口完成密钥迁移。迁移完成后,您可以登录新版密钥管理服务控制台,在密钥管理页面选择目标KMS实例,在密钥列表查看已经完成迁移的密钥。

场景二:使用主密钥(密钥材料由KMS生成)进行自建应用加密

  1. 判断密钥是否可以迁移。

    1. 登录旧版密钥管理控制台

    2. 单击用户主密钥页面,在页面的上方单击用户主密钥迁移判断工具

    3. 仔细阅读提示信息后单击确定,工具会给出是否可以迁移的判断结果。

  2. 判断业务应用是否可以迁移。

    判断条件

    说明

    根据密码运算API判断是否支持迁移。

    如果您的业务应用使用了ReEncryptExportDataKey以及GenerateAndExportDataKey接口时,暂时无法迁移。

    根据应用网络位置判断是否支持迁移。

    应用与KMS实例在同一个VPC或不同VPC均支持迁移。

    根据应用开发语言判断是否支持迁移。

    目前提供Java、Go、Python三种语言类型的迁移SDK,以支持您将业务应用以较少的代码改动完成迁移。如果您的业务应用使用其他语言开发,暂不支持迁移,您可以通过工单联系技术支持人员反馈需求。

  3. 购买KMS软件密钥管理实例或硬件密钥管理实例。

    具体操作,请参见购买KMS实例。关于如何选择KMS实例,请参见产品选型

  4. 联系技术支持人员迁移密钥。

    请通过工单联系技术支持人员,并提供如下信息:需要迁移的密钥ID、迁移时间窗口(建议在业务低峰期进行迁移)、目标KMS实例。

    说明

    阿里云会在迁移时间窗口完成密钥迁移。迁移完成后,您可以登录新版密钥管理服务控制台,在密钥管理页面选择目标KMS实例,在密钥列表查看已经完成迁移的密钥。

  5. 改造业务应用。

    重要

    阿里云将在密钥迁移到KMS实例的1个月后关闭您之前使用的KMS网关入口,因此请务必在密钥迁移后的1个月内完成业务应用的改造。

    1. 创建应用接入点。具体操作,请参见创建应用接入点

    2. 对应用进行改造,具体代码如下。

      改造示例(JAVA)

      导入Maven依赖

         <!-- add dkms sdk dependency -->
        <dependency>
            <groupId>com.aliyun</groupId>
            <artifactId>alibabacloud-dkms-gcs-sdk</artifactId>
            <version>x.x.x</version>
          </dependency>
      
        <dependency>
            <groupId>com.aliyun.kms</groupId>
            <artifactId>kms-transfer-client</artifactId>
            <version>x.x.x</version>
        </dependency>

      代码改造

      说明

      阿里云账号AccessKey拥有所有API的访问权限,建议您使用RAM用户进行API访问或日常运维。强烈建议不要把AccessKey ID和AccessKey Secret保存到工程代码里,否则可能导致AccessKey泄露,威胁您账号下所有资源的安全。

      本示例以将AccessKey配置在环境变量ALIBABA_CLOUD_ACCESS_KEY_ID和ALIBABA_CLOUD_ACCESS_KEY_SECRET的方式来实现身份验证为例。更多认证信息配置方式,请参见Credentials 设置

      改造前业务代码示例:

      import com.aliyuncs.DefaultAcsClient;
      import com.aliyuncs.IAcsClient;
      import com.aliyuncs.exceptions.ClientException;
      import com.aliyuncs.exceptions.ServerException;
      import com.aliyuncs.profile.DefaultProfile;
      import com.google.gson.Gson;
      import java.util.*;
      import com.aliyuncs.kms.model.v20160120.*;
      
      public class Encrypt {
      
          public static void main(String[] args) {
              DefaultProfile profile = DefaultProfile.getProfile("cn-hangzhou", System.getenv("ALIBABA_CLOUD_ACCESS_KEY_ID"), System.getenv("ALIBABA_CLOUD_ACCESS_KEY_SECRET"));
              IAcsClient client = new DefaultAcsClient(profile);
              // 设置 request 参数
              EncryptRequest request = new EncryptRequest();
              request.setProtocol(ProtocolType.HTTPS);
              request.setAcceptFormat(FormatType.JSON);
              request.setMethod(MethodType.POST);
              request.setKeyId(<keyId>);
              request.setPlaintext(plainText);
      
              try {
                  EncryptResponse response = client.getAcsResponse(request);
                  System.out.println(new Gson().toJson(response));
              } catch (ServerException e) {
                  e.printStackTrace();
              } catch (ClientException e) {
                  System.out.println("ErrCode:" + e.getErrCode());
                  System.out.println("ErrMsg:" + e.getErrMsg());
                  System.out.println("RequestId:" + e.getRequestId());
              }
      
          }
      }

      改造后业务代码示例:

      import com.aliyun.kms.KmsTransferAcsClient;
      import com.aliyun.dkms.gcs.openapi.models.Config;
      import com.aliyuncs.IAcsClient;
      import com.aliyuncs.exceptions.ClientException;
      import com.aliyuncs.exceptions.ServerException;
      import com.aliyuncs.profile.DefaultProfile;
      import com.google.gson.Gson;
      import java.util.*;
      import com.aliyuncs.kms.model.v20160120.*;
      
      public class Encrypt {
      
          public static void main(String[] args) {
              DefaultProfile profile = DefaultProfile.getProfile("cn-hangzhou", System.getenv("ALIBABA_CLOUD_ACCESS_KEY_ID"), System.getenv("ALIBABA_CLOUD_ACCESS_KEY_SECRET"));
      
              Config config = new Config();
              //连接协议,固定为HTTPS。
              config.setProtocol("https");
              //KMS实例Client Key。
              config.setClientKeyFile("<your-client-key-file>");
              //KMS实例Client Key解密口令。
              config.setPassword("<your client key password>");
              //Endpoint,KMS实例服务地址去掉https://。
              config.setEndpoint("<service_id>.cryptoservice.kms.aliyuncs.com");
              // 设置CA证书文件路径。还支持设置CA证书内容,请根据需要选择。
              config.setCaFilePath("<path/to/yourCaCert>");
              // 设置CA证书内容。
              //config.setCa("<your-ca-certificate-content");   
              IAcsClient client = new KmsTransferAcsClient(profile, config);
              // 设置 request 参数
              EncryptRequest request = new EncryptRequest();
              request.setProtocol(ProtocolType.HTTPS);
              request.setAcceptFormat(FormatType.JSON);
              request.setMethod(MethodType.POST);
              request.setKeyId(<keyId>);
              request.setPlaintext(plainText);
      
              try {
                  EncryptResponse response = client.getAcsResponse(request);
                  System.out.println(new Gson().toJson(response));
              } catch (ServerException e) {
                  e.printStackTrace();
              } catch (ClientException e) {
                  System.out.println("ErrCode:" + e.getErrCode());
                  System.out.println("ErrMsg:" + e.getErrMsg());
                  System.out.println("RequestId:" + e.getRequestId());
              }
      
          }
      }

      改造示例(Python)

      安装增加依赖包

      代码改造

      说明

      阿里云账号AccessKey拥有所有API的访问权限,建议您使用RAM用户进行API访问或日常运维。强烈建议不要把AccessKey ID和AccessKey Secret保存到工程代码里,否则可能导致AccessKey泄露,威胁您账号下所有资源的安全。

      本示例以将AccessKey配置在环境变量ALIBABA_CLOUD_ACCESS_KEY_ID和ALIBABA_CLOUD_ACCESS_KEY_SECRET的方式来实现身份验证为例。更多认证信息配置方式,请参见客户端与凭证

      改造前业务代码示例:

      from aliyunsdkcore.auth.credentials import AccessKeyCredential
      from aliyunsdkcore.client import AcsClient
      from aliyunsdkkms.request.v20160120.EncryptRequest import EncryptRequest
      
      
      def encrypt():
          credentials = AccessKeyCredential(os.getenv("ALIBABA_CLOUD_ACCESS_KEY_ID"), os.getenv("ALIBABA_CLOUD_ACCESS_KEY_SECRET"))
      
          client = AcsClient(region_id="<your-region-id>", credential=credentials)
      
          request = EncryptRequest()
          request.set_accept_format('json')
          request.set_KeyId("<your-key-id>")
          request.set_Plaintext("<your-plaintext>")
      
          response = client.do_action_with_exception(request)
          print(str(response, encoding='utf-8'))
      
      
      encrypt()

      改造后业务代码示例:

      from alibabacloud_dkms_transfer.kms_transfer_acs_client import KmsTransferAcsClient
      from aliyunsdkcore.auth.credentials import AccessKeyCredential
      from aliyunsdkkms.request.v20160120.EncryptRequest import EncryptRequest
      from openapi.models import Config
      
      
      def encrypt():
          config = Config()
          config.protocol = "https"
          config.client_key_file = "<your-client-key-file-path>"
          config.password = "<your-password>"
          config.endpoint = "<your-endpoint>"
      
          credentials = AccessKeyCredential(os.getenv("ALIBABA_CLOUD_ACCESS_KEY_ID"), os.getenv("ALIBABA_CLOUD_ACCESS_KEY_SECRET"))
      
          client = KmsTransferAcsClient(config=config, credential=credentials, verify='<your-ca-certificate-file-path>')
      
          request = EncryptRequest()
          request.set_KeyId("<your-key-id>")
          request.set_Plaintext("<your-plaintext>")
      
          response = client.do_action_with_exception(request)
          print(str(response, encoding='utf-8'))
      
      
      encrypt()

      改造示例(Go)

      使用如下方式之一安装依赖包

      • 使用go mod管理您的依赖:

      • require (
            github.com/aliyun/alibabacloud-dkms-transfer-go-sdk vX.X.X
            github.com/aliyun/alibabacloud-dkms-gcs-go-sdk vX.X.X
            github.com/alibabacloud-go/tea vX.X.X
        )
      • 通过go get命令获取远程代码包:

      • $ go get -u github.com/aliyun/alibabacloud-dkms-transfer-go-sdk
        $ go get -u github.com/aliyun/alibabacloud-dkms-gcs-go-sdk
        $ go get -u github.com/alibabacloud-go/tea
        说明

        SDK的最新版本,请参见alibabacloud-dkms-gcs-go-sdkalibabacloud-dkms-transfer-go-sdk

      代码改造

      说明

      阿里云账号AccessKey拥有所有API的访问权限,建议您使用RAM用户进行API访问或日常运维。强烈建议不要把AccessKey ID和AccessKey Secret保存到工程代码里,否则可能导致AccessKey泄露,威胁您账号下所有资源的安全。

      本示例以将AccessKey配置在环境变量ALIBABA_CLOUD_ACCESS_KEY_ID和ALIBABA_CLOUD_ACCESS_KEY_SECRET的方式来实现身份验证为例。更多认证信息配置方式,请参见客户端

      改造前业务代码示例:

      import (
          "fmt"
          "github.com/aliyun/alibaba-cloud-sdk-go/services/kms"
      )
      
      func main() {
          client, err := kms.NewClientWithAccessKey("<your-region-id>", os.Getenv("ALIBABA_CLOUD_ACCESS_KEY_ID"), os.Getenv("ALIBABA_CLOUD_ACCESS_KEY_SECRET"))
          if err != nil {
              panic(err)
          }
      
          request := kms.CreateEncryptRequest()
          request.Scheme = "https"
          request.KeyId = "<your cmk id>"
          request.Plaintext = "<your plaintext>"
      
          response, err := client.Encrypt(request)
          if err != nil {
              panic(err)
          }
      
          fmt.Println(response)
      }

      改造后业务代码示例:

      import (
          "fmt"
          "github.com/alibabacloud-go/tea/tea"
          "github.com/aliyun/alibaba-cloud-sdk-go/services/kms"
          dedicatedkmsopenapi "github.com/aliyun/alibabacloud-dkms-gcs-go-sdk/openapi"
          "github.com/aliyun/alibabacloud-dkms-transfer-go-sdk/sdk"
      )
      
      func main() {
          config := &dedicatedkmsopenapi.Config{
              Protocol:      tea.String("https"),
              ClientKeyFile: tea.String("<your-client-key-file>"),
              Password:      tea.String("<your-client-key-password>"),
              Endpoint:      tea.String("<your-dkms-instance-service-endpoint>"),
          }
      
          client, err := sdk.NewClientWithAccessKey("<your-region-id>", os.Getenv("ALIBABA_CLOUD_ACCESS_KEY_ID"), os.Getenv("ALIBABA_CLOUD_ACCESS_KEY_SECRET"), config)
          if err != nil {
              panic(err)
          }
      
          request := kms.CreateEncryptRequest()
          request.KeyId = "<your cmk id>"
          request.Plaintext = "<your plaintext>"
      
          response, err := client.Encrypt(request)
          if err != nil {
              panic(err)
          }
      
          fmt.Println(response)
      }

场景三:使用主密钥(密钥材料为自行导入)进行云产品服务端加密

自行导入密钥材料(即BYOK方式)的主密钥,不支持迁移。

场景四:使用主密钥(密钥材料为自行导入)进行自建应用加密

自行导入密钥材料(即BYOK方式)的主密钥,不支持迁移。

密钥在新旧控制台的位置

  • 服务密钥

    • 旧版控制台

      单击用户主密钥页面,在顶部菜单栏选择地域后,KMS实例列是默认且密钥别名为alias/acs/云产品格式的,即为服务密钥。

      image.png

    • 新版控制台

      单击实例管理页面,在顶部菜单栏选择地域后,单击默认密钥管理页签,密钥用法列为服务密钥的,即为服务密钥。

      image.png

  • KMS默认实例中的主密钥

    • 旧版控制台

      单击用户主密钥页面,在顶部菜单栏选择地域后,KMS实例列是默认且密钥别名不是alias/acs/云产品格式的密钥。

      image.png

    • 新版控制台

      单击实例管理页面,在顶部菜单栏选择地域后,单击默认密钥管理页签,密钥用法列为主密钥的密钥。

      重要

      在新版控制台您只能查看该密钥,无法管理密钥,例如禁用密钥、计划删除密钥等,如果您需要执行这些操作,请切换到旧版控制台。

      image.png

  • 专属KMS实例中的主密钥

    • 旧版控制台

      单击用户主密钥页面,在顶部菜单栏选择地域后,KMS实例列是专属KMS实例ID的密钥。

      image.png

    • 新版控制台

      单击密钥管理页面,在顶部菜单栏选择地域后,选择实例ID后,即显示该KMS实例下的密钥。image.png

了解更多

以旧版控制台展示的资源为例,为您介绍哪些资源支持迁移,哪些资源不支持迁移。

image.png

旧版本控制台

说明

是否需要迁移

专属KMS

您购买的专属KMS实例,实例详情中包含密钥和凭据。

在新版控制台,KMS软件密

钥管理实例即专属KMS基础版实例,KMS硬件密钥管理实例即专属KMS标准版实例。

无需迁移。

切换到新版控制台,实例管理页面的软件密钥管理页签、硬件密钥管理页面即可查看对应的实例。

用户主密钥

包含三部分:

  • 服务密钥:KMS实例列为默认,且密钥别名为alias/acs/云产品

  • KMS默认实例中的用户主密钥:KMS实例列为默认,密钥别名不为alias/acs/云产品

  • 专属KMS实例中的用户主密钥:KMS实例列为专属KMS实例ID。

  • 服务密钥:无需迁移。

  • KMS默认实例中的用户主密钥:需要购买KMS实例,然后迁移,不迁移您也可以继续使用,但无法获得更高的密钥配额。

  • 专属KMS实例中的用户主密钥:无需迁移。

凭据

该页面中的凭据为公测版,您可以继续使用并在旧版控制台管理该部分凭据。

说明

该页面不包含专属KMS实例中的凭据。

暂不支持迁移,您可以通过工单向技术支持人员反馈迁移需求。

如果您需要获得凭据全能力或者更健壮的凭据功能,建议您使用正式商业化版本,即购买KMS软件密钥管理实例或硬件密钥管理实例,在实例中创建并使用凭据。

证书

在2023年07月11日后已不再支持创建证书,已创建的证书不影响使用,请在旧版控制台继续管理证书。新版本KMS不支持该功能。

不支持迁移。

私有CA

在2023年07月11日后已不再支持通过该引导链接购买私有CA证书。新版本KMS不支持该功能。

不支持迁移。

应用管理

页面中的应用接入点用于应用访问专属KMS实例,无需迁移。

无需迁移。

切换到新版控制台,即可应用管理页面查看应用接入点。