A lot of developers use Homestead when working on Laravel-based projects. But the default approach seems to be to install Homestead globally and use it as a replacement for something like MAMP, and serve all of your Laravel projects through a single instance. This approach has some drawbacks, which can be mitigated by using Homestead on a per-project basis instead.
What is Homestead?
Homestead is a pre-built virtual machine image, tailored for Laravel projects. When launched via VirtualBox, it acts a computer within your computer, meaning any software installed to isn’t installed on your actual computer. These virtual machines can then be booted, shut down, and also quickly created and destroyed.
Homestead is an Ubuntu-based virtual machine and comes with all the software pre-installed you’d need to run 99% of Laravel applications: nginx, PHP, MySQL, PostgreSQL, Node.js and much, much more.
Why install on a per-project basis?
Homestead is configured using a YAML file. This YAML file tells Homestead where to find sites’ files on your computer, databases to create, and so on. When you start a new project, you have to add an entry to this file and re-provision.
When using Homestead on a per-project basis, you keep this file with your project and it contains only that project’s settings. That means you can quickly clone a project if it’s under source control (and it should be), and quickly boot a Homestead instance for that project. This is especially helpful when setting an existing project up on a new computer, as you don’t need to manually set up Homestead and configure it for your project.
Getting started
If you have a new or existing Laravel project, adding Homestead to it is the same. Homestead is installed as a Composer dependency, so run the following command:
$ composer require laravel/homestead --dev
Once installed, you need to initialise some files Homestead will require:
$ php vendor/bin/homestead make
This will create an Homestead.yaml file, where you configure your Homestead instance.
There are a handful of options you can specify with the make
command:
--name
to name the virtual machine--hostname
to set the hostname for the virtual machine--ip
to set the IP address to reference the virtual machine--after
to generate a Shell script that’s ran during provisioning--aliases
to add some helpful aliases--example
to create a “blueprint” Homestead.yaml.exmaple file
I’d suggest always including the --example
option, so that people cloning your project can quickly copy that file, similar to how Laravel includes a .env.example file.
It’s always good to specify as many of the other options as you can, too.
I always set --name
to a “slugged” version of my project’s name.
I also always add the --after
and --aliases
options.
The after.sh file is a great place to install Composer dependencies, migrate, and run any seeds:
#!/bin/sh
cd src
composer install --no-progress
php artisan migrate --seed
# Do any other provisioning unique to your application
The --ip
options lets you set an IP address for the machine, so that you can add custom host names.
It’ll be set to 192.168.10.10
by default.
After you have filled out your application’s settings in your Homestead.yaml file, you can boot Homestead. This is the same command as if you had it installed globally:
$ vagrant up
Like a globally-installed Homestead instance it will read your Homestead.yaml file, configure the machine, and provision it. Once provisioned, you can access it via SSH:
$ vagrant ssh
Working with Homestead on other machines
Once you’ve committed the newly-created files to your source control repository, you can use it on other machines. However, it does come with the caveat that the new machine must have Composer installed.
After cloning your project, copy Homestead.yaml.example to Homestead.yaml, and amend any settings for your new environment.
The only setting that should really need to be changed is in the sites
block, and specifying the path to the project on your machine.
There is also the caveat that you must have Composer installed on this machine.
As Homestead is a Composer dependency, you need to have Homestead installed before you can use it.
If you tried to run vagrant up
you would get the following error message:
There was an error loading a Vagrantfile. The file being loaded
and the error message are shown below. This is usually caused by
a syntax error.
Path: /path/to/project/root/Vagrantfile
Line number: 12
Message: LoadError: cannot load such file -- /path/to/project/root/vendor/laravel/homestead/scripts/homestead.rb
To remedy this, install Composer on your machine and then install your dependencies:
$ composer install
With the Homestead package installed, you can now run vagrant up
.
Conclusion
It would be nice if Homestead could be used on a per project basis like this without having to install Composer and dependencies first.
The ideal approach would be to clone a project and be able to run vagrant up
immediately.
However, bundling your Homestead configuration with the project it’s serving makes life a little easier.
Although I’m currently investigating Docker in my day job, I’ll still be using Homestead in this fashion for other projects for the immediate future. Each project has different requirements, and there is no “one size fits all” when it comes to serving them. For me, Homestead nicely fills the gap between “quick and easy” (something like MAMP or Valet, another Laravel offering) and Docker.