We’re excited to announce that we’ve open sourced another project! drone-deploy-ecs is a Drone plugin that enables you to deploy updates to ECS. It’s important to mention that our plugin is opinionated and while it fits our needs nicely, it may not fit yours quite right!
For a bit of context, our engineering team has recently made the decision to migrate from Docker on EC2 to AWS ECS. All of our EC2 deployments are done with bespoke scripts. We knew that moving to ECS would require us to refactor our deployment processes, so we figured we’d wrap all of them up into a single tool that fit into our CICD solution.
Project link: https://github.com/AssemblyAI/drone-deploy-ecs
Approach
We first looked at CodeDeploy as our ECS deployment solution. Our team has experience with CodeDeploy and CodeDeploy has a nice integration with ECS. That said, we don’t want to leverage any of the other Code suite offerings, which means that we’d have to write something to interface with CodeDeploy directly. If we did that, we’d introduce another layer of complexity and in our experience, it’s best to keep your deployment process as simple as possible.
Crossing off CodeDeploy meant that our ECS deployment type would have to be either ECS or an external deployment controller. External deployment controllers introduce a lot of complexity, so we ruled that option out.
That left us with using ECS as our deployment controller. This controller types has built-in rollbacks via the deployment circuit breaker. Initially we tried to offload rollbacks to ECS but found that ECS rollbacks don't reliably fail deployments when containers fail to start.
Writing the Plugin
Writing Drone plugins is pretty simple. Drone exposes plugin settings as environment variables so you don’t have to worry about reading configurations or handling arguments. Because Drone plugins are simply containers that make heavy use of environment variables, there’s nothing stopping you from using a Drone plugin in another build tool. We really like that flexibility.
We decided that we wanted our plugin to only modify a single container within a Task Definition. Our reasoning is that our Task Definitions are simple and most only have one container. Those with multiple containers have one “service” container that gets updated regularly and one or more sidecar-type containers that we update infrequently. The decision to only update one container within a Task Definition helped us keep the plugin’s surface area as small as possible.
Using the Plugin
steps:
- name: deploy
image: public.ecr.aws/assemblyai/drone-deploy-ecs
settings:
aws_region: us-east-2
# The name of the ECS service
service: webapp
# The name of the ECS cluster that the service is in
cluster: dev-ecs-cluster
# The name of the container to update
container: nginx
# The image to deploy
image: myorg/nginx-${DRONE_COMMIT_SHA}
# How many times to check deployment status until timeout
max_deploy_checks: 10
Here's what the settings do:
aws_region
: Sets the region for the AWS SDK. This allows you to run Drone in, say, us-east-1, but deploy to eu-west-2.service
: The name of the ECS service that you want to deploy tocluster
: The name of the ECS cluster the service is incontainer
: The name of the container to updateimage
: The updated image to deploymax_deploy_checks
: How many times to check the status of a deployment before considering it failed and rolling back. This setting is optional with a default value of 60. The plugin waits 10 seconds between status checks, so max_deploy_checks: 60 means that a failing deployment won't be rolled back for 600 seconds.
Things to Look Out For
The IAM permissions required by the plugin are listed in the README
.
Only one container in a given Task Definition can be updated at a time. We don’t have plans to change this but we are open to pull requests to add support for this use case.
What’s Left to Do
We’d like to get our plugin into the Drone Plugin Registry sometime in the near future. And at some point in the near future, we plan to push ARM builds!
If you have any questions about this post, always feel free to reach out to our team at support@assemblyai.com!