Affiliate Disclosure: By buying the products we recommend, you help keep the lights on at MakeUseOf. Read more.
Windows and Mac OSX have been making progress as developer-friendly OSes for the past few years, but every web developer really needs to work in the native environment of the web, Linux.
This article will show you how to get the best of both worlds: sticking with a stable and consumer-friendly OS like Windows or OSX for your everyday needs, while reaping the benefits of developing in the same ecosystem as your production code.
Much of the web runs on what developers call a “LAMP stack.” This acronym means Linux, Apache, MySQL, PHP bundled together and working as what you typically understand as a web server. (A closely related stack — or set of technologies — is “LEMP,” with the “E” derived from the pronunciation of an alternative to Apache, Nginx, which is said “engine x.”)
You may notice that Linux is explicitly included here, but it’s not only for this reason that Linux is recommended by developers. The other technologies — Apache (or Nginx), MySQL, and PHP — all have different tools and implementations available for the different platforms, but for historical and technical reasons, Linux-based configurations dominate the server space and tend to be more predictable.
Predictability and reliability are also big reasons you’d want to develop on an operating system that you use solely for that purpose — a dedicated operating system rather than one that supports the myriad of tasks you undertake on a daily basis as a web developer. Put another way, you don’t want to run a server on the same operating system you’ll need to reboot when your new graphics drivers are installed, or a machine that you will need to pack up and put in a backpack to hit the road with. Involving the processes and software needed to run a server on your mixed-use machine is, in a word, messy.
So how do you balance your ability to multi-task with your need to develop in the native context of your apps?
Enter virtual machines.
Virtual Machines and Vagrant
Virtual machines are programs that run in your primary operating system. They effectively allow you to run a completely separate operating system inside a window, totally contained and apart from whatever else is going on with your physical machine, but at the cost of some overhead.
However, the advantages are many:
- Make a mistake in installing, configuring, or removing software? No big deal, you can simply start again with a fresh image.
- Has your experiment catastrophically failed and frozen the operating system around it? Again, not a problem because only the virtual machine is effected.
- Do you need to iterate in slightly different conditions? Each set of conditions, like different software versions or different software (for example, using Apache versus Nginx), can become a separate software machine or virtual “box.”
A tool called Vagrant will help you deploy “base boxes” that contain preconfigured Linux operating systems in a variety of flavors.
This article assumes you have some comfort with operating a virtual machine without a GUI, and solely by a command-line interface (CLI).
Let’s get a virtual machine provider and Vagrant before we configure a base box.
- Ensure you have a virtual machine provider for your OS. Both Windows and Mac OSX can use Virtual Box. VMware also runs on both platforms. (Windows 10 Pro and up can use Hyper V, which is a step up because it better utilizes hardware.)
- Visit Vagrantup.com and choose an appropriate installer.
- In your local directory tree structure, make a new folder to house the box. (Locations subordinate to your user profile work well, locations within system directories generally don’t.)
The Web Development Environment Configuration
PuPHPet makes base configuration files for Vagrant. The wizard includes over twenty different dimensions to configure, so I’ll only go over some of the most salient.
- Deployment Target — Here you can choose whether you’d like to create an image suitable for VirtualBox, VMWare, and the like, or one that’s suitable for cloud computing infrastructure like AWS or Digital Ocean, among others.
- System > Packages — You can include any software here that you’d install as you would on a normal installation. In particular, you should include whichever packages you use for development that are included in the base of the OS distribution.
- To include development dependencies for Ubuntu, specify
- To include the same for CentOS 7, specify
- To include development dependencies for Ubuntu, specify
- Web Servers — Choose Apache or Nginx to form the backbone of your L(A|E)MP stack.
- Languages — PHP, Ruby, Node.js, Python.
- Databases — Perhaps one of the most attractive features of this approach is the ability to construct virtual machines to play with the different varieties of databases available. While MySQL is a default, you may wish to play with something newer like MariaDB.
- The remainder of the options are somewhat exotic, and if you don’t know what they are, they can always be installed later. What you have, after all, is a fully-fledged operating system at your command.
PuPHPet will, at the end of this configuration journey, produce an archive. Unzip that to the directory you created before configuring the parameters of your new server.
Now, execute the following:
$ vagrant up
And observe the results:
Since you don’t have the base box in your local directory, vagrant will retrieve the image from the Atlas, a repository of pre-configured vagrant boxes.
(Technically, any of these can be added to your local machine by issuing the command:
$ vagrant box add USER/BOX)
At this point, your VM is booted and you’re basically online. Only one thing remains: issue the command
$ vagrant ssh to drop yourself into a proper SSH session with your (headless) VM acting as a LAMP server. Congrats!
From here, there’s more to say about and do in Vagrant and, as you know, an unlimited amount to accomplish with your own development playground. Check out the official Getting Started Guide to pick up where I left off.
Have you ever used a VM for your own development environment? Did you use this setup or did you take a different approach? Share your ideas in the comments section below!