Puppet on Linode
One of the best things to come out of the Continuous Delivery movement is the concept of infrastructure as code. This is the idea that you should treat your servers in the same manner that you treat the programs you write to put on those servers. In other words, you should be able to programmatically specify what type of operating system you want on your server, which packages should be installed, and how they should be configured. Further, all of that should be code, and it should be stored in your version control system and treated with the same rigor as you treat the other code you write.
The movement towards cloud computing has helped this -- we typically no longer have physical servers that have a CD drive and a manually-attended installation. Also, the growth of a number of tools that support this concept (such as Puppet, Chef, Ansible, and SaltStack) have helped the adoption of this concept spread.
To help my learning in this arena, I set up a couple of Linodes earlier this month, installed Puppet on them, and started playing.
Unfortunately, while I was able to find some information about how to accomplish this, some of the Linode docs were outdated. So I'm creating this blog post to help me remember what I did to get up and running.
I needed two Linode servers; one to be the Puppet master node, and one to be the slave. More on that in a bit. For this, I logged into my Linode account in my browser and added 2 Linode 1024 nodes. In the "Settings" tab for them, I named one of the VMs "puppetmaster", and the other "puppetslave." This name will only help you identify the nodes in your Linode manager in your browser...It has no effect on the machine itself. My go-to operating system is Ubuntu, so that's what I installed on them.
Once the Linodes booted, I ensured that the machines each knew who they were supposed to be. For example, on the master node:
The only change I made here was to the first line: added
localhost. And, of course, I made a similar change on the slave node.
Set up DNS "A" Records
For my DNS, I use DNSimple. I logged into my account and added "A" records through the web interface to point
puppetslave.mavelo.us to the newly-created Linodes.
Now it's time to actually install Puppet on each of the servers. On the master, login to the server as root and run:
On the slave, login as root and run:
Create and Sign a Certificate
Puppet uses self-signed SSL certificates to communicate between master and slave. This process starts by having the slave agent create a certificate request, and then signing that certificate on the master node. Because the name of the puppet master
puppet (as above), the slave will automatically know where the master node is (the slave communicates by default with
So, on the slave, create the certificate request:
Then, on the master node, you need to sign the certificate request:
Create a Manifest
Now it's time to actually start using Puppet. To start, you'll need to create a simple manifest file, called
site.pp. This file lives, by default, at
This will install my favorite shell,
tcsh, create a group for me, and also create a user. My user will have a default shell of tcsh, add me to the
mike groups (
mike group is the default), and create my home directory at
Run Puppet on the Slave
By default, Puppet on the slave is probably already running. However, it only checks in with the master for changes once every 30 minutes. I want to check it on-demand. So I killed all running puppet processes via a judicious
kill -9 command.
After Puppet was stopped, I ran Puppet manually:
And just like that, I had a server that was configured to have the packages and users on it that I wanted, configured in the way that I wanted, through something that looks an awfully lot like code.
This whole infrastructure-as-code thing is a very powerful concept. This blog post isn't the end-all-be-all of Puppet or anything like that, and it isn't meant to be. There are many other resources out there for Puppet and any of the other topics covered here, I'm sure. But it scratches my itch.
I have a couple of different follow-ups to this post that I'd like to do, so keep your eyes peeled. I hope to get to them over the next couple of weeks!