In this example, we're going to create a fully functional LAMP environment for symfony with vagrant. The apache web server will also be accessible from a browser of the host machine so with this way we can access our symfony application from the host machine. We'll also have phpMyAdmin installed and accessible from the host machine as well as run build tests in virtual machine such as php-cs-fixer, phpspec, behat etc.

Our project is called travis; guest domain is set to travis.dev; application is accessible from host machine browser via http://192.168.50.10/; phpMyAdmin is accessible via http://192.168.50.10/phpmyadmin and login credentials are root:root; project source is stored under inanzzz:mac-os $ ..../ubuntu-trusty-lamp/public folder of host machine and under vagrant@lamp:/$ ls -l /var/www/html/ folder of vagrant guest machine; shared folders public and var/www/html are writable in both environments.


Configuration


I'm assuming that you already have installed vagrant and Oracle VM software. I also assume that the ubuntu/trusty64 box is already added to your filesystem with vagrant box add ubuntu/trusty64 command. If you're not sure, you can confirm it with ls -l ~/.vagrant.d/boxes/ command.


Create a new project folder


$ mkdir ubuntu-trusty-lamp
$ cd ubuntu-trusty-lamp/

Create a bootstrap file


Do it when you're in ubuntu-trusty-lamp folder. Name the file as bootstrap.sh.


#!/usr/bin/env bash

# BEGIN ########################################################################
echo -e "-- ------------------ --\n"
echo -e "-- BEGIN BOOTSTRAPING --\n"
echo -e "-- ------------------ --\n"

# VARIABLES ####################################################################
echo -e "-- Setting global variables\n"
APACHE_CONFIG=/etc/apache2/apache2.conf
PHP_INI=/etc/php5/apache2/php.ini
SITES_ENABLED=/etc/apache2/sites-enabled
PHPMYADMIN_CONFIG=/etc/phpmyadmin/config-db.php
DOCUMENT_ROOT=/var/www/html/travis/web
VIRTUALHOST=travis.dev
LOCALHOST=localhost
MYSQL_DATABASE=symfony
MYSQL_USER=root
MYSQL_PASSWORD=root

# BOX ##########################################################################
echo -e "-- Updating packages list\n"
apt-get update -y -qq

# APACHE #######################################################################
echo -e "-- Installing Apache web server\n"
apt-get install -y apache2 > /dev/null 2>&1

echo -e "-- Adding ServerName to Apache config\n"
grep -q "ServerName ${LOCALHOST}" "${APACHE_CONFIG}" || echo "ServerName ${LOCALHOST}" >> "${APACHE_CONFIG}"

echo -e "-- Allowing Apache override to all\n"
sed -i "s/AllowOverride None/AllowOverride All/g" ${APACHE_CONFIG}

echo -e "-- Updating vhost file\n"
cat > ${SITES_ENABLED}/000-default.conf <<EOF
<VirtualHost *:80>
ServerName ${VIRTUALHOST}
DocumentRoot ${DOCUMENT_ROOT}

<Directory ${DOCUMENT_ROOT}>
Options Indexes FollowSymlinks
AllowOverride All
Order allow,deny
Allow from all
Require all granted
</Directory>

ErrorLog ${APACHE_LOG_DIR}/${VIRTUALHOST}-error.log
CustomLog ${APACHE_LOG_DIR}/${VIRTUALHOST}-access.log combined
</VirtualHost>
EOF

echo -e "-- Creating the DocumentRoot directory structure\n"
mkdir -p ${DOCUMENT_ROOT}

# PHP ##########################################################################
echo -e "-- Fetching PHP 5.6 repository\n"
add-apt-repository -y ppa:ondrej/php5-5.6 > /dev/null 2>&1

echo -e "-- Updating packages list\n"
apt-get update -y -qq

echo -e "-- Installing PHP modules\n"
apt-get install -y python-software-properties > /dev/null 2>&1
apt-get install -y libapache2-mod-php5 > /dev/null 2>&1
apt-get install -y php5 > /dev/null 2>&1
apt-get install -y php5-cli > /dev/null 2>&1
apt-get install -y php5-mcrypt > /dev/null 2>&1
apt-get install -y php5-curl > /dev/null 2>&1

echo -e "-- Enabling PHP mcrypt module\n"
php5enmod mcrypt

echo -e "-- Turning PHP error reporting on\n"
sed -i "s/error_reporting = .*/error_reporting = E_ALL/" ${PHP_INI}
sed -i "s/display_errors = .*/display_errors = On/" ${PHP_INI}

# MYSQL ########################################################################
echo -e "-- Installing MySQL server\n"
debconf-set-selections <<< "mysql-server mysql-server/root_password password ${MYSQL_PASSWORD}"
debconf-set-selections <<< "mysql-server mysql-server/root_password_again password ${MYSQL_PASSWORD}"

echo -e "-- Installing MySQL packages\n"
apt-get install -y mysql-server > /dev/null 2>&1
apt-get install -y libapache2-mod-auth-mysql > /dev/null 2>&1
apt-get install -y php5-mysql > /dev/null 2>&1

echo -e "-- Setting up a dummy MySQL database\n"
mysql -u${MYSQL_USER} -p${MYSQL_PASSWORD} -h ${LOCALHOST} -e "CREATE DATABASE IF NOT EXISTS ${MYSQL_DATABASE}"

# PHPMYADMIN ###################################################################
echo -e "-- Installing phpMyAdmin GUI\n"
debconf-set-selections <<< "phpmyadmin phpmyadmin/dbconfig-install boolean true"
debconf-set-selections <<< "phpmyadmin phpmyadmin/app-password-confirm password ${MYSQL_PASSWORD}"
debconf-set-selections <<< "phpmyadmin phpmyadmin/mysql/admin-pass password ${MYSQL_PASSWORD}"
debconf-set-selections <<< "phpmyadmin phpmyadmin/mysql/app-pass password ${MYSQL_PASSWORD}"
debconf-set-selections <<< "phpmyadmin phpmyadmin/reconfigure-webserver multiselect apache2"

echo -e "-- Installing phpMyAdmin package\n"
apt-get install -y phpmyadmin > /dev/null 2>&1

echo -e "-- Setting up phpMyAdmin GUI login user\n"
sed -i "s/dbuser='phpmyadmin'/dbuser='${MYSQL_USER}'/g" ${PHPMYADMIN_CONFIG}

# SQLITE #######################################################################
echo -e "-- Installing SQLite and relative PHP module\n"
apt-get install -y php5-sqlite > /dev/null 2>&1
apt-get install -y sqlite > /dev/null 2>&1
apt-get install -y sqlite3 > /dev/null 2>&1
apt-get install -y libsqlite3-dev > /dev/null 2>&1

# COMPOSER #####################################################################
echo -e "-- Installing PHP cURL module\n"
apt-get install -y curl > /dev/null 2>&1

echo -e "-- Setting up Composer\n"
curl -sSk https://getcomposer.org/installer | php -- --disable-tls > /dev/null 2>&1
mv composer.phar /usr/local/bin/composer

# GIT ##########################################################################
echo -e "-- Installing Git\n"
apt-get install -y git > /dev/null 2>&1

# GITHUB #######################################################################
echo -e "-- Enabling SSH connection to GitHub\n"
mkdir -p ~/.ssh > /dev/null 2>&1
ssh-keyscan -H github.com >> ~/.ssh/known_hosts > /dev/null 2>&1

# REFRESH ######################################################################
echo -e "-- Restarting Apache web server\n"
service apache2 restart

# END ##########################################################################
echo -e "-- ---------------- --"
echo -e "-- END BOOTSTRAPING --"
echo -e "-- ---------------- --"

Create vagrant file


Do it when you're in ubuntu-trusty-lamp folder. Name the file as Vagrantfile.


# -*- mode: ruby -*-
# vi: set ft=ruby :

Vagrant.configure("2") do |config|
# Type of the box
config.vm.box = "ubuntu/trusty64"

# Used for SSH and GitHub connections
config.ssh.forward_agent = true

# Configs fo virtual machine
config.vm.define :lamp do |lamp_config|
# Terminal name
lamp_config.vm.hostname = "lamp"
# IP address to access from host machine
lamp_config.vm.network "private_network", ip: "192.168.50.10"
# Script to run while setting up the machine
lamp_config.vm.provision :shell, path: "bootstrap.sh"
end

# Configs for virtual machine entry in Oracle VM VirtualBox
config.vm.provider :virtualbox do |vb_config|
vb_config.name = "Vagrant - Ubuntu 14.04 LAMP"
end

# Shared folder between host and virtual machine with "faster" nfs option and writing permissions enabled
# NFS option speeds up composer processes
# Mouth options grants writing permissions to '/var/www/html' folder
# Mount option below will assign "501 dialout" owner:group permissions to shared folder
# so that you can do whatever you want with it within host and guest machines.
config.vm.synced_folder "public", "/var/www/html", create: true, nfs: true, mount_options: ["actimeo=2"]
end

Run vagrant box


If you ever change your "bootstrap.sh" file, you'll need to run vagrant up command instead. In this process, you'll be prompted to enter admin password which is your OS login password. If you want to bypass it you can look into nfs page.



==> lamp: ......
==> lamp: ......
==> lamp: ......
==> lamp: -- ------------------ --
==> lamp: -- BEGIN BOOTSTRAPING --
==> lamp: -- ------------------ --
==> lamp: -- Setting global variables
==> lamp: -- Updating packages list
==> lamp: -- Installing Apache web server
==> lamp: -- Adding ServerName to Apache config
==> lamp: -- Allowing Apache override to all
==> lamp: -- Updating vhost file
==> lamp: -- Creating the DocumentRoot directory structure
==> lamp: -- Fetching PHP 5.6 repository
==> lamp: -- Updating packages list
==> lamp: -- Installing PHP modules
==> lamp: -- Enabling PHP mcrypt module
==> lamp: -- Turning PHP error reporting on
==> lamp: -- Installing MySQL server
==> lamp: -- Installing MySQL packages
==> lamp: -- Setting up a dummy MySQL database
==> lamp: -- Installing phpMyAdmin GUI
==> lamp: -- Installing phpMyAdmin package
==> lamp: -- Setting up phpMyAdmin GUI login user
==> lamp: -- Installing SQLite and relative PHP module
==> lamp: -- Installing PHP cURL module
==> lamp: -- Setting up Composer
==> lamp: -- Installing Git
==> lamp: -- Enabling SSH connection to GitHub
==> lamp: -- Restarting Apache web server
==> lamp: * Restarting web server apache2
==> lamp: ...done.
==> lamp: -- ---------------- --
==> lamp: -- END BOOTSTRAPING --
==> lamp: -- ---------------- --

Access the box


$ vagrant ssh
vagrant@lamp:~$

Check installed services


vagrant@lamp:~$ uname -mrs
Linux 3.13.0-88-generic x86_64

vagrant@lamp:~$ apache2 -v
Server version: Apache/2.4.7 (Ubuntu)
Server built: May 4 2016 17:05:10

vagrant@lamp:~$ sqlite -version
2.8.17

vagrant@lamp:~$ php -v
PHP 5.6.23-1+deprecated+dontuse+deb.sury.org~trusty+1 (cli)
Copyright (c) 1997-2016 The PHP Group
Zend Engine v2.6.0, Copyright (c) 1998-2016 Zend Technologies
with Zend OPcache v7.0.6-dev, Copyright (c) 1999-2016, by Zend Technologies

vagrant@lamp:~$ composer --version
Composer version 1.1.3 2016-06-26 15:42:08

vagrant@lamp:~$ git --version
git version 1.9.1

mysql> SELECT VERSION();
+-------------------------+
| VERSION() |
+-------------------------+
| 5.5.49-0ubuntu0.14.04.1 |
+-------------------------+
1 row in set (0.00 sec)

Configure Git


Set your account information like below.


vagrant@lamp:~$ git config --global user.name "You"
vagrant@lamp:~$ git config --global user.email "hello@world.com"
vagrant@lamp:~$ git config --list
user.name=You
user.email=hello@world.com

Setup SSH and connect with GitHub


You haven't set your SSH key and activated in GitHub yet so you should get error below.


vagrant@lamp:~$ ssh -T git@github.com
Permission denied (publickey).

You need to authenticate yourself with GitHub from Git over SSH now. For that you follow the instructions given in Set up Git page. Don't enter any password for the question Enter passphrase (empty for no passphrase):. After successfully completing the authentication process, you should get message below.


vagrant@lamp:~$ ssh -T git@github.com
Hi You! You've successfully authenticated, but GitHub does not provide shell access.

Cloning GitHub project


Our provisioning has already created /var/www/html/travis/web to prevent apache virtual host document root error message while booting the vagrant machine but you should now delete travis folder with vagrant@lamp:~$ sudo rm -Rf /var/www/html/travis command before cloning it.


vagrant@lamp:/var/www/html$ git clone git@github.com:You/travis.git
Cloning into 'travis'...
remote: Counting objects: 603, done.
remote: Total 603 (delta 0), reused 0 (delta 0), pack-reused 603
Receiving objects: 100% (603/603), 126.36 KiB | 23.00 KiB/s, done.
Resolving deltas: 100% (316/316), done.
Checking connectivity... done.

Install application


vagrant@lamp:/var/www/html$ cd travis/
vagrant@lamp:/var/www/html/travis$ composer install
Loading composer repositories with package information
Installing dependencies (including require-dev) from lock file
- Installing doctrine/lexer (v1.0.1)
Loading from cache
......
......
......

Run build tests


vagrant@lamp:/var/www/html/travis$ bin/phing
Buildfile: /var/www/html/travis/build.xml

travis > cache.clear:
[echo] Clearing application cache and logs ...
travis > cache.warm:
[echo] Warming up cache ...
travis > composer.update:
[echo] Running composer self-update ...
travis > composer.install:
[echo] Running composer install ...
travis > database.create:
[echo] Creating database ...
travis > doctrine.update.entities:
[echo] Updating doctrine entities ...
travis > doctrine.data.fixtures:
[echo] Loading doctrine data fixtures ...
travis > test.phpcsfixer:
[echo] Checking coding standards ...
travis > test.phpspec:
[echo] Running phpspec tests ...
travis > test.behat:
[echo] Running behat tests ...

BUILD FINISHED

Total time: 24.6246 seconds

Access application from host browser


Just go to http://192.168.50.10/ or http://192.168.50.10/app_dev.php or http://192.168.50.10/app_test.php for different environments. For the "test" and "dev" environments, you need to comment out lines show below in "app_test.php" and "app_dev.php" files.


header('HTTP/1.0 403 Forbidden');
exit('You are not allowed to access this file. Check '.basename(__FILE__).' for more information.');

Note


If the application is slow in browser, you might consider moving "cache" and "logs" folders outside of shared folder (keeping them in just the guest machine instead) and update "AppKernel.php" file accordingly. There are many information about how it is done on the web.