78 lines
2.7 KiB
PHP
78 lines
2.7 KiB
PHP
<?php
|
|
|
|
namespace App\Livewire\Ui\System\Modal;
|
|
|
|
use Livewire\Attributes\On;
|
|
use LivewireUI\Modal\ModalComponent;
|
|
use Illuminate\Support\Str;
|
|
|
|
class UpdateModal extends ModalComponent
|
|
{
|
|
public string $state = 'unknown'; // running|done|unknown
|
|
public ?int $rc = null; // exit code
|
|
public ?string $line = null; // letzte Logzeile hübsch
|
|
public array $tail = []; // letzte N Logzeilen roh
|
|
public int $percent = 0; // heuristisch (optional)
|
|
public static bool $closingAllowed = false;
|
|
|
|
private const LOG = '/var/log/mailwolt-update.log';
|
|
private const STATE_DIR = '/var/lib/mailwolt/update';
|
|
|
|
public function mount(): void
|
|
{
|
|
$this->refresh();
|
|
}
|
|
|
|
public function render()
|
|
{
|
|
return view('livewire.ui.system.modal.update-modal');
|
|
}
|
|
|
|
#[On('update:modal-refresh')]
|
|
public function refresh(): void
|
|
{
|
|
$st = @trim(@file_get_contents(self::STATE_DIR.'/state') ?: '');
|
|
$rcRaw = @trim(@file_get_contents(self::STATE_DIR.'/rc') ?: '');
|
|
|
|
$this->state = $st ?: 'unknown';
|
|
$this->rc = is_numeric($rcRaw) ? (int)$rcRaw : null;
|
|
|
|
// Log einlesen
|
|
$lines = @file(self::LOG, FILE_IGNORE_NEW_LINES) ?: [];
|
|
$this->tail = array_slice($lines, -30);
|
|
|
|
$last = trim($this->tail ? end($this->tail) : '');
|
|
$last = preg_replace('/^\[\w\]\s*/', '', $last);
|
|
$last = preg_replace('/^=+ .*? =+\s*$/', 'Update beendet', $last);
|
|
$last = preg_replace('/^\d{4}-\d{2}-\d{2}T[^ ]+\s*::\s*/', '', $last);
|
|
$this->line = Str::limit($last, 160);
|
|
|
|
// ganz simple Fortschritts-Heuristik über bekannte Meilensteine
|
|
$text = implode("\n", $this->tail);
|
|
$pct = 5;
|
|
foreach ([
|
|
'Update gestartet' => 10,
|
|
'Composer' => 25,
|
|
'npm ci' => 40,
|
|
'npm run build' => 60,
|
|
'migrate' => 75,
|
|
'optimize' => 85,
|
|
'Version aktualisiert' => 95,
|
|
'Update beendet' => 100,
|
|
] as $needle => $val) {
|
|
if (stripos($text, $needle) !== false) { $pct = max($pct, $val); }
|
|
}
|
|
if ($this->state === 'done') { $pct = 100; }
|
|
$this->percent = $pct;
|
|
|
|
// Auto-Close vorbereiten
|
|
if ($this->state === 'done' && $this->rc === 0) {
|
|
static::$closingAllowed = true;
|
|
}
|
|
}
|
|
|
|
public static function modalMaxWidth(): string { return '2xl'; }
|
|
public static function closeModalOnEscape(): bool { return static::$closingAllowed; }
|
|
public static function closeModalOnClickAway(): bool { return static::$closingAllowed; }
|
|
}
|