Simple Laravel Restore

Written by Rich Banks on 23rd Dec, 2015

Laravel

If you have been following my other articles on backing up your mysql database in Laravel 5 and keeping your backups directory tidy, you may also want to be able to restore the backups directly from Laravel.

This article will run through a very simple backup restore using the Laravel artisan console.

Firstly, create a new console command file named BackupRestore.php in app/Console/Commands.

php artisan make:console BackupRestore

Open the newly created file and change the signature as below:

protected $signature = 'backup:restore';

Update the console command description.

protected $description = 'Restore Database backup';

We will be using Storage in the class so define it at the top of your document.

Use Storage;

In the handle method we can add our restore code.

public function handle()
{
    //get all files in s3 storage backups directory
    $files = Storage::disk('s3')->files('backups');

    $i = 0;
    foreach($files as $file){

        $filename[$i]['file'] = $file;
        $i++;

    }

    $headers = ['File Name'];
    //output table of file to console
    $this->table($headers, $filename);
    //ask console user for input
    $backupFilename = $this->ask('Which file would you like to restore?');

    $getBackupFile  = Storage::disk('s3')->get($backupFilename);

    $backupFilename  = explode("/", $backupFilename);

    Storage::disk('local')->put($backupFilename[1], $getBackupFile);
    //get file mime
    $mime = Storage::mimeType($backupFilename[1]);

    if($mime == "application/x-gzip"){

        //mysql command to restore backup from the selected gzip file
        $command = "zcat " . storage_path() . "/" . $backupFilename[1] . " | mysql --user=" . env('DB_USERNAME') ." --password=" . env('DB_PASSWORD') . " --host=" . env('DB_HOST') . " " . env('DB_DATABASE') . "";

    }elseif($mime == "text/plain"){

        //mysql command to restore backup from the selected sql file
        $command = "mysql --user=" . env('DB_USERNAME') ." --password=" . env('DB_PASSWORD') . " --host=" . env('DB_HOST') . " " . env('DB_DATABASE') . " < " . storage_path() . "/" . $backupFilename[1] . "";

    }else{

        //throw error if file type is not supported
        $this->error("File is not gzip or plain text");
        Storage::disk('local')->delete($backupFilename[1]);
        return false;

    }

    if ($this->confirm("Are you sure you want to restore the database? [y|N]")) {

        $returnVar  = NULL;
        $output     = NULL;
        exec($command, $output, $returnVar);

        Storage::disk('local')->delete($backupFilename[1]);

        if(!$returnVar){

            $this->info('Database Restored');

        }else{

            $this->error($returnVar);   

        }

    }
}

Open app/Console/Kernel.php and add your class to the protected commands

protected $commands = [
    \App\Console\Commands\Inspire::class,
    \App\Console\Commands\BackupDatabase::class,
    \App\Console\Commands\BackupTidy::class,
    \App\Console\Commands\BackupRestore::class,
];

If you are ever unfortunate enough to have to restore your database, now all you have to do is run the below command and follow the prompts.

php artisan backup:restore

screenshot.png

Files for this article can be found on GitHub