ECS 服务 - 使用新的 Docker 映像自动部署

Posted

技术标签:

【中文标题】ECS 服务 - 使用新的 Docker 映像自动部署【英文标题】:ECS Service - Automating deploy with new Docker image 【发布时间】:2015-10-07 17:14:26 【问题描述】:

我想通过使用最新的 Docker 映像启动我的 ECS 服务来自动部署我的应用程序。据我了解,部署新镜像版本的方式如下:

    创建新的任务修订版(在更新 Docker 存储库上的映像之后)。 更新服务并指定新版本。

这似乎可行,但我想通过 CLI 完成这一切,以便编写脚本。 #2 似乎很容易通过带有 update-service 的 AWS CLI 完成,但我看不到在不重新指定整个任务 JSON 的情况下执行 #1 的方法,就像 register-task-definition 一样(我的 JSON 将在环境中包含凭证变量,所以我想在尽可能少的地方拥有它)。

这就是我应该如何自动部署我的 ECS 服务更新的方式吗?如果是这样,是否有一种“好”的方法可以让任务定义启动新的修订版(即不复制所有内容)?

【问题讨论】:

诀窍是describe-task-definition 将包含您的原始任务定义,其中 containerDefinitions 作为键。我已经成功地修改了它,然后运行register-task-definition 来注册一个新的定义。如果您担心 ENV,最简单的解决方案是使用非 bash SDK 之一。 【参考方案1】:

是的,这是正确的方法。

不,使用当前 API,您无法在不复制现有任务定义的情况下注册新版本。

如果您没有使用 CLI 来生成原始任务定义(或者不想重用生成它的原始命令),您可以通过 CLI 尝试如下操作:

OLD_TASK_DEF=$(aws ecs describe-task-definition --task-definition <task_family_name>)
NEW_CONTAINER_DEFS=$(echo $OLD_TASK_DEF | jq '.taskDefinition.containerDefinitions' | jq '.[0].image="<new_image_name>"')
aws ecs register-task-definition --family <task_family_name> --container-definitions "'$(echo $NEW_CONTAINER_DEFS)'"

并非 100% 安全,因为最后一个命令的 --container-defintions 参数(包括 "environment" 条目)仍将通过 ps 等进程可见。 AWS 开发工具包之一会让您更加安心。

【讨论】:

您可能还需要其他部分,例如卷。只需使用 jq 解析它,然后将选项(例如 --volumes VOLUMES_DEF)附加到 register-task-definition【参考方案2】:

Matt Callanan 提供的答案对我不起作用:我在这部分收到错误:

--container-definitions "'$(echo $NEW_CONTAINER_DEFS)'"

导致:解析参数“--container-definitions”时出错:预期:“=”,输入:“””:

' 环境:[ etc etc....

我解决它的方法是:

TASK_FAMILY=<task familiy name> 
DOCKER_IMAGE=<new_image_name>
LATEST_TASK_DEFINITION=$(aws ecs describe-task-definition --task-definition $TASK_FAMILY)

echo $LATEST_TASK_DEFINITION \
     | jq 'containerDefinitions: .taskDefinition.containerDefinitions, volumes: .taskDefinition.volumes' \
     | jq '.containerDefinitions[0].image='\"$DOCKER_IMAGE\" \
     > /tmp/tmp.json

aws ecs register-task-definition --family $TASK_FAMILY --cli-input-json file:///tmp/tmp.json

我从原始 json 文档中获取了 containerDefinitions 和 volumes 元素,因为我的 containerDefinition 使用了这些卷(所以如果你不使用卷就不需要它)。

【讨论】:

【参考方案3】:
#!/bin/bash
SERVICE_NAME="your service name"
IMAGE_VERSION="v_"$BUILD_NUMBER
TASK_FAMILY="your task defination name"
CLUSTER="your cluster name"
REGION="your region"


echo "=====================Create a new task definition for this build==========================="
sed -e "s;%BUILD_NUMBER%;$BUILD_NUMBER;g" taskdef.json > $TASK_FAMILY-$IMAGE_VERSION.json

echo "=================Resgistring the task defination==========================================="
aws ecs register-task-definition  --family $TASK_FAMILY --cli-input-json  file://$TASK_FAMILY-$IMAGE_VERSION.json --region $REGION

echo "================Update the service with the new task definition and desired count================"
TASK_REVISION=`aws ecs describe-task-definition --task-definition  $TASK_FAMILY  --region $REGION | egrep "revision" | tr "/" " " | awk 'print $2' | sed 's/"$//'`


DESIRED_COUNT=`aws ecs describe-services --cluster $CLUSTER --services $SERVICE_NAME  --region $REGION | jq .services[].desiredCount`
if [ $DESIRED_COUNT = "0" ]; then
    DESIRED_COUNT="1"
fi

echo "===============Updating the service=============================================================="
aws ecs update-service --cluster $CLUSTER --service $SERVICE_NAME --task-definition $TASK_FAMILY:$TASK_REVISION --desired-count $DESIRED_COUNT --region $REGION


    enter code here

【讨论】:

以上是关于ECS 服务 - 使用新的 Docker 映像自动部署的主要内容,如果未能解决你的问题,请参考以下文章

更新 AWS ECS 服务任务的最佳实践

ECR 映像移动到 ECS(Docker、Gitlab)

ECS 使用 ECR 自动部署

AWS - ECS - 如何在现有 ECS(带有 1 个 EC2)实例上重新部署更新的 Docker 映像?

我可以通过使用 node-exporter docker 映像作为我的微服务的 sidecar 从 AWS ECS Fargate 抓取指标吗?

在ECS中使用哪个ASP.NET Windows容器映像?使用Amazon ECS在基本映像中出现Windows Docker Container兼容性问题