feat: add database backup download via mysqldump (admin-only)

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
GuavaPopper
2026-06-04 14:26:04 +07:00
parent 2d4533683d
commit c4eb884495
4 changed files with 81 additions and 3 deletions
+29
View File
@@ -0,0 +1,29 @@
FROM php:8.3-cli-bookworm
WORKDIR /var/www/html
RUN apt-get update \
&& apt-get install -y --no-install-recommends \
ca-certificates \
curl \
default-mysql-client \
git \
libicu-dev \
libzip-dev \
unzip \
&& docker-php-ext-install \
intl \
pdo_mysql \
zip \
&& apt-get clean \
&& rm -rf /var/lib/apt/lists/*
COPY --from=composer:2 /usr/bin/composer /usr/bin/composer
COPY docker/app/php.ini /usr/local/etc/php/conf.d/99-webgis.ini
COPY docker/app/entrypoint.sh /usr/local/bin/webgis-entrypoint
RUN chmod +x /usr/local/bin/webgis-entrypoint
ENTRYPOINT ["webgis-entrypoint"]
CMD ["php", "artisan", "serve", "--host=0.0.0.0", "--port=8000"]
+41
View File
@@ -0,0 +1,41 @@
<?php
namespace App\Http\Controllers;
use App\Models\ActivityLog;
use Symfony\Component\Process\Process;
class BackupController extends Controller
{
public function download()
{
$db = config('database.connections.mysql');
$process = new Process([
'mysqldump',
'-h', $db['host'],
'-P', (string) $db['port'],
'-u', $db['username'],
'--single-transaction',
'--skip-lock-tables',
'--no-tablespaces',
$db['database'],
], null, ['MYSQL_PWD' => $db['password']]);
$process->setTimeout(120);
$process->run();
if (!$process->isSuccessful()) {
ActivityLog::record('backup', 'Gagal membuat backup database');
return response()->json(['message' => 'Backup gagal: ' . $process->getErrorOutput()], 500);
}
ActivityLog::record('backup', 'Mengunduh backup database');
$filename = 'backup-webgis-' . now()->format('Ymd-His') . '.sql';
return response($process->getOutput(), 200, [
'Content-Type' => 'application/sql',
'Content-Disposition' => "attachment; filename=\"{$filename}\"",
]);
}
}
+8 -3
View File
@@ -91,9 +91,14 @@
</h1>
<p class="text-base-content/50 mt-1">Kelola akun pengguna dan hak akses sistem.</p>
</div>
<button onclick="openCreateModal()" class="btn btn-primary shadow-lg gap-2">
<i class="fa-solid fa-user-plus"></i> Tambah Pengguna
</button>
<div class="flex flex-wrap gap-2">
<a href="{{ url('/api/admin/backup') }}" class="btn btn-outline gap-2">
<i class="fa-solid fa-database text-success"></i> Backup Database
</a>
<button onclick="openCreateModal()" class="btn btn-primary shadow-lg gap-2">
<i class="fa-solid fa-user-plus"></i> Tambah Pengguna
</button>
</div>
</div>
<!-- Stats Grid -->
+3
View File
@@ -2,6 +2,7 @@
use App\Http\Controllers\AdminUserController;
use App\Http\Controllers\AuthController;
use App\Http\Controllers\BackupController;
use App\Http\Controllers\ExportController;
use App\Http\Controllers\IbadahController;
use App\Http\Controllers\ImportController;
@@ -64,6 +65,8 @@ Route::middleware('auth')->group(function () {
Route::post('/import/ibadah', [ImportController::class, 'ibadah']);
Route::post('/import/miskin', [ImportController::class, 'miskin']);
Route::get('/backup', [BackupController::class, 'download'])->name('admin.backup');
});
});
});