Maintaining EC2 Servers with Chef Server - amazon-web-services

I have a hosted chef account working with AWS EC2 instances.
The instances can connect to hosted chef by way of chef-client and run the inital
run_list that is presetly a role called servers. Everything runs and installs
correctly on initial provision.
I should also mention I have autoscaling on ec2 instances that increses the amount of instances
provisioned on an 'as needed' basis and this works fine.
I found one talk that sort of makes sense but seems a bit more involved.
https://www.youtube.com/watch?v=yHub6E4DNvg
My questions are around how to maintain the servers after initial provisioning. First, if I have an update to my role to include more cookbooks or configuration, and how would I push this out to say X amount servers in a simple way.
Second, how would chef server know if a node has failed and notify the admin?
Any guidance?

That's quite vast question ...
For the easy one: failing node => the solution is to use report handlers see the doc here
For the keep in desired state, the idea is to have chef run periodically on the nodes, so it keep enforcing the conf defined in cookbooks, any change will be updated accordingly. (that's the way chef has been concepted).
If you want more control on which server run when you can:
use the push-jobs addon (commercial addon, not free)
use some orchestration tool (I personnaly use rundeck for adhoc runs in addition to periodic runs).
There's a lot of way to do this and which one to use is a question of preference and environment.

I think you could also use knife to run a chef-client based on a certain criteria:
knife ssh 'role:somerole' 'chef-client' -x username -P password
Here is chef's documentation: https://docs.chef.io/knife_ssh.html

Related

Capistrano and Auto-Scaling AWS

We're trying to figure out the best way to deploy to an auto-scaling AWS setup using Capistrano, and stuck on the best way to ensure new servers automatically get the latest code, without having to rely on AMIs.
Any ideas?
Using User Data, you can have your EC2 instances pull the latest code each time a new instance is launched.
More info on user data here: http://docs.aws.amazon.com/AWSEC2/latest/UserGuide/user-data.html
tldr: user data is pretty much a shell script thats executed when your ec2 instance launches. you can get it to pull the latest code and run it
#Moe's answer (or something like it is the right one). But just as another thought, you could write some Ruby which queries AWS on deploy to fetch the list of servers to which Capistrano will deploy. The issue with this approach is that you will have to manually deploy to all servers every time auto-scaling adds a server, which kind of defeats the purpose.

How to deploy to autoscaling group with only one active node without downtime

There are two questions about AWS autoscaling + deployment which I cannot clearly answer:
I'm currently trying to figure out, whats the best strategy to deploy to an EC2 instance behind an ELB which is the only member of an autoscaling group without downtime.
By now the EC2 setup will be done with puppet including the deployment of the application, triggered after an successful build by jenkins.
The best solution I have found is to check per script how many instances are registered at the ELB. If a single one is registered, spawn a new one, which runs puppet on startup (the new node will be up to date) and kill the old node.
How to deploy (autoscaling EC2 behind an ELB) without delivering two different versions of the application?
Possible solution: Check per script how many EC2 instances are registered to the ELB, spawn the same amount of instances, register all new instances and unregister all old ones.
My experiences with AWS teacher me that AWS has a service for everything. So are there any services out there to accomplish my requirements and my solutions are inconvenient?
You can create an entirely new environment with its own ELB and when it's ready and checked, you switch the DNS record to the new ELB.
Anyway for a brief time (60 seconds or so, depending on the TTL of your DNS record) some users will see your old version while some others will see the new version.
In the end there were two possible solutions. Both of them would temporarily deliver two versions of the app.
Use AWS CodeDeploy to perform an sequential deployment (one after another). This solution offers the possibility to rollback to a previous state and visual shows the state and results of the deployment.
Create a python script to get the registered nodes (using Boto) and run the appropriate puppet script on them (using Fabric). This solution offers more control of the deployment but requires some time to build these script. Also there can be bugs..
For now I choose AWS CodeDeploy because its already available and - hopefully - well tested.

chef provisioning recipe to make AWS security groups, how to run from server vs chef client

I need to keep track of my AWS security groups better.
The recipes that use chef/provisioning/aws_driver would let me make recipes per SG and track IPs added/etc.
I can run them just fine locally with chef-client -z -r
What I really want is to upload the cookbook to my chef server and run it any time I need to change a SG. But chef seems to require recipes apply to nodes, not to AWS cloudiness.
Basically I want to run chef-client from my workstation and have it execute a cookbook that doesn't impact any running servers, or create them, but rather hits AWS and converges the resources specified.
If you create a client.rb for your workstation with the chef server URL and keys:
chef_server_url "http://servername/organizations/myorg"
validation_key "path/to/validation/key"
client_key "path/to/client/key"
you should be able to run provisioning recipes that have been uploaded to the server. E.g. if they're in a 'provisioning' cookbook:
chef-client -c client.rb -o provisioning::myrecipe
You probably want to create a provisioning node. Chef Server is essentially a glorified database and isn't intended to be an active controller. There is Chef Push Jobs, but even that is pushing to nodes.
Instead, create a node that is essentially a proxy for the resource that can't run chef client itself, and have that run chef client as a CRON service. Of course you don't need to create a separate node for every resource, one node can easily manage many of them. If you have a very large number you might have to start partitioning these resources. Or you might partition for security causes.
If everything is a declarative resource that behaves idempotently (as all good Chef things should be), then you can have two nodes with the same recipes to provide redundancy.

Boot strapping AWS auto scale instances

We are discussing at a client how to boot strap auto scale AWS instances. Essentially, a instance comes up with hardly anything on it. It has a generic startup script that asks somewhere "what am I supposed to do next?"
I'm thinking we can use amazon tags, and have the instance itself ask AWS using awscli tool set to find out it's role. This could give puppet info, environment info (dev/stage/prod for example) and so on. This should be doable with just the DescribeTags privilege. I'm facing resistance however.
I am looking for suggestions on how a fresh AWS instance can find out about it's own purpose, whether from AWS or perhaps from a service broker of some sort.
EC2 instances offer a feature called User Data meant to solve this problem. User Data executes a shell script to perform provisioning functions on new instances. A typical pattern is to use the User Data to download or clone a configuration management source repository, such as Chef, Puppet, or Ansible, and run it locally on the box to perform more complete provisioning.
As #e-j-brennan states, it's also common to prebundle an AMI that has already been provisioned. This approach is faster since no provisioning needs to happen at boot time, but is perhaps less flexible since the instance isn't customized.
You may also be interested in instance metadata, which exposes some data such as network details and tags via a URL path accessible only to the instance itself.
An instance doesn't have to come up with 'hardly anything on it' though. You can/should build your own custom AMI (Amazon machine image), with any and all software you need to have running on it, and when you need to auto-scale an instance, you boot it from the AMI you previously created and saved.
http://docs.aws.amazon.com/gettingstarted/latest/wah-linux/getting-started-create-custom-ami.html
I would recommend to use AWS Beanstalk for creating specific instances, this makes it easier since it will create the AutoScaling groups and Launch Configurations (Bootup code) which you can edit later. Also you only pay for EC2 instances and you can manage most of the things from Beanstalk console.

efficient way to administer or manage an auto-scaling instances in aws

As a sysadmin, i'm looking for an efficient way or best practices that you do on managing an ec2 instances with autoscaling.
How you manage automate this following scenario: (our environment is running with autoscaling, Elastic Load Balancing and cloudwatch)
patching the latest version of the rpm packages of the server for security reasons? like (yup update/upgrade)
making a configuration change of the Apache server like a change of the httpd.conf and apply it to all instances in the auto-scaling group?
how do you deploy the latest codes to your app to the server with less disruption in production?
how do you use puppet or chef to automate your admin task?
I would really appreciate if you have anything to share on how you automate your administration task with aws
Check out Amazon OpsWorks, the new Chef based DevOps tool for Amazon Web Services.
It gives you the ability to run custom Chef recipes on your instances in the different layers (Load Balancer, App servers, DB...), as well as to manage the deployment of your app from various source repositories (Git, Subversion..).
It supports auto-scaling based on load (like the auto-scaling that you are already using), as well as auto-scaling based on time, which is more complex to achieve with standard EC2 auto-scaling.
This is relatively a young service and not all functionality is available already, but it might be useful for your.
patching the latest version of the rpm packages of the server for
security reasons? like (yup update/upgrade)
You can use puppet or chef to create a cron job that takes care of this for you (the cron would in its most basic form download and or install updates via a bash script). You may want to automatically upgrade, or simply notify an admin via email so you can evaluate before apply updates.
making a configuration change of the Apache server like a change of
the httpd.conf and apply it to all instances in the auto-scaling
group?
I usually handle all of my configuration files through my Puppet manifest. You could setup each EC2 instance to pull updates from a Puppet Server, then you can roll out changes on demand. Part of this process should be updating the AMI stored in your AutoScale group (this is done with the Amazon Command Line tools).
how do you deploy the latest codes to your app to the server with less
disruption in production?
Test it in staging first! Also a neat trick is to versioned deployments, so each time you do a deployment it gets its own folder (/var/www/v1 /var/www/v2 etc) and once you have verified the deployment was successful you simply update a symlink to point to the lastest version (/var/www/current points to /var/www/v2).
OpsWorks handles all this sort of stuff for you so you can look into that if you don't want to do it all yourself.
how do you use puppet or chef to automate your admin task?
You can use Chef or Puppet to do all sorts of things, and anything they can't (or you don't know how to) do can be done via a bash/python script that you invoke from Chef or Puppet.
I normally do things like install packages, build custom packages, set permissions, download things, start services, manage configuration files, setup cron jobs etc
I would really appreciate if you have anything to share on how you automate your administration task with aws
Look into CloudFormation. This can help you setup all your servers and related services (think EC2, LBS, CloudWatch) through configuration files, thus helping you to automate your entire stack (not just the EC2's Operating System).