Tag Archives: chef

Configuration Management

We create Ruby on Rails Web Applications, mainly in several environments, so that is really important not only the automated Deployment for us, but the automated installation (Configuration) also. For Server side, we use dedicated Ubuntu LTS Systems, on the usual providers: AWS, DO, Linode …

We use Capistrano for automated deployments, and we searched years ago for a tool for Configuration Management. We were evaluating all market possibilities: Chef, Puppet, Salt, Ansible …. And finally we decided Chef for a reason: We know ruby so writing recipes in ruby was a big advantage.

But working with Chef Solo we found several limitations:

  • Need to install Chef Agent in node, which makes the process heavy.
  • You need to run all tasks on every setup command, it delays debugging tasks.
  • Debugging errors are a hell, there is not a clear help for errors. Indeed the documentation is sometimes poor.

Probably regarding that situation Ansible server agent-less promise would be the best option. But I found several inconveniences:

  • Language based on YAML, really verbose (try to install a big list of packages)
  • We would lose ruby for writing recipes.
  • Working with environments/roles is not really standardized.

What do we really need?

  • Write recipes (scripts) in Ruby, in our well-known and loved language.
  • Agent-less server side. Solve everything with an ssh connection.
  • Work with variables.
  • Work with environment/roles variables and configurations.
  • Work with templates for configuration files.

Chef, Ansible, Salt … Are really powerful, but:

  • Do we need OS compatibility? No, we use Ubuntu LTS versions.
  • Do we need complicated idioms? No, we have ruby and Shell scripts.
  • Do we need Warehouses or Galaxies of recipes? well … yes, they are useful, but sometimes they are solved with a shell script.

Sometimes, the solution is the easiest way. Shell scripting ? near, but what about ruby, variables or templates …. Capistrano 3:

  • Based on Ruby rake tasks.
  • Only SSH connections, based on SSHkit.
  • Working with roles, environments and variables out of the box.
  • We know the tool because our deployments are based on this.
  • We will integrate the standard recipes into our prun-ops gem.

Yes, we need templates, but we have ERB in Ruby, and googling a while we can find an easy solution for templating.

Today our analysis gives Capistrano 3 as the best way to go, tomorrow … who knows?

Docker basics

Installation

[On Ubuntu 14.04] Installation:

sudo apt-get update
sudo apt-get install -y docker.io
sudo ln -sf /usr/bin/docker.io /usr/local/bin/docker
sudo sed -i '$acomplete -F _docker docker' /etc/bash_completion.d/docker.io

Last version installation:

wget -qO- https://get.docker.io/gpg | sudo apt-key add -
sudo sh -c "echo deb http://get.docker.io/ubuntu docker main > /etc/apt/sources.list.d/docker.list"
sudo apt-get update
sudo apt-get install lxc-docker -y

Removing sudo for commands

I order to avoid ‘sudo’ prefix in all docker commands, here I write a tip for removing sudo from all Docker commands:

# Add the docker group
sudo groupadd docker
 
# Add the connected user "${USERNAME}" to the docker group.
sudo gpasswd -a ${USERNAME} docker
# Logout/Login with this user for changes to take effect
 
# Restart the docker daemon.
sudo service docker.io restart

Run your first container

Docker Hub is the big repo of images. You can login by ‘docker login’

Download image and run container console:

docker run -t -i ubuntu:14.04 /bin/bash
root@af8bae53bdd3:/# pwd
/
root@af8bae53bdd3:/# exit

Basic operations

Operations with Containers:

  • ‘docker ps [-a] CONTAINER’ containers running (-a shows all including stopped)
  • ‘docker logs -f CONTAINER’ container standard output
  • ‘docker top CONTAINER’ container processes running list
  • ‘docker inspect CONTAINER’ container low level json report
  • ‘docker stop CONTAINER’ stops the container
  • ‘docker start CONTAINER’ restarts a container previously stopped
  • ‘docker rm [-f] CONTAINER’ removes definitely a container previously stopped. ‘docker rm -f $(docker ps -a -q)’ removes all containers.

Operations with images:

  • ‘docker images’ list images in workstation
  • ‘docker search TERM’ search images (look at Docker Hub)
  • ‘docker tag [ID] [NAME]:[TAG]’ tags an image
  • ‘docker push [NAME]’ upload image to Docker.hub
  • ‘docker rmi [NAME]’ locally removes an image

Create an Image

mkdir ubuntu-chef
cd ubuntu-chef
touch Dockerfile

And write it:

# Ubuntu + chef-solo
FROM ubuntu:14.04
MAINTAINER Juan Lebrijo "juan@lebrijo.com"

RUN apt-get -y update
RUN apt-get -y install curl build-essential libxml2-dev libxslt-dev git
RUN curl -L https://www.opscode.com/chef/install.sh | bash

Operations with Chef:

  • ‘docker build -t jlebrijo/ubuntu-chef .’ creates an image
  • docker run -d -m 8g –cpuset 0-7 –name rails_stack -p 2222:22 -i jlebrijo/trusty-chef
  • knife solo cook root@localhost -p 2222
  • ssh root@localhost -p 2222

Tricks

  • Stopping all containers: docker stop $(docker ps -a -q)
  • Removing all containers: docker rm $(docker ps -a -q)

Exposing a port on a live container

You need to create an image from your container and restart the container based on this image:

docker stop www
docker commit www www-image
docker rm www
docker run --detach=true --name www -p 2222:22 -p 80:80 -p 443:443 -p 9292:9292 www-image
docker rm www-image

 

Create a Vagrant image file and share on VagrantCloud

Here we will cover how to create a Vagrant Box. In this case I want to install chef-solo over an Ubuntu/trusty image. You can clone all work in this post from this repo https://github.com/jlebrijo/trusty64-chef.

mkdir trusty64-chef
cd trusty64-chef/
rbenv local 2.1.2
gem install bundle

Create Gemfile:

source 'https://rubygems.org'
gem 'vagrant', github: 'mitchellh/vagrant', tag: 'v1.6.4'
gem 'knife-solo'

Install gems:

bundle
bundle install --binstubs .bundle/bin

Create Vagrantfile: ‘vagrant init’. In order to take access to the image, add to Vagrantfile:

config.vm.network :public_network, bridge: "wlan0", ip: "192.168.10.25"

Start box: ‘vagrant up’. Install Chef in the image:

knife solo prepare vagrant@192.168.10.25 ## password: vagrant

Update Ubuntu:

vagrant ssh
sudo apt-get update

Package the Box: `vagrant package –base trusty64-chef_default_1409751631640_92694 –output trusty64-chef.box`

Add to local Box list: `vagrant box add lebrijo/trusty64-chef package.box`

Upload the box to a HTTP server: `scp trusty64-chef.box lebrijoc@files.lebrijo.com:www/lebrijo.com/files`

Create an account and entry in vagrantcloud.com [lebrijo/trusty64-chef](https://vagrantcloud.com/lebrijo/trusty64-chef)