I am currently having a docker container running on a fargate that is working well automatically turning on and off to run a workload. Due to restrictions in memory and I want to have more GBs than 30GB, I wanted to move to EC2 version of ECS task. The task is running in EC2 instance created but doesnt turn off after the task is completed.
I want to know how to configure this automatically using ECS.
ECS Cluster Auto Scaling should be able to scale your EC2 cluster back to 0 instances if you have no tasks running on it. Have a look at this blog.
Related
I have a service that needs to run on our own EC2 instances, since it requires some support from the kernel. My previous experience is all with containers in AWS. The application itself is distributed as a single JAR file and I'm looking for advice for how I should automate deployments. The architecture is:
An ALB in front of the ASG.
EC2 instance running a single Java application.
Any open sockets are open for an hour tops and to not cause any trouble, we have to drain the connections to the EC2 instances before performing an update, so a hard requirement is for the ALB to stop opening new connections for an hour before updating the software. The application is mission critical and ECS has had some issues last year, so I want to minimize the AWS services I depend on. While I could do what I want on my own ECS cluster with custom AMIs, I don't want to do it, since I will run a single instance of the app per host and don't need the extra layer.
My question: What is the simplest method to achieve this using CodePipeline? My understanding is that I need to use a CodeDeploy deployment step to push something to bare EC2 instances. How does draining with an ALB work in this case? We're using CloudFormation for the deployment.
You need to use codedeploy. You can find tutorial on AWS codedeploy documentation.
Codedeploy deployment lifecycle hooks for EC2.
https://docs.aws.amazon.com/codedeploy/latest/userguide/reference-appspec-file-structure-hooks.html#appspec-hooks-server
I have an ECS cluster which i have an ec2 instance tied to and a scheduled task set to run daily using the 'Scheduled Tasks' functionality on the ECS dashboard.
This task runs a a bunch of containers that are each relatively expensive in memory, and this is compounded even more so with all the containers running at once.
I do not currently have a service set up for the ECS cluster and it is my understanding that for my goals, running a set task on some interval, a service would not be used.
AWS's definition of a service in there ECS docs says:
An Amazon ECS service enables you to run and maintain a specified number of instances of a task definition simultaneously in an Amazon ECS cluster.
Since this is not what I want; instead i need to just run a task on some scheduled interval i gather i do not need an service tied to my ECS cluster.
My question is on how to set up autoscaling for my scheduled tasks? The only references i can find to auto scaling within an ECS cluster are to do with creating ecs services that auto scale - which again, is not what I want (at least from how i understand ecs services to work).
What I need is for my ec2 instances to auto scale with my scheduled task running, allocating more resources as need for the task to run. Would I just need to set up auto scaling on the specific ec2 instance the ecs cluster is tied to from within the ec2 dashboard or is there some other way to do this from ECS directly?
I want; instead, I need to just run a task on some scheduled interval I gather I do not need a service tied to my ECS cluster.
For the above use case better to use fargate and you will not maintain or worry about auto-scaling scheduling, all you need to setup schedule task and AWS will take care of memory and other resources required for your task plus you will only pay for the resources that were used by you ECS task, unlike EC2 type task where you pay for the container instance.
AWS Fargate is a serverless compute engine for containers that works with both Amazon Elastic Container Service (ECS) and Amazon Elastic Kubernetes Service (EKS). Fargate makes it easy for you to focus on building your applications. Fargate removes the need to provision and manage servers, lets you specify and pay for resources per application, and improves security through application isolation by design.
aws fargate
Create a cloud watch rule base on some schedule that will trigger the task, make sure that the container exit once it completes the job, fargate will automatically stop the container.
cloudwatch-event-rule-to-invoke-an-ecs-task
I have a dockerized Jenkins build server set up like below and I want move it to AWS.
I have some questions on how to do it, Thanks.
Is ECS the right choice to deploy dockerized Jenkins agents?
Is Fargate launch type of ECS support Windows containers?
I know ECS can dynamically provision EC2 instances, can ECS provision like below?
a. If there is no job to build, there is no ECS2 instance running in the cluster.
b. If a build job started, ECS dynamically launch a EC2 instance to run the dockerized agents to handle it.
c. After build job is finished, ECS cluster will automatically stop or terminate the running EC2 instance.
==================================================================
Jenkins master:
Runs as a Linux container hosted on a UBUNTU virtual machine.
Jenkins Agents:
Linux Agent:
Runs as a Linux container hosted on the same UBUNTU virtual machine as master.
Windows Agents:
Runs as a windows container hosted on a Windows server 2019.
Well, I have some tips for you:
Yes, ECS can dynamically provision EC2 Instances using autoscaling, but only when the threshold of a metric is reached in cloudwatch and an alarm is thrown out and autoscaling start to works. Start a task in ECS with a jenkins master server, and then start 1 or 2 agents when you go to execute a job is not a good tactic neither practical idea, who going to wake up these tasks?
If you want to use a jenkins docker inside an EC2 instance and you have a master node running and you want to keep stopped your unused agents and start it only if is needed by a job maybe in your Jenkinsfile you can call a lambda function to start your agent, here and example in a Jenkinsfile:
stage('Start Infrastructure') {
steps {
sh '''
#!/bin/bash
aws lambda invoke --function-name Wake_Up_Jenkins_Agent --invocation-type Event --log-type Tail --payload '{"node":"NodeJS-Java-Agent","action":"start"}' logsfile.txt
'''
}
}
And later another stage to stop your agent, but your master node need to be online because it is the key and main component either called from the repository or your CI/CD process. Also you need to implement the lambda with a logical procedure to start or stop the instance.
In my experience run Jenkins directly in EC2 is a better choice that run it in ECS or Fargate.
Has anyone been able to configure selenoid on aws ecs ? I am able to run the selenoid-ui container but the selenoid hub image keeps throwing an error regarding the browsers.json however I have not been able to find a way to add the browsers.json file because it stops before it executes the CMD command
There is no point to run selenoid on AWS ECS, as your setup won't scale (your browser containers will be launched on the same EC2 instance where your selenoid container is running). With ECS, you run your service on a cluster, so either your cluster contains on 1 EC2 instance, or you waste your compute resources.
If you don't need scaling, I'd suggest you run selenoid on simple EC2 instance with docker installed. If you do want to have scaling, then I suggest you to take a look at a commercial version of selenoid (called Moon), which you can run on AWS EKS.
We have an AutoScaling Group that runs containers (using ECS). When we add OR replace EC2 instances in the ASG, they don't have the docker images we want on them. So, we run a few docker pull commands using cloud-init to fetch the images when they boot up.
However, the ASG thinks that the new instance is ready, and terminates an old instance. But in reality, this new instance isn't ready until all docker images have been pulled.
E.g.
Let's say my ASG's desired count is 5, and I have to pull 5 containers using cloud-init. Now, I want to replace all EC2 instances in my ASG.
As new instances start to boot up, ASG will terminate old instances. But due to the docker pull lag, there will be a time during the deploy, when the actual valid instances will be lesser than 3 or 2.
How can I "mark an instance ready" only when cloud-init is finished?
Note:I think Cloudformation can bridge this communication gap using CFN-Bootstrap. But I'm not using Cloudformation.
What you're look got is AutoScaling Lifecycle Hooks. You can keep an instance in the Pending:Wait state until you're docker pull has completed. You can then move the instance to InService. all of this can be done with the AWS CLI so it should be achievable with an AWS AutoScaling command before and after your docker commands.
The link to the documentation I have provided explains this feature in detail and provides great examples on how to use it.