本文介绍如何使用EDAS提供的Java SDK调用API在K8s集群中进行金丝雀发布应用(JAR包、WAR包和镜像)。
准备工作
金丝雀发布应用前,您必须提前完成以下准备工作:
- 确定应用部署地域,假设为cn-hangzhou。
在EDAS K8s环境中创建应用。目前支持多种创建应用的方式,请根据实际需求选择:
如果已经创建应用,您可以调用ListApplication接口查询应用列表,获取目标应用的AppId,假设为6bbc57a2-a017-4bec-b521-49a15bd3****。
- 已将应用升级部署包(JAR包、WAR包和镜像)上传至目标地址。
- JAR包或WAR包:本示例以OSS存储路径为例,假设为https:doc***.oss-cn-hangzhou.aliyuncs.com/sc-****-D-0.0.2-SNAPSHOT.jar。
- 镜像:假设镜像仓库为image-demo-project,镜像地址为registry-vpc.cn-hangzhou.aliyuncs.com/image-demo-project/provider:2.0。
背景信息
使用API金丝雀发布应用,在首批灰度发布后,您必须手动确认继续剩余批次的发布。在确认剩余批次发布前,您可以进行小规模验证,验证后,再继续剩余批次的发布,即将应用全量升级到新版本。
使用API金丝雀发布应用,设置剩余批次(除首批灰度发布外)的发布方式时推荐选用自动分批发布。如果您选用手动分批发布方式,则还需要调用ContinuePipeline接口手动确认执行下一批发布。
此处提供两种金丝雀发布策略示例,请根据您的实际场景选择并修改策略。
首批灰度发布2个Pod实例+剩余Pod实例分2批发布+自动分批+分批间隔1分钟。
{"type":"GrayBatchUpdate","batchUpdate":{"batch":2,"releaseType":"auto","batchWaitTime":1},"grayUpdate":{"gray":2}}
首批灰度发布2个Pod实例+剩余Pod实例分2批发布+手动分批。
{"type":"GrayBatchUpdate","batchUpdate":{"batch":2,"releaseType":"manual"},"grayUpdate":{"gray":2}}
使用JAR包或WAR包金丝雀发布应用
运行以下示例代码,使用JAR包或WAR包金丝雀发布应用。
以下代码适用于在EDAS K8s集群中金丝雀发布应用(JAR包)。代码中未设置调度规则、启动命令、环境变量等高级参数,如需了解更多API参数信息,请参见DeployK8sApplication。
说明如果您需要使用WAR包金丝雀应用,请根据需要在示例代码中增加以下两个参数:
//部署包依赖的Tomcat版本。适用于通过WAR包部署的Spring Cloud和Dubbo应用。 request.setWebContainer("apache-tomcat-7.0.91"); //部署包依赖的EDAS Container版本。适用于通过WAR包部署的HSF应用。 request.setEdasContainerVersion("3.5.9");
import com.aliyuncs.DefaultAcsClient; import com.aliyuncs.exceptions.ClientException; import com.aliyuncs.exceptions.ServerException; import com.aliyuncs.profile.DefaultProfile; import com.aliyuncs.edas.model.v20170801.DeployK8sApplicationRequest; import com.aliyuncs.edas.model.v20170801.DeployK8sApplicationResponse; public class DeployK8sApplication { public static void main(String[] args) { // 阿里云账号AccessKey拥有所有API的访问权限,风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维,请登录RAM控制台创建RAM用户。 // 此处以把AccessKey和AccessKeySecret保存在环境变量为例说明。您可以根据业务需要,保存到配置文件里。 // 强烈建议不要把AccessKey和AccessKeySecret保存到代码里,会存在密钥泄漏风险。 String aliyun_user_ak = System.getenv("ACCESS_KEY_ID"); String aliyun_user_sk = System.getenv("ACCESS_KEY_SECRET"); //应用所在地域ID。 String region_id = "cn-hangzhou"; DefaultProfile defaultProfile = DefaultProfile.getProfile(region_id, aliyun_user_ak, aliyun_user_sk); DefaultAcsClient client = new DefaultAcsClient(defaultProfile); //创建API请求,并设置参数。 DeployK8sApplicationRequest request = new DeployK8sApplicationRequest(); //应用ID。 request.setAppId("6bbc57a2-a017-4bec-b521-49a15bd3****"); //JAR包或者WAR包地址、版本。 request.setPackageUrl("https:doc***.oss-cn-hangzhou.aliyuncs.com/sc-****-D-0.0.2-SNAPSHOT.jar"); request.setPackageVersion("2021-04-15 16:41:52"); //部署包依赖的JDK版本。可选的参数值为Open JDK 7和Open JDK 8。 request.setJDK("Open JDK 8"); //自定义分批发布策略。此处示例值代表“首批灰度发布2个Pod实例+剩余Pod实例分2批发布+自动分批+分批间隔1分钟”。 request.setUpdateStrategy("{\"type\":\"GrayBatchUpdate\",\"batchUpdate\":{\"batch\":2,\"releaseType\":\"auto\",\"batchWaitTime\":1},\"grayUpdate\":{\"gray\":2}}"); //灰度发布流量控制策略。示例策略表示:50%的流量会被转发到灰度分组。 request.setTrafficControlStrategy("{\"http\":{\"rules\":[{\"conditionType\":\"percent\",\"percent\":50}]}}"); //应用实例数。 request.setReplicas(4); //应用运行过程中,应用实例的CPU限额、内存限额等,0表示不限制。 request.setCpuLimit(0); request.setMemoryLimit(0); request.setCpuRequest(0); request.setMemoryRequest(0); //CPU最小资源需求,单位:核数。0表示不限制。 request.setMcpuRequest(0); //CPU能使用的最大值,单位:核数。0表示不限制。 request.setMcpuLimit(0); //变更记录描述。 request.setChangeOrderDesc("金丝雀发布(JAR包)"); try { DeployK8sApplicationResponse response = client.getAcsResponse(request); System.out.println("ChangeOrderId=" + response.getChangeOrderId() + "\nMessage=" + response.getMessage()); } catch (ServerException e) { e.printStackTrace(); } catch (ClientException e) { e.printStackTrace(); } } }
运行程序,返回的执行结果如下:
ChangeOrderId=5886e6f9-05b1-42f0-a3d4-5d90558e**** Message=success
调用GetChangeOrderInfo接口,获取金丝雀发布应用变更的相关批次的流程ID(PipelineId)。
调用GetChangeOrderInfo接口,返回结果如下:
{ "Message": "success", "RequestId": "19C54DC3-C66C-40D0-AEED-8D5A1F00F3BA", "Code": 200, "changeOrderInfo": { "Status": 8, "Desc": "金丝雀发布(JAR包)", "PipelineInfoList": { "PipelineInfo": [ { "PipelineStatus": 2, "PipelineName": "Canary Change", ...... "PipelineId": "ca7221a6-2c39-40b5-b40a-53fd3d99****" ...... "PipelineId": "e228e628-f722-43bc-9c2b-45076c3a****" ...... "PipelineId": "d6dcb857-2ff0-4db9-90fa-a2d9db7b****" ...... //此处未罗列全部执行结果,仅供参考。
说明示例代码中使用的是首批灰度发布2个Pod实例+剩余Pod实例分2批发布+自动分批+分批间隔1分钟的金丝雀发布策略,在首批灰度发布2个Pod实例流程运行完以后,需要手动确认继续剩余批次的发布。在调用GetChangeOrderInfo接口返回结果中出现3个流程ID(PipelineId),第二次出现的流程ID(PipelineId)代表需要手动确认继续剩余批次的发布。
剩余批次的策略是剩余Pod实例分2批发布+自动分批+分批间隔1分钟,则无需手动确认,系统自动完成剩余批次的发布。
调用ContinuePipeline接口,手动确认继续剩余批次的发布。
返回结果如下:
{ "Message": "success", "RequestId": "050392EE-959D-4144-AA02-3A1E7CE2F736", "Code": 200 }
使用镜像金丝雀发布应用
运行程序,使用镜像金丝雀发布应用。
以下代码适用于在EDAS K8s集群中金丝雀发布应用(镜像)。代码中未设置调度规则、启动命令、环境变量等高级参数,如需了解更多API参数信息,请参见DeployK8sApplication。
import com.aliyuncs.DefaultAcsClient; import com.aliyuncs.exceptions.ClientException; import com.aliyuncs.exceptions.ServerException; import com.aliyuncs.profile.DefaultProfile; import com.aliyuncs.edas.model.v20170801.DeployK8sApplicationRequest; import com.aliyuncs.edas.model.v20170801.DeployK8sApplicationResponse; public class DeployK8sApplication { public static void main(String[] args) { // 阿里云账号AccessKey拥有所有API的访问权限,风险很高。强烈建议您创建并使用RAM用户进行API访问或日常运维,请登录RAM控制台创建RAM用户。 // 此处以把AccessKey和AccessKeySecret保存在环境变量为例说明。您可以根据业务需要,保存到配置文件里。 // 强烈建议不要把AccessKey和AccessKeySecret保存到代码里,会存在密钥泄漏风险。 String aliyun_user_ak = System.getenv("ACCESS_KEY_ID"); String aliyun_user_sk = System.getenv("ACCESS_KEY_SECRET"); //应用所在地域ID。 String region_id = "cn-hangzhou"; DefaultProfile defaultProfile = DefaultProfile.getProfile(region_id, aliyun_user_ak, aliyun_user_sk); DefaultAcsClient client = new DefaultAcsClient(defaultProfile); //创建API请求,并设置参数。 DeployK8sApplicationRequest request = new DeployK8sApplicationRequest(); //应用ID。 request.setAppId("6bbc57a2-a017-4bec-b521-49a15bd3****"); //镜像地址。 request.setImage("registry-vpc.cn-hangzhou.aliyuncs.com/image-demo-project/provider:2.0"); //自定义金丝雀发布策略。此处示例值代表“首批灰度发布2个Pod实例+剩余Pod实例分2批发布+手动分批”。 request.setUpdateStrategy("{\"type\":\"GrayBatchUpdate\",\"batchUpdate\":{\"batch\":2,\"releaseType\":\"manual\"},\"grayUpdate\":{\"gray\":2}}"); //灰度发布流量控制策略。示例策略表示:50%的流量会被转发到灰度分组。 request.setTrafficControlStrategy("{\"http\":{\"rules\":[{\"conditionType\":\"percent\",\"percent\":50}]}}"); //应用实例数。 request.setReplicas(4); //应用运行过程中,应用实例的CPU限额、内存限额等,0表示不限制。 request.setCpuLimit(0); request.setMemoryLimit(0); request.setCpuRequest(0); request.setMemoryRequest(0); //CPU最小资源需求,单位:核数。0表示不限制。 request.setMcpuRequest(0); //CPU能使用的最大值,单位:核数。0表示不限制。 request.setMcpuLimit(0); //变更记录描述。 request.setChangeOrderDesc("金丝雀发布(镜像)"); try { DeployK8sApplicationResponse response = client.getAcsResponse(request); System.out.println("ChangeOrderId=" + response.getChangeOrderId() + "\nMessage=" + response.getMessage()); } catch (ServerException e) { e.printStackTrace(); } catch (ClientException e) { e.printStackTrace(); } } }
运行程序,返回的执行结果如下:
ChangeOrderId=a7431f9e-7e05-4590-aef8-17088f0**** Message=success
调用GetChangeOrderInfo接口,获取金丝雀发布应用变更的相关批次的流程ID(PipelineId)。
调用GetChangeOrderInfo接口,返回结果如下:
{ "Message": "success", "RequestId": "1B1127FB-251C-4946-AA20-D4FF5DF4788F", "Code": 200, "changeOrderInfo": { "Status": 8, "Desc": "金丝雀发布(镜像)", "PipelineInfoList": { "PipelineInfo": [ { "PipelineStatus": 2, "PipelineName": "Canary Change", ...... "PipelineId": "09e7d9aa-e79d-49ef-99b9-5405532d****" ...... "PipelineId": "1ea53844-2c60-46f1-b46d-df3b34d0****" ...... "PipelineId": "d99da075-b87d-4fe7-bbb6-ae1c6c26****" ...... //此处未罗列全部执行结果,仅供参考。
说明示例代码中使用的是首批灰度发布2台+剩余分2批发布+手动分批的金丝雀发布策略,在首批灰度发布2个Pod实例流程运行完以后,需要手动确认继续剩余批次的发布。在调用GetChangeOrderInfo接口返回结果中出现3个流程ID(PipelineId),第二次出现的流程ID(PipelineId)代表需要手动确认继续剩余批次的发布,第三次出现的流程ID(PipelineId)代表剩余批次中第一批完成后需要手动确认继续下一批次的发布。
调用ContinuePipeline接口,手动确认继续剩余批次发布。
返回结果如下:
{ "Message": "success", "RequestId": "B8ECF6F7-672D-40E9-91DD-1C33F06D4FD8", "Code": 200 }
调用ContinuePipeline接口,手动确认下一批发布。
返回结果如下:
{ "Message": "success", "RequestId": "7BB4F043-7C28-4A0E-B6A5-D4023EB24388", "Code": 200 }
说明示例代码中使用的是首批灰度发布2个Pod实例+剩余Pod实例分2批发布+手动分批的金丝雀发布策略,运行到剩余批次发布过程,只需要手动确认一批。如果您是剩余批次需要手动确认多批的场景,请选择正确批次的流程ID(PipelineId)并重复执行此步骤。
重复执行此步骤时,请等待批次内部署间隔时长,默认10秒。
结果验证
您在金丝雀发布应用后,可以调用GetChangeOrderInfo接口查看变更流程详情,获取金丝雀发布应用的变更状态。具体API参数详情,请参见GetChangeOrderInfo。
调用GetChangeOrderInfo接口查看变更流程详情,返回的执行结果如下:
{
"Message": "success",
"RequestId": "10DA427D-AF74-4ECE-BB0A-EECC0EBF7548",
"Code": 200,
"changeOrderInfo": {
"Status": 2,
"Desc": "金丝雀发布(***)",
"PipelineInfoList": {
"PipelineInfo": [
{
......
//此处未罗列全部执行结果,仅供参考。
请查看上述执行结果中的changeOrderInfo.Status参数值,通过该值判断金丝雀发布应用的变更是否成功。changeOrderInfo.Status的取值如下:
0:准备
1:执行中
2:执行成功
3:执行失败
6:终止
8:手动分批发布模式下,等待手工确认执行下一批。
9:自动分批发布模式下,等待下一批执行中。
10:系统异常执行失败