Simplify Your Laravel Project Installation with One Custom Command
Overview
This article will demonstrate how to create a command to install your Laravel project. The command will ensure that the application is consistent across all team members by executing all the necessary steps to get the application up and running.
Introduction
When working with a Laravel project, you don't want to complicate your life by requiring your team members to run different commands to get your application working. Instead, creating one command that executes everything needed ensures that everything is consistent within everyone's application.
Creating the Command
To create the command, start by running the following command:
1art make:command System/InstallCommand
This will create the command under app/Console/Commands/System
. You can create additional directories inside the Commands
directory to keep your application more organized. For example, you could lump all system:*
commands under the System/
directory.
Here is the code for the InstallCommand
:
1<?php 2 3declare(strict_types=1); 4 5namespace App\Console\Commands\System; 6 7use App; 8use Illuminate\Console\Command; 9 10class InstallCommand extends Command11{12 /**13 * The name and signature of the console command.14 *15 * @var string16 */17 protected $signature = 'system:install';18 19 /**20 * The console command description.21 *22 * @var string23 */24 protected $description = 'Install the application on a non-production environment.';25 26 /**27 * Create a new command instance.28 *29 * @return void30 */31 public function __construct()32 {33 parent::__construct();34 }35 36 /**37 * Execute the console command.38 *39 * @return int40 */41 public function handle(): int42 {43 // Check that the application you are installing has the proper .env configuration44 if (config('app.name') !== 'myappname') {45 $this->error('Application name is not myappname.');46 47 return Command::FAILURE;48 }49 50 // Check if this command is being run in production51 if ($this->isRunningInProduction()) {52 $this->error('Cannot run this command in production.');53 54 return Command::FAILURE;55 }56 57 // Create symbolic links58 $this->info('Create Symbolic links.');59 $this->call('storage:link', ['--force' => true]);60 61 // Clear cached bootstrap files62 $this->clearCommands();63 64 // Migrate and seed a fresh database to work with65 $this->info('Migrate and seed a fresh database to work with.');66 $this->call('migrate:fresh', ['--seed' => true]);67 68 // Display success message69 $this->line('[Installation is now complete]', 'info');70 71 return Command::SUCCESS;72 }73 74 /**75 * Check if this command is being run in production76 *77 * @return bool78 */79 protected function isRunningInProduction(): bool80 {81 return App::isProduction() === true;82 }83 84 /**85 * Clear cached bootstrap files86 */87 protected function clearCommands(): void88 {89 $this->info('Clearing cached bootstrap files.');90 91 // Clear cached bootstrap files such as optimize and queue92 collect([93 'optimize' => fn () => $this->callSilent('optimize:clear') == 0,94 'queue' => fn () => $this->callSilent('queue:clear') == 0,95 ])->each(fn ($task, $description) => $this->components->task($description, $task));96 97 $this->newLine();98 }99}
Explanation
When you run the system:install
command, several things happen:
- The command checks to make sure that the application you are installing has the proper .env configuration. This code checks that
config('app.name')
matchesmyappname
. This initial check ensures that your environment variables match.
1if (config('app.name') !== 'myappname') {2 $this->error('Application name is not myappname.');34 return Command::FAILURE;5}
- The command checks whether it is being run in production, to avoid accidentally installing your application on a live server. This method should have more complex logic, check to make sure that specific critical configuration variables hold non-production values in a way to not divulge any sensitive information.
1if ($this->isRunningInProduction()) {2 $this->error('Cannot run this command in production.');34 return Command::FAILURE;5}
- The command creates the storage links configured:
1$this->call('storage:link', ['--force' => true]);
- Your custom command runs
optimize:clear
, which as of Laravel 10 clearsevents
,views
,cache
,route
,config
, andcompiled
by default. In the code we added an additional item during an app install such asqueue:clear
, you can check your packages to add additional clear commands.
1$this->clearCommands();
- The command runs
migrate:fresh
with the seed, to drop and create the tables from a fresh state. This allows you to work between separate branches without any issues that are introduced with rollbacks.
1$this->call('migrate:fresh', ['--seed' => true]);
- The command displays a message and sends the success signal to instruct the machine running this command that everything installed correctly and fire off any additional commands as needed.
1$this->line('[Installation is now complete]', 'info');
By following these steps and creating a consistent installation process, you can save yourself and your team members time and unnecessary hassle when working on your Laravel project.