As a Mac user I often have to fight the difficulty of installing new kinds of services, databases and other daemons, which have been crafted for a *nix like environment. Even though OS X technically belongs to this family of systems certain types of software don't feel at home instantly. Usually most services can be convinced to do their deed on OS X as well, even though in certain cases it is a quite time consuming process. As I am in the business of presenting at conferences and providing training services for companies, I often need a clean demonstration environment, which is guaranteed to work, regardless of system updates or things I changed while playing around with new technologies. While researching solutions for this problem, I got used to working with VMs running a simple Linux guest system containing all the different environments and services I need. As you might have guessed the last thing I wanted to do is manually managing all those VMs. Fortunately Vagrant in combination with Ansible allows for easy automation of all the necessary steps.
While recently cleaning up some of my VMs, which involved creating proper Ansible playbooks for provisioning, as well as structuring there contents, I ended up thinking, that those virtual machines may be useful for other developers as well. They allow to maintain a clean host system, without having to give up the flexibility of installing all kinds of different services for project or research work.
Because of that I created a repository on github and started putting playground VM definitions there. At the time of writing this blogpost the repository hosts a VM with a recent version of Elasticsearch, as well as one, containing a nvm managed nodejs environment with all kinds of different versions installed. Expect more playgrounds to pop up in the future. Cleaning up all my VMs is ongoing process. I will push each of them to the repository as soon as they are ready.
Using a playground
Using any of the playgrounds is quite simple. First of all you need to checkout the repository:
$ git clone https://github.com/jakobwesthoff/playgrounds.git
All playgrounds are contained inside this single repository. Don't worry about the filesize. The different playgrounds only contain Ansible definitions, which are containing a list of all the needed downloads and installation steps, to correctly provision the VM. Therefore the repository itself is quite small.
Each playground is put into a separate directory. Its name already hints at the purpose of the corresponding VM. Inside each directory a detailed README file can be found. It documents why I created the VM in the first place, as well as which stuff is installed into it once it is provisioned. Further information like ip addresses, exposed services and ports are documented there as well.
After picking a playground to instantiate, change into it's directory and tell Vagrant to bring it to life:
$ cd Node.js $ vagrant up
In order to successfully execute the whole provisioning process you need recent versions of Vagrant and Ansible installed on your system. Mac OS X users can install those two quite easily through homebrew and homebrew-cask:
$ homebrew install ansible $ homebrew cask install vagrant
For other environments please consult your systems package manager or download and install those tools from the corresponding web pages manually.
The before mentioned call to
vagrant up will fetch the base box for the corresponding playground, if it is not already in place. At the time of writing this article all playgrounds are using Ubuntu 14.04 LTS as guest operating system.
After fetching the base box, a new instance of it will be created. Once the VM has been correctly configured and booted, Vagrant triggers Ansible in order to provision it. Ansible will execute each step to download, install and configure the playgrounds environment.
After the provisioning process has finished the playground is ready to be used. While you are inside its directory you can easily create a connection to it by calling
vagrant ssh. This command will drop you straight to a prompt inside the VM. You may either use it from there, or simply talk to the exposed services from your host operating system. Details about different usage possibilities are usually provided within the playgrounds README file.
Some of the playgrounds, like nodejs, utilize shared folders. Those folders allow the easy transportation of files between the VM and the host os. They will be automatically connected through the used virtualization software (VirtualBox by default). The playgrounds README details all of its shared folders, while providing information where exactly they are placed within the VM. For example the nodejs playground does contain a
Shared folder, which is automatically synced with the
/home/vagrant/Shared folder inside of the VM.
As I mentioned before, I am going to publish some more playgrounds in the future. Nevertheless you can help to improve things as well. If you are missing something inside a certain environment already present don't hesitate to add it to the provisioning scripts and submit a pull request. If you take a look at the corresponding Ansible playbooks and roles you will notice, that they are not that complicated. As a matter of fact most of the Ansible configuration is based on YAML files. The configuration of each playground is well structured, clean and self-documenting. It should be quite easy to use what is already there in order to create your own playgrounds containing all the services and environments you may desire. I am looking forward to your pull requests containing new playgrounds and all kinds of amazing things :).