Compare commits

..

8 Commits

Author SHA1 Message Date
Muhep Atasoy ea566de865 Create .env.example
continuous-integration/drone/push Build is passing Details
2020-02-04 23:34:56 +03:00
Muhep Atasoy ed02258674 Update .drone.yml
continuous-integration/drone/push Build is passing Details
2020-02-04 23:30:44 +03:00
Muhep Atasoy c38a444db6 Update .drone.yml
continuous-integration/drone/push Build was killed Details
2020-02-04 23:29:58 +03:00
Muhep Atasoy a2f1302a67 Create LICENSE
continuous-integration/drone/push Build is passing Details
2020-02-04 23:25:30 +03:00
Muhep Atasoy 2b7ab97ce8 Update README.md 2020-02-04 23:25:29 +03:00
Muhep Atasoy 5bedb3f9fa Improved & Bug Fix
continuous-integration/drone/tag Build is passing Details
continuous-integration/drone/push Build is passing Details
- Code improved.
- Bugs fixed.
- Stability is improved.
2019-12-19 23:11:32 +03:00
Muhep Atasoy e9e5d61330 (Fix) Test
continuous-integration/drone/push Build is passing Details
continuous-integration/drone/tag Build is passing Details
2019-12-17 20:42:00 +03:00
Muhep Atasoy 2467ac62e2 New Feature
continuous-integration/drone/push Build is failing Details
.env file or argument in command can be used both same time.
2019-12-17 20:38:09 +03:00
15 changed files with 373 additions and 112 deletions

7
.env.example Normal file
View File

@ -0,0 +1,7 @@
BACKUP_FOLDER=/root/backup
EXPORT_FOLDER=/root/export
TARGET_FOLDER=/backup
DATA_FOLDER=/root/git/home
MYSQL_CONTAINER_NAME=mysql
MYSQL_USER=root
MYSQL_PASSWORD=secret

21
LICENSE Normal file
View File

@ -0,0 +1,21 @@
MIT License
Copyright (c) 2019 Muhep Atasoy
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.

View File

@ -1,37 +1,9 @@
<p align="center"> # Backupper
<img title="Laravel Zero" height="100" src="https://raw.githubusercontent.com/laravel-zero/docs/master/images/logo/laravel-zero-readme.png" /> Backup manager for backing up Docker Containers to Mega.nz.
</p>
<p align="center">
<a href="https://travis-ci.org/laravel-zero/framework"><img src="https://img.shields.io/travis/laravel-zero/framework/stable.svg" alt="Build Status"></img></a>
<a href="https://scrutinizer-ci.com/g/laravel-zero/framework"><img src="https://img.shields.io/scrutinizer/g/laravel-zero/framework.svg" alt="Quality Score"></img></a>
<a href="https://packagist.org/packages/laravel-zero/framework"><img src="https://poser.pugx.org/laravel-zero/framework/d/total.svg" alt="Total Downloads"></a>
<a href="https://packagist.org/packages/laravel-zero/framework"><img src="https://poser.pugx.org/laravel-zero/framework/v/stable.svg" alt="Latest Stable Version"></a>
<a href="https://packagist.org/packages/laravel-zero/framework"><img src="https://poser.pugx.org/laravel-zero/framework/license.svg" alt="License"></a>
</p>
<h4> <center>This is a <bold>community project</bold> and not an official Laravel one </center></h4>
Laravel Zero was created by, and is maintained by [Nuno Maduro](https://github.com/nunomaduro), and is a micro-framework that provides an elegant starting point for your console application. It is an **unofficial** and customized version of Laravel optimized for building command-line applications.
- Built on top of the [Laravel](https://laravel.com) components.
- Optional installation of Laravel [Eloquent](https://laravel-zero.com/docs/database/), Laravel [Logging](https://laravel-zero.com/docs/logging/) and many others.
- Supports interactive [menus](https://laravel-zero.com/docs/build-interactive-menus/) and [desktop notifications](https://laravel-zero.com/docs/send-desktop-notifications/) on Linux, Windows & MacOS.
- Ships with a [Scheduler](https://laravel-zero.com/docs/task-scheduling/) and a [Standalone Compiler](https://laravel-zero.com/docs/build-a-standalone-application/).
- Integration with [Collision](https://github.com/nunomaduro/collision) - Beautiful error reporting
------
## Documentation ## Documentation
For full documentation, visit [laravel-zero.com](https://laravel-zero.com/). For full documentation, visit [Wiki](https://github.com/muhep06/dgd-backupper-php/wiki).
## Support the development
**Do you like this project? Support it by donating**
- PayPal: [Donate](https://www.paypal.com/cgi-bin/webscr?cmd=_s-xclick&hosted_button_id=66BYDWAT92N6L)
- Patreon: [Donate](https://www.patreon.com/nunomaduro)
## License ## License
Backupper is an open-source software licensed under the [MIT license](https://github.com/muhep06/dgd-backupper-php/blob/master/LICENSE).
Laravel Zero is an open-source software licensed under the [MIT license](https://github.com/laravel-zero/laravel-zero/blob/stable/LICENSE.md).

View File

@ -5,21 +5,21 @@ namespace App\Commands;
use Illuminate\Console\Scheduling\Schedule; use Illuminate\Console\Scheduling\Schedule;
use LaravelZero\Framework\Commands\Command; use LaravelZero\Framework\Commands\Command;
class InspiringCommand extends Command class AboutCommand extends Command
{ {
/** /**
* The signature of the command. * The signature of the command.
* *
* @var string * @var string
*/ */
protected $signature = 'inspiring {name=Artisan}'; protected $signature = 'about';
/** /**
* The description of the command. * The description of the command.
* *
* @var string * @var string
*/ */
protected $description = 'Display an inspiring quote'; protected $description = 'Display about message';
/** /**
* Execute the console command. * Execute the console command.
@ -28,7 +28,12 @@ class InspiringCommand extends Command
*/ */
public function handle() public function handle()
{ {
$this->info('Simplicity is the ultimate sophistication.'); $this->line("<fg=green>Backup manager for backing up Docker Containers to Mega.nz.</>");
$this->line("<fg=blue>Developer: </><fg=red>Muhep Atasoy</>");
$this->line("<fg=magenta>Github: </>https://github.com/muhep06");
$this->line("<fg=red>Gitea: </>https://git.muhepatasoy.xyz/muhep");
$this->line("<fg=yellow>Drone: </>https://drone.muhepatasoy.xyz/muhep/dgd-backupper-php");
return;
} }
/** /**
@ -37,7 +42,7 @@ class InspiringCommand extends Command
* @param \Illuminate\Console\Scheduling\Schedule $schedule * @param \Illuminate\Console\Scheduling\Schedule $schedule
* @return void * @return void
*/ */
public function schedule(Schedule $schedule) public function schedule(Schedule $schedule): void
{ {
// $schedule->command(static::class)->everyMinute(); // $schedule->command(static::class)->everyMinute();
} }

View File

@ -2,10 +2,7 @@
namespace App\Commands; namespace App\Commands;
use App\Utils\BackupManager;
use App\Utils\Builders\ContainerBuilder;
use Illuminate\Console\Scheduling\Schedule; use Illuminate\Console\Scheduling\Schedule;
use Illuminate\Support\Facades\Artisan;
use LaravelZero\Framework\Commands\Command; use LaravelZero\Framework\Commands\Command;
class BackupCommand extends Command class BackupCommand extends Command
@ -15,7 +12,7 @@ class BackupCommand extends Command
* *
* @var string * @var string
*/ */
protected $signature = 'backup {containers*} {--data} {--mysql} {--upload} {--clean}'; protected $signature = 'backup {containers*} {--data} {--mysql} {--pack} {--upload} {--clean}';
/** /**
* The description of the command. * The description of the command.
@ -41,18 +38,40 @@ class BackupCommand extends Command
} }
if ($this->option('mysql')) { if ($this->option('mysql')) {
$this->call("backup:mysql", [ $this->call("backup:mysql");
'--container' => env('MYSQL_CONTAINER_NAME'), }
'--user' => env('MYSQL_USER'),
'--password' => env('MYSQL_PASSWORD'), date_default_timezone_set('Europe/Istanbul');
$date = date('d-m-Y_H-i-s', time());
if ($this->option('pack')) {
$this->call('backup:pack', [
'name' => 'backup_' . $date,
]);
}
if ($this->option('upload')) {
if (!$this->option('pack')) {
$this->call('backup:pack', [
'name' => 'backup_' . $date,
]);
}
$this->call("backup:upload", [
'name' => 'backup_' . $date . '.tar.gz',
]); ]);
} }
if ($this->option('clean')) { if ($this->option('clean')) {
$this->line("<fg=yellow>|-> Cleaning...</>");
$files = glob(env('BACKUP_FOLDER') . '/*'); $files = glob(env('BACKUP_FOLDER') . '/*');
foreach($files as $file){ foreach($files as $file){
is_file($file) ? unlink($file) : null; is_file($file) ? unlink($file) : null;
} }
$files = glob(env('EXPORT_FOLDER') . '/*');
foreach($files as $file){
is_file($file) ? unlink($file) : null;
}
} }
$this->line("<fg=blue>|-> The backup and upload process is finished.</>"); $this->line("<fg=blue>|-> The backup and upload process is finished.</>");

View File

@ -15,7 +15,9 @@ class ContainerBackupCommand extends Command
* *
* @var string * @var string
*/ */
protected $signature = 'backup:container {containers*}'; protected $signature = 'backup:container
{containers* : Name or ID of the containers to be backed up.}
{--folder= : Export folder for backed up containers.}';
/** /**
* The description of the command. * The description of the command.
@ -33,12 +35,17 @@ class ContainerBackupCommand extends Command
public function handle() public function handle()
{ {
$containers = $this->argument('containers'); $containers = $this->argument('containers');
$backupFolder = $this->option('folder');
if (!$backupFolder) {
$backupFolder = env('BACKUP_FOLDER');
}
$backupManager = new BackupManager(); $backupManager = new BackupManager();
$backupManager->setBackupFolder(env('BACKUP_FOLDER'));
foreach ($containers as $container) { foreach ($containers as $container) {
$this->line("<fg=blue>|-> Backing up {$container}...</>"); $this->line("<fg=blue>|-> Backing up {$container}...</>");
$builder = new ContainerBuilder(); $builder = new ContainerBuilder();
$builder->setContainerName($container); $builder->setContainerName($container)
->setBackupFolder($backupFolder);
$backupManager->setBuilder($builder)->execute(); $backupManager->setBuilder($builder)->execute();
if ($backupManager->getShell()->getReturnValue() == 0) { if ($backupManager->getShell()->getReturnValue() == 0) {
$this->line("<fg=green> |-> {$container} successfully backed up.</>"); $this->line("<fg=green> |-> {$container} successfully backed up.</>");

View File

@ -15,7 +15,9 @@ class DataBackupCommand extends Command
* *
* @var string * @var string
*/ */
protected $signature = 'backup:data'; protected $signature = 'backup:data
{--data= : You can use it to back up the data folder of all containers or any folder. }
{--folder= : Export folder for backed up folder. }';
/** /**
* The description of the command. * The description of the command.
@ -34,11 +36,21 @@ class DataBackupCommand extends Command
{ {
$this->line("<fg=blue>|-> Backing up data folder...</>"); $this->line("<fg=blue>|-> Backing up data folder...</>");
$bm = new BackupManager(); $backupFolder = $this->option('folder');
$dataFolder = $this->option('data');
if (!$backupFolder) {
$backupFolder = env('BACKUP_FOLDER');
}
if (!$dataFolder) {
$dataFolder = env('DATA_FOLDER');
}
$builder = new DataBuilder(); $builder = new DataBuilder();
$builder->setDataFolder(env('DATA_FOLDER')); $builder->setDataFolder($dataFolder)
$bm->setBackupFolder(env('BACKUP_FOLDER')) ->setBackupFolder($backupFolder);
->setBuilder($builder)->execute(); $bm = new BackupManager();
$bm->setBuilder($builder)->execute();
if ($bm->getShell()->getReturnValue() == 0) { if ($bm->getShell()->getReturnValue() == 0) {
$this->line("<fg=green> |-> Data folder successfully backed up.</>"); $this->line("<fg=green> |-> Data folder successfully backed up.</>");

View File

@ -15,7 +15,11 @@ class MysqlBackupCommand extends Command
* *
* @var string * @var string
*/ */
protected $signature = 'backup:mysql {--container=} {--user=} {--password=}'; protected $signature = 'backup:mysql
{--container= : Mysql container name or id}
{--user= : Mysql username}
{--password= : Mysql password}
{--folder= : Export folder for backup}';
/** /**
* The description of the command. * The description of the command.
@ -35,6 +39,19 @@ class MysqlBackupCommand extends Command
$container = $this->option('container'); $container = $this->option('container');
$user = $this->option('user'); $user = $this->option('user');
$password = $this->option('password'); $password = $this->option('password');
if (!$container) {
$container = env('MYSQL_CONTAINER_NAME');
}
if (!$user) {
$user = env('MYSQL_USER');
}
if (!$password) {
$password = env('MYSQL_PASSWORD');
}
$bm = new BackupManager(); $bm = new BackupManager();
$this->line("<fg=blue>|-> Backing up mysql databases...</>"); $this->line("<fg=blue>|-> Backing up mysql databases...</>");
@ -42,12 +59,17 @@ class MysqlBackupCommand extends Command
$credentials->setUsername($user); $credentials->setUsername($user);
$credentials->setPassword($password); $credentials->setPassword($password);
$backupFolder = $this->option('folder');
if (!$backupFolder) {
$backupFolder = env('BACKUP_FOLDER');
}
$builder = new DatabaseBuilder(); $builder = new DatabaseBuilder();
$builder->setCredential($credentials); $builder->setCredential($credentials);
$builder->setContainerName($container); $builder->setContainerName($container)
->setBackupFolder($backupFolder);
$bm->setBackupFolder(env('BACKUP_FOLDER')) $bm->setBuilder($builder)->execute();
->setBuilder($builder)->execute();
if ($bm->getShell()->getReturnValue() == 0) { if ($bm->getShell()->getReturnValue() == 0) {
$this->line("<fg=green> |-> Mysql databases successfully backed up.</>"); $this->line("<fg=green> |-> Mysql databases successfully backed up.</>");

View File

@ -0,0 +1,77 @@
<?php
namespace App\Commands;
use App\Utils\BackupManager;
use App\Utils\Builders\PackageBuilder;
use Illuminate\Console\Scheduling\Schedule;
use LaravelZero\Framework\Commands\Command;
class PackCommand extends Command
{
/**
* The signature of the command.
*
* @var string
*/
protected $signature = 'backup:pack
{name : Package name.}
{--folder= : Backup folder.}
{--export= : Export folder for created package.}';
/**
* The description of the command.
*
* @var string
*/
protected $description = 'Create backup package';
/**
* Execute the console command.
*
* @return mixed
* @throws \Throwable
*/
public function handle()
{
$backupFolder = $this->option('folder');
$exportFolder = $this->option('export');
$packageName = $this->argument('name');
if (!$backupFolder) {
$backupFolder = env('BACKUP_FOLDER');
}
if (!$exportFolder) {
$exportFolder = env('EXPORT_FOLDER');
}
$this->line("<fg=blue>|-> {$packageName} is packing...</>");
$packageBuilder = new PackageBuilder();
$packageBuilder->setBackupFolder($backupFolder)
->setExportFolder($exportFolder)
->setPackageName($packageName);
$backupManager = new BackupManager();
$backupManager->setBuilder($packageBuilder)->execute();
if ($backupManager->getShell()->getReturnValue() == 0) {
$this->line("<fg=green> |-> Package created.</>");
} else {
$this->line("<fg=red> |-> Failed to create package.</>");
}
return;
}
/**
* Define the command's schedule.
*
* @param \Illuminate\Console\Scheduling\Schedule $schedule
* @return void
*/
public function schedule(Schedule $schedule): void
{
// $schedule->command(static::class)->everyMinute();
}
}

View File

@ -0,0 +1,79 @@
<?php
namespace App\Commands;
use App\Utils\BackupManager;
use App\Utils\Builders\DataBuilder;
use App\Utils\Builders\UploadBuilder;
use Illuminate\Console\Scheduling\Schedule;
use LaravelZero\Framework\Commands\Command;
class UploadCommand extends Command
{
/**
* The signature of the command.
*
* @var string
*/
protected $signature = 'backup:upload
{name : Package name.}
{--export : Folder for created packages.}
{--target= : Target folder for Mega.nz}';
/**
* The description of the command.
*
* @var string
*/
protected $description = 'Upload backup file to Mega.nz';
/**
* Execute the console command.
*
* @return mixed
* @throws \Throwable
*/
public function handle()
{
$exportFolder = $this->option('export');
$targetFolder = $this->option('target');
$name = $this->argument('name');
if (!$targetFolder) {
$targetFolder = env('TARGET_FOLDER');
}
if (!$exportFolder) {
$exportFolder = env('EXPORT_FOLDER');
}
$this->line("<fg=blue>|-> {$name} is uploading...</>");
$uploadBuilder = new UploadBuilder();
$uploadBuilder->setExportFolder($exportFolder)
->setTargetFolder($targetFolder)
->setPackageName($name);
$backupManager = new BackupManager();
$backupManager->setBuilder($uploadBuilder)
->execute();
if ($backupManager->getShell()->getReturnValue() == 0) {
$this->line("<fg=green> |-> Upload successful.</>");
} else {
$this->line("<fg=red> |-> Upload failed.</>");
}
return;
}
/**
* Define the command's schedule.
*
* @param \Illuminate\Console\Scheduling\Schedule $schedule
* @return void
*/
public function schedule(Schedule $schedule): void
{
// $schedule->command(static::class)->everyMinute();
}
}

View File

@ -9,41 +9,13 @@ use Throwable;
class BackupManager class BackupManager
{ {
private $exportFolder;
private $backupFolder;
private $shell; private $shell;
private $builder; private $builder;
private $containerName;
public function __construct() public function __construct()
{ {
$this->shell = new Exec(); $this->shell = new Exec();
} }
/**
* @param mixed $backupFolder
* @return BackupManager
* @throws Throwable
*/
public function setBackupFolder($backupFolder): BackupManager
{
throw_if(!file_exists($backupFolder), new BackupFolderNotFoundException('Backup folder not exist!'));
$this->backupFolder = $backupFolder;
return $this;
}
/**
* @param mixed $exportFolder
* @return BackupManager
* @throws Throwable
*/
public function setExportFolder($exportFolder): BackupManager
{
throw_if(!file_exists($exportFolder), new ExportFolderNotFoundException('Export folder not exist!'));
$this->exportFolder = $exportFolder;
return $this;
}
/** /**
* @return Exec * @return Exec
*/ */
@ -52,30 +24,6 @@ class BackupManager
return $this->shell; return $this->shell;
} }
/**
* @return mixed
*/
public function getBackupFolder()
{
return $this->backupFolder;
}
/**
* @return mixed
*/
public function getExportFolder()
{
return $this->exportFolder;
}
/**
* @return mixed
*/
public function getContainerName()
{
return $this->containerName;
}
public function setBuilder(Builder $builder): BackupManager public function setBuilder(Builder $builder): BackupManager
{ {
$this->builder = $builder; $this->builder = $builder;
@ -93,7 +41,7 @@ class BackupManager
*/ */
public function execute() public function execute()
{ {
$builder = $this->getBuilder()->setBackupFolder($this->backupFolder)->builder(); $builder = $this->getBuilder()->builder();
return $this->shell->run($builder); return $this->shell->run($builder);
} }
} }

View File

@ -10,7 +10,10 @@ use Throwable;
abstract class Builder abstract class Builder
{ {
private $backupFolder; private $backupFolder;
private $exportFolder;
private $targetFolder;
private $containerName; private $containerName;
private $packageName;
private $clean; private $clean;
/** /**
@ -55,6 +58,24 @@ abstract class Builder
return $this->backupFolder; return $this->backupFolder;
} }
/**
* @param string $exportFolder
* @return Builder
*/
public function setExportFolder(string $exportFolder): Builder
{
$this->exportFolder = $exportFolder;
return $this;
}
/**
* @return string
*/
public function getExportFolder(): string
{
return $this->exportFolder;
}
/** /**
* @param $containerName * @param $containerName
* @return Builder * @return Builder
@ -65,6 +86,24 @@ abstract class Builder
return $this; return $this;
} }
/**
* @param string $targetFolder
* @return Builder
*/
public function setTargetFolder(string $targetFolder): Builder
{
$this->targetFolder = $targetFolder;
return $this;
}
/**
* @return string
*/
public function getTargetFolder(): string
{
return $this->targetFolder;
}
/** /**
* @return string * @return string
*/ */
@ -73,6 +112,24 @@ abstract class Builder
return $this->containerName; return $this->containerName;
} }
/**
* @param string $packageName
* @return Builder
*/
public function setPackageName(string $packageName): Builder
{
$this->packageName = $packageName;
return $this;
}
/**
* @return string
*/
public function getPackageName(): string
{
return $this->packageName;
}
/** /**
* @param bool $clean * @param bool $clean
*/ */

View File

@ -0,0 +1,17 @@
<?php
namespace App\Utils\Builders;
use AdamBrett\ShellWrapper\Command\Builder as CommandBuilder;
use App\Utils\Builder;
class PackageBuilder extends Builder
{
/**
* @return CommandBuilder
*/
public function builder(): CommandBuilder
{
return new CommandBuilder("tar -zcf {$this->getExportFolder()}/{$this->getPackageName()}.tar.gz {$this->getBackupFolder()}");
}
}

View File

@ -0,0 +1,18 @@
<?php
namespace App\Utils\Builders;
use AdamBrett\ShellWrapper\Command\Builder as CommandBuilder;
use App\Utils\Builder;
class UploadBuilder extends Builder
{
/**
* @return CommandBuilder
*/
public function builder(): CommandBuilder
{
return new CommandBuilder("mega-put {$this->getExportFolder()}". DIRECTORY_SEPARATOR .
"{$this->getPackageName()} {$this->getTargetFolder()}/{$this->getPackageName()}");
}
}

View File

@ -13,8 +13,8 @@ class InspiringCommandTest extends TestCase
*/ */
public function testInspiringCommand() public function testInspiringCommand()
{ {
$this->artisan('inspiring') $this->artisan('about')
->expectsOutput('Simplicity is the ultimate sophistication.') ->expectsOutput('Backup manager for backing up Docker Containers to Mega.nz.')
->assertExitCode(0); ->assertExitCode(0);
} }
} }