The problem: I need to test something or learn something new and it takes too long to get a clean machine up and running.
The problem: Well it works on MY machine. Why not yours?
On their site their tag line is "Create and configure lightweight, reporducible, and portable development environments."
On their site they show it is this easy to get started.
$ vagrant init ubuntu/trusty64
$ vagrant up
Their tutorial starts off here ; we'll use it as our guide.
Before we get started let us at least get the two major components installed. Those are Vagrant and VirtualBox. Below I've included links to the download section of each.
Quick Note (Aug 22nd 2016) - There is an issue with Vagrant 1.8.5 preventing a lot of this tutorial to work well with CentOS images. But notes this will not be fixed until 1.8.6. Will re-test when it is released.
Current Known Working Versions:
VirtualBox Install Vagrant Install
Okay, lets go through some of the terms we're going t be using in this section so we are all have the same base understanding.
- Vagrantfile - The main configuration file for Vagrant. Yes the V in Vagrantfile must be capitalized.
- Provider - Vagrant can talk to many different APIs to deploy systems in various environments. Think of the term provider as what API we are talking to.
- Vagrant Boxes (Or Box) - This is a Vagrant base image. This is what helps make Vagrant so quick to deploy environments.
In this section we'll discover the basic Vagrant work flow. We'll see that regardless of provider this work flow for the most part remains the same.
Before we do anything we need to create a directory we'll use as our project directory. Each directory represents an environment.
Once we have created our project directory we can create the Vagrantfile with the vagrant init command. The command is followed by which box we want to use in this environment.
$ vagrant init ubuntu/trusty64
Note: The Vagrantfile is very well documented, but we wanted to make it less verbose we could use the --minimal option.
Bringing the machine up is simple.
$ vagrant up
That's it. This command will read our Vagrantfile and bring up a machine based off the provider and the settings in our Vagrantfile.
One of the beautiful things about Vagrant is we do not have to worry so much about passwords and IP addresses to remember. We access our machine via the ssh sub-command.
$ vagrant ssh
Boom! Now we can get work.
In the way we are going to be using Vagrant and Virtualbox we are going to be bringing up and tearing down machines often. We can tear a machine down using the destroy sub-command.
$ vagrant destroy
Note: Keep in mind all of these commands work relative to the machines in the current project directory
There are a few more one-off commands we might use within our workflow.
Checking the status of a machine.
$ vagrant status
Checking the status of ALL the machines
$ vagrant global-status
If you have made changes to your Vagrantfile and need to reload your settings.
$ vagrant reload
If you do want to bring down your machine, but do not want to completely destroy it.
$ vagrant halt
Let us see if we can do the following. For each step, how do we verify our work?
- Get Vagrant and Virtualbox installed
- Create a new Vagrant environment using ubuntu/trusty64 as your box
- Bring your machine up.
- SSH in to your machine and update all of the available packages.
In previous examples we used an Ubuntu Trusty (14.04) box from Vagrant's box repository. There are two sources for additional boxes.
Atlas / Vagrant Cloud - HashiCorp Atlas ( a.k.a Vagrant Cloud)
Vagrantbox.es - Just more boxes. Can be used as secondary source. In most cases we would look to use images form Atlas
As we start to manage additional Vagrant boxes we'll want to use the vagrant box sub-commands to manage this boxes.
List out all of the Boxes
$ vagrant box list
centos/7 (virtualbox, 1607.01)
jhcook/centos6 (virtualbox, 2.6.32.642.3.1)
rscloud (rackspace, 0)
ubuntu/trusty64 (virtualbox, 20160801.0.0)
ubuntu/trusty64 (virtualbox, 20160816.0.0)
xenial (virtualbox, 0)
Add a new box without a vagrant init
$ vagrant box add <SOME-NAME>
Remove a box once it is no longer needed
$ vagrant box remove <SOME-NAME>
There are two ways we can access our guest VM from our host machine.
The following will configure the host machine to forward port 8080 to port 80 of our guest VM.
config.vm.network "forwarded_port", guest: 80, host: 8080
With this setting we can access our VM via http://127.0.0.1:8080
The following will configure an additional NIC on our guest machine. It will assign the NIC the IP address of 192.168.33.10.
config.vm.network "private_network", ip: "192.168.33.10"
With this setting we can access our VM via http://192.168.33.10
Vagrant's main purpose is to deploy an environment. It talks to the API and configures and creates VMs. The other of the environment is configuration management. Vagrant can use a number of provisioners such as Shell, Ansible, Salt Stack, Puppet and Chef.
The default Vagrantfile gives us an example of using the Shell provisioner.
config.vm.provision "shell", inline: <<-SHELL
sudo apt-get update
sudo apt-get install -y apache2
SHELL
The commands between <<-SHELL and SHELL will be executed on the VM.
Other provisioners can be found on Vagrant's site. https://www.vagrantup.com/docs/provisioning/
If at first we don't succeed . . . . Vagrant allows us to iteratively re-run just the provisioning section of our Vagrantfile.
$ vagrant provision
Up until this point we have only been working with a single machine. Part of the power of Vagrant is we can deploy and configure entire environments.
The following is an example of creating a Vagrantfile with multiple machines.
This file configures two machines with the hostnames of server and client.
Vagrant.configure(2) do |config|
config.vm.define "server" do |server|
server.vm.box = "ubuntu/trusty64"
server.vm.hostname = "master"
server.vm.network "private_network", ip: "192.168.33.100"
server.vm.provider "virtualbox" do |vb|
vb.gui = false
vb.memory = "1024"
end
end
config.vm.define "client" do |client|
client.vm.box = "ubuntu/trusty64"
client.vm.hostname = "slave"
client.vm.network "private_network", ip: "192.168.33.200"
client.vm.provider "virtualbox" do |vb|
vb.gui = false
vb.memory = "1024"
end
end
end
With multiple machines we bring up and access them in a slightly different way.
Bring up the entire environment
$ vagrant up
Note: the following examples refers to what is listed in config.vm.define "SERVER-NAME" Bring up a specific machine.
$ vagrant up <SERVER-NAME>
Connecting to a single machine
$ vagrant ssh <SERVER-NAME>
Destroying a single server
$ vagrant destroy <SERVER-NAME>
Let us see if we can do the following. Use this as a template and expand to try out new ideas. Keep in mind to think about how you would verify each step of your work.
- Create a new project directory
- Create a multi-machine Vagrant file
- The machine should be two different operating systems
- Machine 1 - 192.168.33.100
- Machine 2 - 192.168.33.200
- Configure the shell provisioner to do the following
- Server 1
- Configure Apache, PHP, Wordpress
- Server 2
- Configure MySQL
- Server 1
- Share your Vagrantfile with somebody else and see if they can bring up the same environment.
# Example Vagrantfile for multiple machines
# This file configures two machines with the hostnames of server and client.
Vagrant.configure(2) do |config|
config.vm.define "server" do |server|
server.vm.box = "centos/6"
server.vm.hostname = "cent6"
server.vm.network "private_network", ip: "192.168.33.100"
server.vm.synced_folder "./", "/var/www/html"
server.vm.provision "shell", inline: <<-SHELL
sudo yum update
sudo yum install -y httpd php php-mysql
SHELL
server.vm.provider "virtualbox" do |vb|
vb.gui = false
vb.memory = "1024"
end
end
config.vm.define "client" do |client|
client.vm.box = "centos/7"
client.vm.hostname = "cent7"
client.vm.network "private_network", ip: "192.168.33.200"
client.vm.provider "virtualbox" do |vb|
vb.gui = false
vb.memory = "1024"
end
client.vm.provision "shell", inline: <<-SHELL
sudo yum update
sudo yum install -y mariadb-server
SHELL
end
end
Thank you for taking the time to go through this quick-start tutorial.