Загрузка данных


$ErrorActionPreference = "Continue"

$TimeStamp = Get-Date -Format "yyyyMMdd_HHmmss"
$Log = "C:\Disk_C_Cleanup_$TimeStamp.log"

function Write-Log {
    param([string]$Text)

    $Line = "{0}  {1}" -f (Get-Date -Format "yyyy-MM-dd HH:mm:ss"), $Text
    Write-Host $Line
    $Line | Out-File -FilePath $Log -Append -Encoding UTF8
}

function Get-CDriveInfo {

    $Drive = Get-WmiObject Win32_LogicalDisk -Filter "DeviceID='C:'"

    [pscustomobject]@{
        SizeGB    = [math]::Round($Drive.Size / 1GB, 2)
        FreeGB    = [math]::Round($Drive.FreeSpace / 1GB, 2)
        UsedGB    = [math]::Round(($Drive.Size - $Drive.FreeSpace) / 1GB, 2)
        FreePct   = [math]::Round(($Drive.FreeSpace / $Drive.Size) * 100, 1)
    }
}

function Remove-OldFiles {
    param(
        [string]$Path,
        [int]$OlderThanDays
    )

    if (-not (Test-Path -LiteralPath $Path)) {
        Write-Log "Папка отсутствует: $Path"
        return
    }

    $Limit = (Get-Date).AddDays(-$OlderThanDays)

    Write-Log "Очистка файлов старше $OlderThanDays дней: $Path"

    Get-ChildItem `
        -LiteralPath $Path `
        -File `
        -Force `
        -Recurse `
        -ErrorAction SilentlyContinue |
        Where-Object {
            $_.LastWriteTime -lt $Limit
        } |
        ForEach-Object {

            try {
                Write-Log "Удаление: $($_.FullName) [$([math]::Round($_.Length / 1MB, 2)) MB]"

                Remove-Item `
                    -LiteralPath $_.FullName `
                    -Force `
                    -ErrorAction Stop
            }
            catch {
                Write-Log "Не удалось удалить: $($_.FullName) — $($_.Exception.Message)"
            }
        }

    Get-ChildItem `
        -LiteralPath $Path `
        -Directory `
        -Force `
        -Recurse `
        -ErrorAction SilentlyContinue |
        Sort-Object FullName -Descending |
        ForEach-Object {

            try {
                if (-not (Get-ChildItem -LiteralPath $_.FullName -Force -ErrorAction SilentlyContinue)) {
                    Remove-Item -LiteralPath $_.FullName -Force -ErrorAction Stop
                }
            }
            catch {
            }
        }
}

Write-Log "============================================================"
Write-Log "НАЧАЛО БЕЗОПАСНОЙ ОЧИСТКИ ДИСКА C:"
Write-Log "============================================================"

$Before = Get-CDriveInfo

Write-Log "До очистки:"
Write-Log "Размер C: $($Before.SizeGB) GB"
Write-Log "Свободно: $($Before.FreeGB) GB ($($Before.FreePct)%)"
Write-Log "Занято:   $($Before.UsedGB) GB"

Write-Log ""
Write-Log "1. Очистка Windows Error Reporting"

$WerService = Get-Service -Name WerSvc -ErrorAction SilentlyContinue
$WerWasRunning = $false

if ($WerService -and $WerService.Status -eq "Running") {

    $WerWasRunning = $true

    try {
        Stop-Service WerSvc -Force -ErrorAction Stop
        Write-Log "Служба WerSvc остановлена"
    }
    catch {
        Write-Log "Не удалось остановить WerSvc: $($_.Exception.Message)"
    }
}

$WerPaths = @(
    "C:\ProgramData\Microsoft\Windows\WER\ReportQueue",
    "C:\ProgramData\Microsoft\Windows\WER\ReportArchive",
    "C:\ProgramData\Microsoft\Windows\WER\Temp"
)

foreach ($WerPath in $WerPaths) {

    if (Test-Path -LiteralPath $WerPath) {

        Get-ChildItem `
            -LiteralPath $WerPath `
            -Force `
            -ErrorAction SilentlyContinue |
            ForEach-Object {

                try {
                    Write-Log "Удаление WER: $($_.FullName)"

                    Remove-Item `
                        -LiteralPath $_.FullName `
                        -Recurse `
                        -Force `
                        -ErrorAction Stop
                }
                catch {
                    Write-Log "Не удалось удалить WER: $($_.FullName)"
                }
            }
    }
}

if ($WerWasRunning) {

    try {
        Start-Service WerSvc -ErrorAction Stop
        Write-Log "Служба WerSvc запущена"
    }
    catch {
        Write-Log "Не удалось запустить WerSvc: $($_.Exception.Message)"
    }
}

Write-Log ""
Write-Log "2. Очистка старых временных файлов Windows"

Remove-OldFiles `
    -Path "C:\Windows\Temp" `
    -OlderThanDays 7

Write-Log ""
Write-Log "3. Очистка старых TEMP-файлов пользовательских профилей"

Get-ChildItem `
    -LiteralPath "C:\Users" `
    -Directory `
    -Force `
    -ErrorAction SilentlyContinue |
    ForEach-Object {

        $UserTemp = Join-Path $_.FullName "AppData\Local\Temp"

        Remove-OldFiles `
            -Path $UserTemp `
            -OlderThanDays 14
    }

Write-Log ""
Write-Log "4. Штатная очистка хранилища компонентов Windows"
Write-Log "Команда может выполняться продолжительное время"

$DismProcess = Start-Process `
    -FilePath "dism.exe" `
    -ArgumentList "/Online", "/Cleanup-Image", "/StartComponentCleanup" `
    -Wait `
    -PassThru `
    -NoNewWindow

Write-Log "DISM завершён. ExitCode=$($DismProcess.ExitCode)"

$After = Get-CDriveInfo
$Freed = [math]::Round($After.FreeGB - $Before.FreeGB, 2)

Write-Log ""
Write-Log "============================================================"
Write-Log "ОЧИСТКА ЗАВЕРШЕНА"
Write-Log "============================================================"
Write-Log "До очистки свободно:    $($Before.FreeGB) GB"
Write-Log "После очистки свободно: $($After.FreeGB) GB"
Write-Log "Освобождено:            $Freed GB"
Write-Log "Свободно сейчас:        $($After.FreePct)%"
Write-Log ""
Write-Log "Лог: $Log"

Write-Host ""
Write-Host "Результат:" -ForegroundColor Cyan
Get-CDriveInfo | Format-List
Write-Host "Лог: $Log" -ForegroundColor Cyan