Comúnmente, en un proyecto web, los desarrolladores prueban la aplicación que están construyendo en su propio equipo de trabajo. Pero, muchas veces, configurar y mantener el entorno de desarrollo no es tarea sencilla. Veamos tres posibles escenarios:

  1. Los miembros del equipo de desarrollo usan indistintamente GNU/Linux, Mac OS X o Windows, cada uno con versiones diferentes de bases de datos, intérpretes, dependencias… Esto lleva a inconsistencias y, en muchos casos, el código que funciona en el equipo de un desarrollador no funciona en el de otro.

  2. Estamos desarrollando varios proyectos en paralelo que tienen dependencias que entran en conflicto entre sí.

  3. Entra una persona nueva en el departamento y tiene que instalar y configurar un equipo con todas las dependencias del proyecto antes de poder ponerse a trabajar.

La solución a estos problemas es utilizar máquinas virtuales. Así, podemos aislar el entorno de pruebas del entorno de trabajo y, además, compartirlo entre los miembros del equipo de desarrollo.

Hoy en día disponemos de multiples soluciones de virtualización: VMWare, Xen, VirtualBox, KVM, LXC… Pero requieren instalar el Sistema Operativo desde cero y suelen ser complejas de configurar. Entra Vagrant al rescate.

¿Qué es Vagrant?

Vagrant es una aplicación escrita en Ruby que facilita considerablemente la creación de entornos virtuales de desarrollo. Para ello Vagrant nos abstrae del sistema de virtualización subyacente y nos permite instalar y configurar el software de la máquina virtual con herramientas de automatización como Chef, Puppet o incluso los clásicos scripts de shell.

Manos a la obra

Instalación

Aunque Vagrant puede ser utilizado con varios sistemas de virtualización, vamos a utilizar VirtualBox porque es gratuito, está disponible en las plataformas mayoritarias y funciona con Vagrant sin configuraciones adicionales.

  1. Descargamos la última versión de Vagrant disponible para nuestra plataforma y la instalamos en nuestro sistema.

  2. Descargamos y ejecutamos el instalador adecuado para nuestra plataforma de la página de descargas de VirtualBox. En algunas distribuciones de GNU/Linux podemos añadir a nuestras fuentes su repositorio de paquetes.

Inicio rápido

Inicializamos la configuración partiendo de una imagen de base.

$ vagrant init precise32 http://files.vagrantup.com/precise32.box

Lanzamos la VM.

$ vagrant up

Con estos dos simples comandos ya tenemos funcionando una máquina virtual de Ubuntu 12.04 LTS de 32 bits. Podemos conectarnos a ella por SSH con vagrant ssh y, una vez hemos terminado de usarla, eliminarla con vagrant destroy.

El comando vagrant init crea un fichero Vagrantfile en el directorio donde lo hemos ejecutado que contiene la configuración de la máquina virtual. Estando en ese directorio, con vagrant up podemos volver a levantar la máquina sin necesidad de hacer de nuevo el init.

Boxes

En Vagrant una box es un fichero que contiene la base a partir de la cual se crean las máquinas virtuales. Este fichero puede ser compartido fácilmente para que otros repliquen nuestro mismo entorno de desarrollo.

Antes hemos mostrado cómo crear una máquina virtual con Ubuntu, pero no estamos limitados a este sistema. En la página vagrantbox.es disponemos de un listado enorme de Sistemas Operativos, tanto de 32 como de 64 bits, que podemos utilizar como base para nuestras máquinas de Vagrant. Podríamos incluso crear nuestras propias boxes utilizando Veewee.

Comandos

vagrant init [box-name] [box-url]

Inicializa el fichero de configuración Vagrantfile en el directorio actual. Si se pasan el segundo y el tercer parámetro, se establecen el nombre y la box a utilizar en la configuración.

vagrant up

Levanta la máquina virtual de acuerdo a la configuración del Vagrantfile del directorio actual.

vagrant halt

Detiene la máquina virtual, pero mantiene los cambios que hayamos hecho en ella para la siguiente vez que ejecutemos vagrant up.

vagrant reload

Equivale a hacer un vagrant halt seguido de un vagrant up. Tras hacer cambios en un Vagrantfile es necesario hacer reload.

vagrant suspend

Suspende la máquina virtual, salvando el estado de ejecución actual de forma que pueda ser resumido más tarde y continuar desde ese punto exacto.

vagrant resume

Resume una máquina que ha sido anteriormente suspendida con vagrant suspend.

vagrant destroy

Detiene la máquina virtual y destruye todos los cambios que podamos haber hecho. La siguiente vez que hagamos un vagrant up partirá de una imagen totalmente limpia.

vagrant ssh

Nos conecta por SSH a la máquina virtual en ejecución.

vagrant status

Muestra el estado de las máquinas levantadas con Vagrant.

vagrant box

Comando para gestionar las boxes que tenemos en nuestro sistema.

vagrant package

Exporta la máquina virtual en ejecución en un fichero box que puede ser reutilizado.

Vagrantfile

El fichero Vagrantfile contiene el tipo de máquina virtual y su configuración. Por defecto, tras hacer vagrant init, la configuración solo incluye el nombre de la box que va a usar y su URL. Pero con unas pocas opciones podemos configurar la máquina según nuestras necesidades:

Vagrant.configure("2") do |config|

# Nombre de la box a utilizar
config.vm.box = "precise32"

# Url de donde Vagrant se descargará la box si no existe ya en el sistema
config.vm.box_url = "http://files.vagrantup.com/precise32.box"

# Redirigir el puerto 80 de la VM al 8080 local
config.vm.network :forwarded_port, guest: 80, host: 8080

# Asignar una IP a la VM que es solo accesible desde nuestro equipo
config.vm.network :private_network, ip: "192.168.33.10"

# Compartir un directorio de nuestro host con la VM
config.vm.synced_folder "~/shared", "/vagrant_shared"
end

Esto es solo un pequeño ejemplo de lo que se puede hacer. Hay muchas más opciones de configuración que pueden consultarse en la documentación de Vagrant.

Providers

  • VirtualBox: Es el proveedor de virtualización por defecto de Vagrant.

  • VMWare: Se recomienda en caso de usar Vagrant para crear arquitecturas en producción, ya que tiene mejor rendimiento que VirtualBox. Es necesario adquirir la licencia para usarlo.

  • AWS: Existe un plugin no oficial de Vagrant, vagrant-aws, que permite desplegar nuestro entorno en la nube de Amazon.

  • Otros proveedores: Vagrant se puede extender mediante plugins escritos en Ruby, por lo que podríamos crear nuestro propio proveedor personalizado.

Provisioning

La mayoría de las veces la box que utilicemos vendrá con poco más que el SO instalado. Podremos acceder a la máquina con vagrant ssh e instalar a mano el software que necesitemos. Pero mejor que eso es utilizar los provisioners de Vagrant que automatizan el proceso de instalar y configurar el software. Disponemos de varias alternativas:

  • Shell: La forma más simple de aprovisionar la máquina virtual es definir un script de shell que se lanzará al realizar vagrant up.

  • Ansible: Ansible es un framework de automatización que se sirve de configuraciones escritas en documentos YAML para orquestar los despliegues.

  • Chef Client: Chef es una herramienta para la gestión de configuración y aprovisionamiento automático de sistemas. Utiliza una arquitectura Cliente-Servidor y las configuraciones, denominadas recetas, se escriben en un DSL sobre Ruby.

  • Chef Solo: Chef Solo es una variante de Chef que no necesita el nodo servidor para funcionar. Todas las recetas que utilicemos deben residir en el disco.

  • Puppet Agent: Puppet es un software de automatización similar a Chef. Al igual que éste tiene una arquitectura Cliente-Servidor y las configuraciones pueden ser escritas en Ruby, aunque el lenguaje principal es un DSL propio de Puppet.

  • Puppet Apply: Es el equivalente a Chef Solo para Puppet. No requiere del Puppet Master para funcionar.