Simplifying maintenance with fabric and pycloudsigma

When you’re working with a cloud infrastructure, it’s pretty common that you need to perform the same task on all your servers. Perhaps you need deploy a hotfix, or simply just check what kernel version your servers are running.

The traditional sysadmin way of doing this was to simply write a for-loop in shell-script which fires off the execution of the desired command via SSH on each server. There’s nothing wrong with this approach, but when you are dealing with a large pool of dynamic IPs, it becomes somewhat challenging (not to mention that it is slow and hard to manage on a larger sets of nodes).

A popular tool in the DevOps toolbox is fabric. It is much like the traditional approach, but written in Python and far more dynamic. In this article, we will explore to use fabric in conjunction with our own Python-module to automate tasks.

Before we begin, you need to have both fabric and pycloudsigma installed (both of which can be installed via PyPi).

We’re going to assume that you have already configured pycloudsigma, so let’s dive in. The task we will run is a simple echo on each server that is online. We’re also going to assume that you have SSH enabled and that you have the same username on all servers.

First, we need to create the file fabfile.py with the following content:
[python] import cloudsigma
from fabric.api import run, env

server = cloudsigma.resource.Server()

# Set variables for Fabric
env.disable_known_hosts = True
env.user = ‘cloudsigma’
env.colorize_errors = True
env.hosts = []

def build_host_list():
""" Add all running servers’ public IP to the hosts pool """
for s in server.list():
# Try to get IP of all running servers.
# Will throw an exception on non-running servers.
try:
env.hosts.append(s[‘runtime’][‘nics’][0][‘ip_v4’][‘uuid’])
except:
pass
return None

def say_hello():
run("echo hostname at your service!")

build_host_list()
[/python]

With the file created, let’s run fabric (from the folder you created the above file):

[bash] $ fab say_hello
[u’aaa.aaa.aaa.aaa’, u’bbb.bbb.bbb.bbb’, u’ccc.ccc.ccc.ccc’, u’ddd.ddd.ddd.ddd’] [aaa.aaa.aaa.aaa] Executing task ‘say_hello’
[aaa.aaa.aaa.aaa] run: echo hostname at your service!
[aaa.aaa.aaa.aaa] out: test3.local at your service!
[aaa.aaa.aaa.aaa] out: [bbb.bbb.bbb.bbb] Executing task ‘say_hello’
[bbb.bbb.bbb.bbb] run: echo hostname at your service!
[bbb.bbb.bbb.bbb] out: test2.local at your service!
[bbb.bbb.bbb.bbb] out: [ccc.ccc.ccc.ccc] Executing task ‘say_hello’
[ccc.ccc.ccc.ccc] run: echo hostname at your service!
[ccc.ccc.ccc.ccc] out: test0.local at your service!
[ccc.ccc.ccc.ccc] out: [ddd.ddd.ddd.ddd] Executing task ‘say_hello’
[ddd.ddd.ddd.ddd] run: echo hostname at your service!
[ddd.ddd.ddd.ddd] out: test1.local at your service!
[ddd.ddd.ddd.ddd] out:

Done.
Disconnecting from aaa.aaa.aaa.aaa… done.
Disconnecting from ccc.ccc.ccc.ccc… done.
Disconnecting from bbb.bbb.bbb.bbb… done.
Disconnecting from ddd.ddd.ddd.ddd… done.
[/bash]

Success! As you can see, we ran the command on all servers and got a very readable result back.

This a super simple example to illustrate the concept. We’re really just scraping the surface of fabric’s functionaries.

One concrete example that this could be used for is if you have tagged all your web servers, you could leverage that tag and run a deploy on just those servers.

If you have any questions, feel free to post a comment below.

Happy hacking!

Share this Post

C770b64f01d6b9360b59e8470c2754f4?s=80&r=g

About Viktor Petersson

Former VP of Business Development at CloudSigma. Currently CEO at WireLoad and busy making a dent in the Digital Signage industry with Screenly. Viktor is a proud geek and loves playing with the latest technologies.