| 12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182 |
- <?php
- namespace App\Console\Commands;
- use Illuminate\Console\Command;
- use Illuminate\Support\Facades\Storage;
- use Symfony\Component\Process\Process;
- class DbExport extends Command
- {
- protected $signature = 'db:export
- {--path= : Путь для сохранения файла (по умолчанию storage/app/db-backups)}
- {--no-gzip : Не сжимать дамп gzip}
- {--connection=mysql : Имя соединения из config/database.php}';
- protected $description = 'Полный SQL-дамп базы данных через mysqldump';
- public function handle(): int
- {
- $connection = $this->option('connection');
- $config = config("database.connections.{$connection}");
- if (!$config || !in_array($config['driver'] ?? null, ['mysql', 'mariadb'], true)) {
- $this->error("Соединение {$connection} не найдено или не MySQL/MariaDB.");
- return self::FAILURE;
- }
- $database = $config['database'];
- $host = $config['host'] ?? '127.0.0.1';
- $port = (string) ($config['port'] ?? '3306');
- $user = $config['username'] ?? 'root';
- $password = (string) ($config['password'] ?? '');
- $gzip = !$this->option('no-gzip');
- $timestamp = date('Y-m-d_His');
- $filename = "{$database}_{$timestamp}.sql" . ($gzip ? '.gz' : '');
- $dir = $this->option('path') ?: storage_path('app/db-backups');
- if (!is_dir($dir) && !mkdir($dir, 0775, true) && !is_dir($dir)) {
- $this->error("Не удалось создать каталог: {$dir}");
- return self::FAILURE;
- }
- $filepath = rtrim($dir, '/') . '/' . $filename;
- $cmd = sprintf(
- 'mysqldump --host=%s --port=%s --user=%s %s --single-transaction --quick --routines --triggers --events --hex-blob --default-character-set=utf8mb4 %s',
- escapeshellarg($host),
- escapeshellarg($port),
- escapeshellarg($user),
- $password !== '' ? '--password=' . escapeshellarg($password) : '',
- escapeshellarg($database),
- );
- if ($gzip) {
- $cmd .= ' | gzip';
- }
- $cmd .= ' > ' . escapeshellarg($filepath);
- $this->info("Создаю дамп БД {$database} → {$filepath}");
- $process = Process::fromShellCommandline($cmd);
- $process->setTimeout(null);
- $process->run(function ($type, $buffer) {
- if ($type === Process::ERR) {
- $this->getOutput()->write($buffer);
- }
- });
- if (!$process->isSuccessful()) {
- @unlink($filepath);
- $this->error('Ошибка mysqldump: ' . $process->getErrorOutput());
- return self::FAILURE;
- }
- $size = is_file($filepath) ? filesize($filepath) : 0;
- $this->info(sprintf('Готово. Размер: %.2f MB', $size / 1024 / 1024));
- $this->line($filepath);
- return self::SUCCESS;
- }
- }
|