Enhance Proxmox views with improved loading states and UI updates
- Updated serverplaceholder.blade.php to enhance loading skeletons for server details. - Added navigation breadcrumbs to statistics, subdomain, and system views for better user experience. - Improved loading indicators for CPU, network, memory, and disk charts in statistics.blade.php. - Refined storage.blade.php layout with section dividers and improved drive display, including bus type indicators and quota usage. - Enhanced VNC and Xterm popups with a new header design, loading animations, and reconnect functionality. - Added error handling for VNC and Xterm connections to inform users when unable to connect.
This commit is contained in:
@@ -514,18 +514,40 @@ class Storage extends Component
|
||||
*/
|
||||
public function addDrive(): void
|
||||
{
|
||||
// Validate bus type against allowed values to prevent config key injection
|
||||
if (!array_key_exists($this->newDriveBus, $this->busTypes)) {
|
||||
$this->notify('Invalid bus type selected.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate cache mode against allowed values to prevent config value injection
|
||||
$allowedCaches = array_column($this->cacheOptions, 'value');
|
||||
if (!in_array($this->newDriveCache, $allowedCaches, true)) {
|
||||
$this->notify('Invalid cache mode selected.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate AIO type against allowed values to prevent config value injection
|
||||
$allowedAios = array_column($this->aioOptions, 'value');
|
||||
if (!in_array($this->newDriveAio, $allowedAios, true)) {
|
||||
$this->notify('Invalid async IO type selected.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate size
|
||||
if ($this->newDriveSize < 1) {
|
||||
$this->notify('Drive size must be at least 1 GB.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Check storage quota
|
||||
$newTotal = $this->totalAllocatedStorage + $this->newDriveSize;
|
||||
if ($newTotal > $this->maxAllowedStorage) {
|
||||
$remaining = $this->maxAllowedStorage - $this->totalAllocatedStorage;
|
||||
$this->notify("Adding this drive would exceed your storage quota. You have {$remaining} GB remaining.", 'error');
|
||||
return;
|
||||
// Check storage quota (skip if no limit is set, i.e. maxAllowedStorage is 0)
|
||||
if ($this->maxAllowedStorage > 0) {
|
||||
$newTotal = $this->totalAllocatedStorage + $this->newDriveSize;
|
||||
if ($newTotal > $this->maxAllowedStorage) {
|
||||
$remaining = max(0, $this->maxAllowedStorage - $this->totalAllocatedStorage);
|
||||
$this->notify("Adding this drive would exceed your storage quota. You have {$remaining} GB remaining.", 'error');
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
// Get next available index
|
||||
@@ -644,6 +666,20 @@ class Storage extends Component
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate cache mode against allowed values to prevent config value injection
|
||||
$allowedCaches = array_column($this->cacheOptions, 'value');
|
||||
if (!in_array($this->editDriveCache, $allowedCaches, true)) {
|
||||
$this->notify('Invalid cache mode selected.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Validate AIO type against allowed values to prevent config value injection
|
||||
$allowedAios = array_column($this->aioOptions, 'value');
|
||||
if (!in_array($this->editDriveAio, $allowedAios, true)) {
|
||||
$this->notify('Invalid async IO type selected.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
$drive = $this->drives[$this->editingDriveKey];
|
||||
$busType = $drive['bus'];
|
||||
|
||||
@@ -840,6 +876,12 @@ class Storage extends Component
|
||||
$drive = $this->drives[$this->movingDriveKey];
|
||||
$targetBus = $this->moveDriveTargetBus;
|
||||
|
||||
// Validate target bus type against allowed values
|
||||
if (!array_key_exists($targetBus, $this->busTypes)) {
|
||||
$this->notify('Invalid target bus type.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Prevent moving to the same bus type
|
||||
if ($drive['bus'] === $targetBus) {
|
||||
$this->notify('Drive is already on the ' . $this->busTypes[$targetBus]['label'] . ' bus.', 'error');
|
||||
@@ -1080,6 +1122,12 @@ class Storage extends Component
|
||||
$unusedDrive = $this->unusedDrives[$this->reattachingDriveKey];
|
||||
$targetBus = $this->reattachTargetBus;
|
||||
|
||||
// Validate target bus type against allowed values
|
||||
if (!array_key_exists($targetBus, $this->busTypes)) {
|
||||
$this->notify('Invalid target bus type.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
// Reattaching doesn't add new storage — unused drives are already counted in totalAllocatedStorage.
|
||||
// Only block if total storage strictly exceeds the quota (which would indicate a data inconsistency).
|
||||
if ($this->totalAllocatedStorage > $this->maxAllowedStorage && $this->maxAllowedStorage > 0) {
|
||||
@@ -1209,6 +1257,13 @@ class Storage extends Component
|
||||
*/
|
||||
public function saveScsiController(): void
|
||||
{
|
||||
// Validate SCSI controller type against allowed values
|
||||
$allowedControllers = array_column($this->scsiControllerOptions, 'value');
|
||||
if (!in_array($this->scsiControllerType, $allowedControllers, true)) {
|
||||
$this->notify('Invalid SCSI controller type.', 'error');
|
||||
return;
|
||||
}
|
||||
|
||||
if ($this->scsiControllerType === $this->originalScsiControllerType) {
|
||||
$this->notify('No changes to save.', 'info');
|
||||
return;
|
||||
|
||||
Reference in New Issue
Block a user