Files
Network-MGMT/app/Console/Commands/AppInstallUpdateCommand.php
T

116 lines
5.4 KiB
PHP

<?php
namespace App\Console\Commands;
use Illuminate\Console\Command;
use Illuminate\Support\Facades\Artisan;
use Illuminate\Support\Facades\Cache;
class AppInstallUpdateCommand extends Command
{
protected $signature = 'app:install-update {--tag= : Bestimmten Git-Tag installieren}';
protected $description = 'Installiert das neueste Update vom Gitea-Repository';
public function handle(): int
{
$projectPath = base_path();
$this->info('');
$this->info('╔══════════════════════════════════════╗');
$this->info('║ Network-MGMT Update ║');
$this->info('╚══════════════════════════════════════╝');
$this->info('');
// ── 1. Tags holen ──────────────────────────────────────────────────────
$this->info('▶ Git: Aktuelle Tags holen ...');
$this->exec("cd {$projectPath} && git fetch --tags 2>&1");
// ── 2. Ziel-Tag bestimmen ──────────────────────────────────────────────
if ($this->option('tag')) {
$targetTag = $this->option('tag');
} else {
$targetTag = trim(shell_exec(
"cd {$projectPath} && git describe --tags \$(git rev-list --tags --max-count=1) 2>/dev/null"
));
}
if (empty($targetTag)) {
$this->error('Kein Release-Tag im Repository gefunden.');
return Command::FAILURE;
}
$currentVersion = config('version.current');
$this->info(" Aktuell: {$currentVersion}");
$this->info(" Ziel: {$targetTag}");
$this->info('');
if ($targetTag === $currentVersion) {
$this->warn('Bereits auf der neuesten Version. Abbruch.');
return Command::SUCCESS;
}
// ── 3. Wartungsmodus ───────────────────────────────────────────────────
$this->info('▶ Wartungsmodus aktivieren ...');
Artisan::call('down', ['--render' => 'errors.maintenance']);
try {
// ── 4. Git Checkout ────────────────────────────────────────────────
$this->info("▶ Git: Checkout {$targetTag} ...");
$this->exec("cd {$projectPath} && git checkout {$targetTag} 2>&1");
// ── 5. Composer ────────────────────────────────────────────────────
$this->info('▶ Composer: Abhängigkeiten aktualisieren ...');
$this->exec("cd {$projectPath} && composer install --no-dev --optimize-autoloader --no-interaction 2>&1");
// ── 6. Assets ──────────────────────────────────────────────────────
if (file_exists("{$projectPath}/package.json")) {
$this->info('▶ Node: Assets neu bauen ...');
$this->exec("cd {$projectPath} && npm ci --silent 2>&1");
$this->exec("cd {$projectPath} && npm run build 2>&1");
}
// ── 7. Migrationen ─────────────────────────────────────────────────
$this->info('▶ Datenbank: Migrationen ausführen ...');
Artisan::call('migrate', ['--force' => true, '--no-interaction' => true]);
$this->line(Artisan::output());
// ── 8. Cache leeren und neu aufbauen ───────────────────────────────
$this->info('▶ Cache: Neu aufbauen ...');
Artisan::call('config:cache');
Artisan::call('route:cache');
Artisan::call('view:cache');
// ── 9. Update-Cache zurücksetzen ───────────────────────────────────
Cache::forget('app_update_available');
Cache::forget('app_update_checked_at');
$this->info('');
$this->info("✓ Update auf {$targetTag} erfolgreich abgeschlossen!");
} catch (\Throwable $e) {
$this->error('Update fehlgeschlagen: ' . $e->getMessage());
Artisan::call('up');
return Command::FAILURE;
} finally {
// ── 10. Wartungsmodus deaktivieren ─────────────────────────────────
$this->info('▶ Wartungsmodus deaktivieren ...');
Artisan::call('up');
}
return Command::SUCCESS;
}
private function exec(string $cmd): void
{
$output = shell_exec($cmd);
if ($output) {
foreach (explode("\n", trim($output)) as $line) {
if (trim($line)) {
$this->line(" {$line}");
}
}
}
}
}