'latest', 'region' => $config['s3']['region'], 'endpoint' => $config['s3']['endpoint'], 'use_path_style_endpoint' => true, 'credentials' => [ 'key' => $config['s3']['key'], 'secret' => $config['s3']['secret'], ], 'suppress_php_deprecation_warning' => true ]); $stats = [ 'total' => count($files), 'existing' => 0, 'deleted' => 0, 'missing' => 0, 'restored' => 0, 'failed' => 0, ]; foreach ($files as $s3Key) { $filename = basename($s3Key); echo "Файл: {$filename}\n"; echo " Путь: {$s3Key}\n"; // Проверяем существование $exists = $s3Client->doesObjectExist($s3Bucket, $s3Key); if ($exists) { echo " ✅ Файл существует\n\n"; $stats['existing']++; continue; } // Проверяем версии try { $versions = $s3Client->listObjectVersions([ 'Bucket' => $s3Bucket, 'Prefix' => $s3Key, ]); $deleteMarker = null; $fileVersion = null; foreach ($versions['Versions'] ?? [] as $version) { if (isset($version['IsDeleteMarker']) && $version['IsDeleteMarker']) { $deleteMarker = $version; } else { $fileVersion = $version; } } if ($deleteMarker) { echo " ❌ Файл удален (delete marker от " . $deleteMarker['LastModified']->format('Y-m-d H:i:s') . ")\n"; if (!$dryRun) { // Удаляем delete marker $s3Client->deleteObject([ 'Bucket' => $s3Bucket, 'Key' => $s3Key, 'VersionId' => $deleteMarker['VersionId'], ]); echo " ✅ Delete marker удален\n"; // Восстанавливаем файл из версии if ($fileVersion) { $s3Client->copyObject([ 'Bucket' => $s3Bucket, 'Key' => $s3Key, 'CopySource' => "{$s3Bucket}/{$s3Key}?versionId={$fileVersion['VersionId']}", ]); echo " ✅ Файл восстановлен из версии\n"; $stats['restored']++; } else { echo " ⚠️ Версия файла не найдена\n"; $stats['missing']++; } sleep(1); } else { echo " ⏸️ Будет восстановлен (dry-run)\n"; $stats['restored']++; } $stats['deleted']++; } else { echo " ⚠️ Файл отсутствует, delete marker не найден\n"; $stats['missing']++; } } catch (Exception $e) { echo " ❌ Ошибка: " . $e->getMessage() . "\n"; $stats['failed']++; } echo "\n"; } // Итоги echo str_repeat("=", 80) . "\n"; echo "ИТОГИ:\n"; echo "Всего файлов: {$stats['total']}\n"; echo "Существующих: {$stats['existing']}\n"; echo "Удаленных: {$stats['deleted']}\n"; echo "Отсутствующих: {$stats['missing']}\n"; if (!$dryRun) { echo "Восстановлено: {$stats['restored']}\n"; echo "Ошибок: {$stats['failed']}\n"; } else { echo "Будет восстановлено: {$stats['restored']}\n"; } echo "\n=== ГОТОВО ===\n"; } catch (Exception $e) { echo "❌ Ошибка: " . $e->getMessage() . "\n"; exit(1); }