 Rwy'n gweithio, wrth gwrs. As I was talking to people last night and today, I could tell people what I was speaking today, I started to dread the inevitable question. What's your talk about then? I would tell them the title, Managing WordPress of Ansible and then wait for the typical response of Managing WordPress with what? So I'd give a quick summary of the talk and then explain that since I'm pretty new to WordPress and wanting to get involved in the WordPress community I took topics that I was comfortable with and hopefully made them relevant and well, here we are. Now, there are lots of David Murphy's in the world so the easiest way to find me is to use my online alter ego, Shrock. I've been using this name since the late 90s and as far as I know I'm the only one using it. There's a story behind the name but it's really not that interesting. I've been messing around with computers since I was around seven years old and working professionally getting paid to mess around with them for over 20 years. Aside from my long standing interest with computers and technology I'm also a husband, a father of four two schools and I live in the very north west of England. I'm also an automatician. I joined automatic just over a year ago and my journey there was a slightly different one than most of my colleagues. Despite being a long time WordPress user in fact my WordPress.com account is over nine years old and a long term fan of open source software I never became involved in developing or extending it. Similarly, while I was aware of the WordPress community I did not actively participate in it. Before automatic I was a canonical working on and with Ubuntu for seven and a half years. And as very predominantly a python shop I haven't even touched PHP for nearly eight years. What brought me to automatic was the company itself of automatic that is inspiring me to become more involved in this, our community. So I titled my talk Managing WordPress of Ansible but the reality is that once it is deployed WordPress especially when combined with plugins like WP, CLI, Jetpack and others is really good at managing itself. That means what we're really talking about today is deploying WordPress of Ansible. I'm going to show you one way to replicate and improve upon the famous five minute install. Now hopefully some of you are asking yourselves why bother? And that's an important question to ask. There are so many great choices out there for hosting, so many options for one-click installs and pre-configured services that you may never have actually installed or deployed WordPress yourself. Or maybe you're lucky enough to have someone or a team do it for you. Then again maybe you don't. Perhaps you still follow the five minute install and FTP your files up and to your web post unaware that there are things, tools that will make your life easier. But before I dive into how to do this I would like to talk a little bit more about why I do it this way. I believe the best way to learn is to do it yourself. Being able to do it yourself is an important life skill. We can learn any subject we put our minds to and exercising that knowledge reinforces our learning more fully than just trying to soak up the knowledge. No matter how much we hated them both tests in school helped us. Remember what we had been taught and led us to put that knowledge into practice. Don't worry there's no quizzes today. Of course while we can learn any skill we still need to be pragmatic. If you primarily consider yourself a designer you may not think learning any form of systems administration is any use. The best use of your time. I disagree with that and that is because it is knowing how to do it yourself but it's the most important part here. When I first got involved with Linux I was looking to replace my copy of Microsoft Windows with something better. I had no idea what I was doing. I would buy books and magazines and I would install the latest distroges from the accompanying CDs and DVDs. Yeah I never quite got what I wanted or anything truly working for that matter. Then a friend introduced me to OpenBSD and it was pretty bare bones that I had been trying. That forced me to learn some basic principles first. When it came time to try something else I was much more comfortable and successful. I did the same thing with email. Running my own server and knowing how it worked. These days like most people I let Google take care about for me but I still have that basic knowledge of how email works. So when there's a problem I can try and figure things out and it's not just with technology but with supplies either. Picking up basic DIY skills around the house when you're dealing with contractors or dealing with a mechanic for your car so it's just that little bit of knowledge really does help you in life. So speaking of getting people to do the work for us it's time to talk about automation. Whoops! It is really hard to spell that with just two Ts these days. That's better. Automation is one of those things that makes our lives easier and we're going to use automation to deploy WordPress. Why automate things? Why bother? Doing the same thing repeatedly is inefficient, prone to error and let's be honest, dull. By automating things we make that same task efficient, consistent and most of all easily reproducible both by ourselves and by others. Sure you may only deploy WordPress once but you know the men let it upgrade itself but what happens if that server crashes or is hacked or if you're lucky you need to add more capacity because your site has blown up in popularity. A little bit of effort now can be huge rewards later on and if you don't have time and then you don't have to remember or even Google how to do things again. Okay, that's enough of why I don't do it this way. Let's talk about what. We have lots of choices in life. Some are easy, some are hard. Some are inconsequential and some are life changing. The choices here aren't quite as significant as that but since I'm talking about my preferred approach to this I wanted to explain some of the thinking behind the choices I made in putting this together. Our first choice is what are we going to deploy. Of course that's easy WordPress. But in reality most of this talk can be applied to any type of software deployment. Our second choice is what are we going to deploy on to. We need an operating system to run our software on and the decision we make will affect our solution as you'll see. There are plenty of platforms to choose from and these are just some of the best ones for us in speech ones. It should be obvious by now but my preference is to run this laptop and I use Linux on all my other machines. Fortunately they're all good. They each have their strengths and weaknesses so pick one, learn it, try it out see if it works for you, if you don't like it try something else. These days my personal preference is for Debian. I'm sure some of you expected to see Ubuntu here but I've come to appreciate the simpler and more consistent approach of Debian when running it on my servers and my other machines. If I was still running Linux on my laptop perhaps my choice would be different. There's an even greater choice here catering for all tastes and requirements since there is so much choice let's take a closer look. Shared hosting is the easiest and cheapest choice but it can be restrictive both in terms of performance and control. It can be a great starting point but it is not to my taste. If you have grow shared hosting it used to be that the only alternatives were to lease a dedicated server or co-locate your own box both of which can be as expensive as they sound. There's a little ground bow and that's virtual private servers. They're exactly what they sound like real machines carved up into lots of little virtual ones. They can provide complete control and can be very flexible but at a fraction of the cost of a dedicated server. A natural progression of the growth of virtual private servers gave us the cloud. On-demand computing which is incredibly flexible and powerful and can be as cheap or as expensive as you choose. However you should be prepared to invest upfront in automation or it can be incredibly inefficient to manage. You also need to be aware that they are not all equal. Just as the different hosting types have their own strengths and weaknesses so do the companies providing them. Do your homework and choose wisely. My choice for local development is vagrant. This is a set of automation tools wrapped around virtual machines so you can get pretty close to the experience of using a virtual private server on your local machine. In addition it has the advantage of keeping your work isolated within those virtual machines to mix and match different operating systems and different software versions and not worry about things tools conflicting. For actual hosting my choice is digital ocean. I find them incredible value for money and they have just the right amount of control. They actually bridge the gap between traditional virtual private servers and a full-blown cloud service like Amazon or Google compute engine. Final choice. What tool are we going to use to deploy? These are just some of the well-known software configuration management that anyone who's paid attention to the title of this talk will know full well that I'm going to use Ansible. In their own words Ansible is a powerful automation tool that you can learn quickly which I definitely do agree with. I've tried them all out and with Ansible I found the scripts quite closely resemble the manual steps that I would take which combined with the fact that everything is done over secure shell and nothing is installed that I don't ask for there's no software agents running. It makes it feel more like true automation compared to some of the other ones which feel programming languages. Ansible has three core concepts that we need to understand. Inventory, playbooks and roles. Today we're only going to look at inventory and playbooks. Roles allow us to break down our playbooks into manageable, reasonable chunks but should be considered a more advanced topic. Let's get started with inventory. Okay, so this is a sample inventory taken straight from their documentation. It is in plain text using the easy to understand any format. Here we can see there are four hosts. Two web servers and two database servers contained within two groups. Ansible makes it easy to target as few or as many machines as we want. For example, we could just specify all or only web servers or even just the DB1 host. We can have multiple groups and hosts can be defined by host name or IP address. Now, what if we have lots of hosts? Here is another example containing 50 web hosts and six database servers using only four lines of text and the naming pattern. A positive argument for naming servers sensibly rather than just after Lord of the Rings characters. Apart from supporting lots of hosts we can also be very clever with our inventory by using groups of groups. Here we have three hosts and two groups. You'll notice that host two is in both the web and database groups and both groups are contained within the site group at the bottom. Ansible allows us to target the union, intersection and difference between groups. For example, if we include the web group but exclude the database group only host one will actually be targeted. So with a simple text file we can describe and target large amounts of servers with ease. You can have multiple inventory files and if you're using a cloud-based computing solution like Amazon EC2 or GCE you can actually have a dynamic generation of this inventory from your running instances. Here is my inventory for the purpose of this talk. The local vagrant host and the production host running on digital ocean, both are running Debian. Now, not all instances are equal but we can easily accommodate that in our inventory. For example, you can see here but I'm telling Ansible to always use the sudo command to elevate privileges on the vagrant host. As by default there we use the vagrant user. While that is not needed on my droplet because we have a root user there which is a security problem in itself but this is just a demonstration. Let's see Ansible in action. That's a lot smaller than I expected it to be. First we're going to run the Ansible command which you might not be able to see and tell it to target all hosts which inventory file we want to use and then tell it to use the ping module. Execute that ping command on both hosts simultaneously and get a successful response just as we would expect. Next we target just the development host of the same command. That works just as we expected. We have a working inventory file now we need something to run against for them. Let's have a look at playbooks. Playbooks are instruction sets. They consist of plays which in turn consist of tasks. Plays can define the inventory groups that they apply to and each play and task will be completed in sequence until the playbook is complete. Again, that's very small. Here is a sample playbook again taken from Ansible's own documentation. This time it is in the Yamel format yet another markup language that provides more structure whilst retaining readability. This contains two plays. The first targeting web servers the second DB servers. Both say the play should be run as the root user and both contain two tasks. For the web servers it uses yum for Fedora package manager to install the latest version of Apache and then creates a configuration file using a template. For the database servers it again uses yum to install the first SQL and ensure that it is running. Each task specifies a module to be used so let's dig into some of those modules. Most Ansible modules and tasks are idempotent. They can be run multiple times and the end result will be the same. There are three types of results from tasks. Changed meaning something was changed. Okay meaning nothing was changed but the command completed successfully and failed which failed. If we ran that example playbook twice we would get multiple change results because something was changed. If we ran it again we would get multiple okay results because nothing was changed but everything was successful. If we changed something and then ran it again it would actually go back and revert our work to set the server back to its expected state. Here are four examples for using the yum module which installs, upgrades and removes packages using the yum package manager. The first one is installing the latest version of Apache as we saw in the playbook. Specifying latest as opposed to present will apply upgrades if available each time the playbook is run. The next one tells yum to remove that same package then use an alternate repository and finally specify a specific version of the package. Since I'm using Debian I'll be using the apt module but they're basically the same principles. Template was the next module that we saw and it is used to create and modify files using variables. It uses Ginger 2 templates which use the same style of curly braces surrounding a variable but you'll be familiar from other templating languages. In both examples we specify a local source stored alongside our playbook and a remote destination along with the ownership and permissions for the resulting file. We can also back up an existing file before using our template so as not to lose anything. Here we see how to use the service module to control services on a remote host well maybe you can't see it actually. We can ensure that it's started or stopped but we don't force it to be restarted or reloaded or just ensure that the service is enabled so that it will start automatically after a reboot. There are lots and lots of modules plenty of official ones and plenty of third party ones too including some specifically for WordPress these are a few of the ones that I regularly use. Command for running arbitrary commands and get URL for well you know getting URLs various apt modules for managing Debian or Ubuntu packages and repositories modules for controlling cloud instances from a variety providers modules for sending notifications I mean who doesn't use Slack these days modules for controlling databases and users and modules for accessing code and version control you can deploy your site straight from Git if you wanted and this is just scratching the surface but you may have noticed a couple missing but you might have expected like Apache or PHP but reality is we already have everything we need to manage rows The common pattern here is to install the package software and control the service in terms of modules all we need are apt to install, template to configure and service to control ok so now we have everything we need to actually deploy WordPress so let's look at what we're going to do now I'm sure most of you will be familiar with these steps first we download and unzip WordPress itself then we create a database we edit the configuration file and finally we upload it but since we're going to be doing this directly on the server we can skip that step however, anyone who's done this before will realise there's some missing details so let's look at a better example we're going to install the packages we need we're going to create the database and the database user to go along with it we're going to download and unzip WordPress we're going to edit the configuration file we're going to configure our web server and ensure that it's running and since we're automating this we also want to be able to reuse our playbook so that we can and will do this by using variables the first part of our playbook is to define values that we want to use and here we have a database name a user and a password as well as the site name in alias with those in place we can install the packages here we're installing the four main packages we need along with two more to help Ansible this does the job but it is very verbose and when we run it it will be very noisy because it's actually running six tasks and of course there's a better way to do this here we're doing exactly the same thing but we're now installing those multiple packages using an array and a variable and a loop, much neater so there we go, we're going to install MySQL server Apache 2, ModPHP5 PHP5, MySQL and a couple of Python libraries once we've got those installed we can set up the database time to use some of those variables that we defined earlier we're going to create the database and the user and grant the user access to the database this requires one of those Python modules I just mentioned so Ansible can talk directly to MySQL next we're going to install WordPress these tasks should be getting pretty easy to understand by now and it's clear to see here but you create a directory download WordPress and then zip it into that directory next configuring WordPress anyone who's installed WordPress before will know that we need some unique and random keys and salts we should create them by hand and there is a we could create them by hand but there is a nice API endpoint that will do that for us and so we're just going to retrieve that using the URI module we also specify that it will create a file to make it idempotent otherwise it would generate new ones every time we run the playbook and that would be pretty bad with our keys and salts in place we can create our config using a template let's have a look at that that or maybe not if that should look familiar if you could see it it's for defaultwpconfig.php with the comments removed, variables added and an include statement added for our keys file almost there we just need to configure our web server here we're going to use another template but now we're going to do a couple of different things first we're asking to restart Apache handler to be notified after we create our config second we're using a command module to execute commands right on the box to control Apache itself to enable and disable sites and surely we'd need to be able to restart Apache again after doing that but the reality is those handlers execute at the very end of the playbook so we can queue them up as many as we like and they'll wait till we end and how do we define handlers they just work like any of a task here it's just calling the service okay that's it our playbook is done and time for another demo this time we're going to use the ansible playbook command in very small writing along with my sensibly named playbook wordpress.yaml and specifying our inventory file okay first it's going to gather some details from the servers that's very quick and then it goes to install the packages that'll take about 15-20 seconds on the boxes I configured this is definitely the longest part of the process while it updates that package list downloads the packages and installs them okay done on one server and done on the second one and then it runs very quickly through the rest of the process you can see that it is returning a change response for all of those events it creates the database and the user it installs wordpress by creating the directory and extracting it generates the keys from our config and manages the web server and there we go that's it we now have a bare bones wordpress site obviously we now have to go through the manual setup but let's go a bit further and do another demo this time I've added four extra hosts to our inventory file it's just going to run through exactly the same process but here we see some of the power of Ansible by reusing and automating so it checks all six servers it hits our first two servers first and there's nothing to do because both packages are already installed so it returns an okay response we're going to wait for a changed response to come from those other four servers and then it will run through the rest of the install process there we go so okay on the first two servers changed on the next four and the rest of the process is just as quick so we now have six servers deployed in exactly the same way at exactly the same state and you could deploy six or six hundred using this process and our original hosts have remained untouched the new hosts have configured exactly the same way and all I did was add a new host into my inventory file now clearly these hosts are not production ready but by combining all the steps shown we can improve on this in lots of ways like installing additional packages PHPGD or downloading plugins we could call WPCLI directly using the command module switch out a patchy for engine X as most people would want to and installing and configuring firewalls as most people should we could also use Ansible for building out a more scalable infrastructure for example multiple web servers speaking to a single database this was a deliberately superficial intro to Ansible and I hope it's whetted your appetite a bit and like all good talks this one was opinionated as I may have mentioned once or twice this is what I've shown here is not best practices for deploying WordPress so please don't use this in production but by sharing my passion for systems administration automation I hope that I've inspired some of you to look further into these topics and see where you can improve your own processes and practices and finally as an ex-pearl hacker I always keep a pearl motto in mind there's more than one way to do it it's all about expanding knowledge and what you do with it try your tools, try distributions see what works for you in return if you have your own solutions I would love to hear about them so I can expand my own knowledge and that's it, thank you ok, if there are any questions then there's a microphone in the middle of the room but I'm sorry but just one have you ever tried to use Ansible with Docker? I haven't I've used Docker but I haven't and I've used Ansible but I've not combined the two yet what would you like to do? based on what you're doing with Vagrant I want to figure out how to do with Docker because I'm trying to move from Vagrant to Docker so I know that you can manage your Docker instances or images using Ansible and use that to deploy into those images as well but it's not something I've actually done myself yet thank you great job there's an open source project Roots Trellis that's like a full featured Ansible set of playbooks even production ready but I was wondering did you know of any more or do you have like any open source set of playbooks for WordPress? there are a couple and I haven't actually got the links on me but I will dig them up afterwards if you want to come and see me there are a couple of very full featured ones there's so many different ways to do this you find something that works for yourself but there are a couple of playbooks come and see me ok thank you any more? Vagrant, Ansible and Puppet or Chef? so I'm definitely going to be opinionated on I've used Puppet quite extensively I disliked it because mainly because of the amount of Ruby in it the manifest that you would write within Puppet were basically full blown scripts with extensive logic and I would find them far too complicated for other people to understand and sometimes a bit magical ansible to me is a lot more logical and does things the way I would do them if I wasn't scripting it how do you handle keeping database credentials and stuff like that out of your repo but still have them accessible to ansible when you do your deployments ok so there's two solutions for this the first one is to use environment variables so I specified the variables within the playbook but you can also do them directly through the environment the second option is a ansible module called Bolt which will store details encrypted so that they can be committed or passed around within the team but they're not visible until ansible actually runs any more? ok that's it thank you