checker.php
162 lines
| 1 | <?php |
| 2 | |
| 3 | // Namespace |
| 4 | namespace BMI\Plugin\Checker; |
| 5 | |
| 6 | // Use |
| 7 | use BMI\Plugin\BMI_Logger AS Logger; |
| 8 | use BMI\Plugin\Progress\BMI_ZipProgress AS Progress; |
| 9 | use BMI\Plugin\Backup_Migration_Plugin as BMP; |
| 10 | |
| 11 | // Exit on direct access |
| 12 | if (!defined('ABSPATH')) exit; |
| 13 | |
| 14 | /** |
| 15 | * BMI_Checker |
| 16 | */ |
| 17 | class BMI_Checker { |
| 18 | |
| 19 | public $issues = array(); |
| 20 | public $progress; |
| 21 | |
| 22 | function __construct($progress = false) { |
| 23 | |
| 24 | $this->progress = $progress; |
| 25 | |
| 26 | } |
| 27 | |
| 28 | public function logs($log, $status = 'INFO') { |
| 29 | |
| 30 | if ($this->progress) { |
| 31 | $this->progress->log($log, $status); |
| 32 | } |
| 33 | |
| 34 | } |
| 35 | |
| 36 | public function is_enabled($func) { |
| 37 | |
| 38 | $disabled = explode(',', ini_get('disable_functions')); |
| 39 | $isDisabled = in_array($func, $disabled); |
| 40 | if (!$isDisabled && function_exists($func)) return true; |
| 41 | else return false; |
| 42 | |
| 43 | } |
| 44 | |
| 45 | public function check_free_space($size, $hideRequire = false) { |
| 46 | |
| 47 | if (!$hideRequire) { |
| 48 | $this->logs(__('Requires at least ', 'backup-backup') . $size . __(' bytes.', 'backup-backup') . ' [' . BMP::humanSize($size) . ']'); |
| 49 | } |
| 50 | |
| 51 | $maxTime = 60; |
| 52 | if ($this->is_enabled('get_ini')) { |
| 53 | $maxTime = @ini_get('max_execution_time'); |
| 54 | if ($this->is_enabled('ini_set')) @ini_set('max_execution_time', '259200'); |
| 55 | } |
| 56 | |
| 57 | $shouldUseDiskFreeSpaceIfAvailable = false; |
| 58 | |
| 59 | // If free disk space is larger lower than 50 GBs |
| 60 | // OR { |
| 61 | // If there is low execution time use space check, as the other may take too much time |
| 62 | // If size of the backup is larger than 3 GBs (as it may be to slow to check) |
| 63 | // } |
| 64 | if ($this->is_enabled('disk_free_space') && (disk_free_space(BMI_BACKUPS) < 1024*1024*1024*50 || ($size > 1024*1024*1024*3 && $maxTime <= 60))) |
| 65 | $shouldUseDiskFreeSpaceIfAvailable = true; |
| 66 | |
| 67 | if ($this->is_enabled('disk_free_space') && intval(disk_free_space(BMI_BACKUPS)) > 100 && $shouldUseDiskFreeSpaceIfAvailable) { |
| 68 | |
| 69 | $this->logs(__('Disk free space function is not disabled - using it...', 'backup-backup')); |
| 70 | $this->logs(__('Checking this path/partition: ', 'backup-backup') . BMI_BACKUPS); |
| 71 | $free = intval(disk_free_space(BMI_BACKUPS)); |
| 72 | $this->logs(__('There is ', 'backup-backup') . number_format($free / 1024 / 1024, 2) . __(' MB free.', 'backup-backup') . ' [' . BMP::humanSize($free) . ']', 'SUCCESS'); |
| 73 | if ($free > $size) { |
| 74 | $this->logs(__('Great! We have enough space.', 'backup-backup'), 'SUCCESS'); |
| 75 | return true; |
| 76 | } else { |
| 77 | return false; |
| 78 | } |
| 79 | |
| 80 | } else { |
| 81 | |
| 82 | // Log |
| 83 | $this->logs(__('Disk free space function is disabled by hosting.', 'backup-backup')); |
| 84 | $this->logs(__('Using dummy file to check free space (it can take some time).', 'backup-backup')); |
| 85 | |
| 86 | // TMP Filename |
| 87 | $file = BMI_BACKUPS . '/' . '.space_check'; |
| 88 | try { |
| 89 | |
| 90 | $total = $currentTestSize = $size; |
| 91 | |
| 92 | $baseChunk = 65536; |
| 93 | $maxChunk = 1048576; |
| 94 | $currentChunk = $baseChunk; |
| 95 | $iterations = 0; |
| 96 | |
| 97 | |
| 98 | $fh = @fopen($file, 'wb'); |
| 99 | if (!$fh) { |
| 100 | $this->logs(__('Cannot create test file for space checking.', 'backup-backup'), 'ERROR'); |
| 101 | return false; |
| 102 | } |
| 103 | |
| 104 | $bytesWritten = 0; |
| 105 | |
| 106 | while ($currentTestSize > 0) { |
| 107 | $iterations++; |
| 108 | |
| 109 | $writeSize = min($currentChunk, $currentTestSize); |
| 110 | |
| 111 | $written = @fwrite($fh, str_repeat('0', $writeSize)); |
| 112 | |
| 113 | if ($written === false || $written < $writeSize) { |
| 114 | $this->logs(__('Write failed during space check - insufficient space detected.', 'backup-backup'), 'WARNING'); |
| 115 | fclose($fh); |
| 116 | if (file_exists($file)) @unlink($file); |
| 117 | return false; |
| 118 | } |
| 119 | |
| 120 | $bytesWritten += $written; |
| 121 | $currentTestSize -= $written; |
| 122 | |
| 123 | if ($iterations % 10 == 0 && $currentChunk < $maxChunk) { |
| 124 | $currentChunk = min($currentChunk * 2, $maxChunk); |
| 125 | } |
| 126 | |
| 127 | if ($iterations % 10 == 0) { |
| 128 | @fflush($fh); |
| 129 | } |
| 130 | } |
| 131 | |
| 132 | fclose($fh); |
| 133 | |
| 134 | $fs = filesize($file); |
| 135 | @unlink($file); |
| 136 | |
| 137 | if ($fs > ($total - 1024)) return true; |
| 138 | else return false; |
| 139 | |
| 140 | } catch (\Exception $e) { |
| 141 | |
| 142 | Logger::error($e); |
| 143 | if (file_exists($file)) @unlink($file); |
| 144 | $this->logs(__('Exception during space check: ', 'backup-backup') . $e->getMessage(), 'ERROR'); |
| 145 | |
| 146 | return false; |
| 147 | |
| 148 | } catch (\Throwable $e) { |
| 149 | |
| 150 | Logger::error($e); |
| 151 | if (file_exists($file)) @unlink($file); |
| 152 | $this->logs(__('Error during space check: ', 'backup-backup') . $e->getMessage(), 'ERROR'); |
| 153 | |
| 154 | return false; |
| 155 | |
| 156 | } |
| 157 | |
| 158 | } |
| 159 | |
| 160 | } |
| 161 | |
| 162 | } |