We can't find the internet
Attempting to reconnect
Something went wrong!
Hang in there while we get back on track
I often create custom commands to do things like data migrations.
Once scenario that pops up quite often is that I want to check that all database migrations are applied before doing the data migration.
To make this easier from within a console command, I started with creating a trait which can check this.
The basic idea is to run artisan migrate
with the --pretend
option and checking the output.
namespace App\Traits;
use Illuminate\Support\Facades\App;
use Illuminate\Support\Facades\Artisan;
use Illuminate\Support\Str;
trait ChecksPendingMigrations
{
public function hasPendingMigrations(): bool
{
if (App::environment('testing')) {
return false;
}
Artisan::call('migrate', ['--pretend' => true, '--force' => true]);
return Str::doesntContain(Artisan::output(), 'Nothing to migrate.');
}
}
Note that when running tests, I'm skipping the check as the migrations are already applied anyway.
Using it inside a custom command is then very easy and can by done by using the trait and calling the hasPendingMigrations
function:
namespace App\Console\Commands;
use App\Traits\ChecksPendingMigrations;
use Illuminate\Console\Command;
final class MySampleCommand extends Command
{
use ChecksPendingMigrations;
protected $signature = 'my-sample-command';
protected $description = 'Sample command which checks pending migrations';
public function handle(): int
{
if ($this->hasPendingMigrations()) {
$this->error('Run the pending database migrations first');
return self::FAILURE;
}
return self::SUCCESS;
}
}
A different approach can be to simply apply the migrations instead of checking them. If prefer no to do this as I want to be able to check what is happening.
If this post was enjoyable or useful for you, please share it! If you have comments, questions, or feedback, you can email my personal email. To get new posts, subscribe use the RSS feed.