Сила - удаляет файлы, и каталоги в PowerShell иногда перестал работать, но не всегда

Обновление:

Эта ссылка объясняет, как диагностировать Удаленный доступ для Вашего MediaSmart или Windows Home Server:

ВАЖНЫЙ - ДОЛЖЕН ЧИТАТЬ: Если у Вас есть какие-либо другие маршрутизаторы в Вашей сети. Это включает DSL или Кабельные модемы со встроенными маршрутизаторами, Vonage или другими Телефонными устройствами IP, это могло быть причиной Вашей проблемы. Можно попытаться установить демилитаризованную зону из Vonage или VoIP, DSL или Кабельного устройства к маршрутизатору и затем попробовать конфигурацию Маршрутизатора MS снова. Это могло решить Вашу проблему.

Если у Вас есть маршрутизатор Vonage, который является перед Вашим нормальным маршрутизатором, можно попытаться переместить устройство Vonage позади маршрутизатора. Удостоверьтесь, что Вы перезагружаете свой кабельный модем, маршрутизатор и устройство Vonage (в том порядке, приостанавливающем 1 минуту прежде, чем включить каждое устройство). Удостоверьтесь, что сервер MediaSmart подключен к нормальному маршрутизатору а не устройству Vonage (если это не Ваша установка),


Если Вы получите "Проверку, что Ваш удаленный веб-сайт доступен из Интернета" ошибка при конфигурировании Вашего маршрутизатора, считайте этот поток форумов Microsoft:

У меня была та же проблема, которая заставляла меня напряженно трудиться в течение двух дней. Просто найденный решением в Интернете. Сначала не настройте и маршрутизатор и домен. Затем настройте домен, сначала заканчивают маршрутизатор впоследствии.


Могло иметь место, что Вы ищете проблему на неправильном конце? Могло случиться так, что Нельзя соединиться от Вашего удаленного местоположения?

Если Вашей моделью маршрутизатора является UPnP-сертифицированное-устройство и если установка UPnP маршрутизатора включена, Windows Home Server может автоматически настроить его. См. эту статью поддержки Microsoft: информация об автоматической функции конфигурации маршрутизатора в Windows Home Server.

Если последний метод не работает с Вашей моделью маршрутизатора, попытайтесь передать следующие порты это для включения удаленного доступа: TCP 80, 443 и 4125 к локальному IP-адресу Вашего Windows Home Server.

33
задан 30 October 2015 в 19:22
10 ответов

help Remove-Item говорит:

Рекурсивно вызывать параметр в этом cmdlet не работает правильно.

и

Поскольку Рекурсивно вызывать параметр в этом cmdlet является дефектным, команда использует Получение-Childitem cmdlet для получения требования d файлы, и это использует оператора трубопровода для передачи их Удалять-объекту cmdlet.

и предлагает эту альтернативу как пример:

get-childitem * -include *.csv -recurse | remove-item

Таким образом, необходимо передать по каналу get-childitem -recurse в remove-item.

31
ответ дан 28 November 2019 в 19:54

У меня была эта проблема с каталогом, который не удалит. Я нашел, что одна из подпапок была повреждена и когда я пытался переместиться, или переименовать тот дочерний dir я получил сообщение об ошибке, говоря что-то об этом являющийся недостающим. Я попытался использовать комнату - Сила и получил ту же ошибку, как Вы сделали.

то, Что работало на меня, сжимало родительский dir, использующий с 7 zip с проверенной опцией "Delete files after compression". После того как это было сжато, я смог удалить zip-файл.

0
ответ дан 28 November 2019 в 19:54

Текущий ответ на самом деле не удалит каталог, просто его дети. Кроме того, это будет иметь проблемы с вложенными каталогами, поскольку это будет снова пытаться удалить каталог перед своим содержанием. Я записал что-то для удаления файлов в правильном порядке, будет все еще иметь ту же проблему, хотя иногда каталог все еще был бы вокруг позже.

Так, теперь я использую что-то, что поймает исключение, ожидать, и повторная попытка (3 раза):

На данный момент я использую это:

function EmptyDirectory($directory = $(throw "Required parameter missing")) {

    if ((test-path $directory) -and -not (gi $directory | ? { $_.PSIsContainer })) {
        throw ("EmptyDirectory called on non-directory.");
    }

    $finished = $false;
    $attemptsLeft = 3;

    do {
        if (test-path $directory) {
            rm $directory -recurse -force
        }

        try {
            $null = mkdir $directory
            $finished = $true
        } 
        catch [System.IO.IOException] {
            Start-Sleep -Milliseconds 500
        }

        $attemptsLeft = $attemptsLeft - 1;
    } 
    while (-not $finished -and $attemptsLeft -gt 0)

    if (-not $finished) {
        throw ("Unable to clean and recreate directory " + $directory)
    }
}
3
ответ дан 28 November 2019 в 19:54

Чтобы удалить каталог и его содержимое, нужно выполнить два шага. Сначала удалите содержимое, затем саму папку. Используя обходной путь для ошибочного рекурсивного элемента удаления, решение будет выглядеть следующим образом:

Get-ChildItem -Path "$folder\\*" -Recurse | Remove-Item -Force -Recurse
Remove-Item $folder

Таким образом, вы также можете удалить родительский каталог.

3
ответ дан 28 November 2019 в 19:54

ETA 20181217: PSVersion 4.0 и более поздних версий все равно не удастся при некоторых обстоятельствах, см. Альтернативный ответ Мехрдад Мирреза и отчет об ошибке , поданный mklement

mklement , предоставляет доказательство концепции в этом ответе SO , так как ошибка ожидает официального исправления

Новая версия из PowerShell ( PSVersion 4.0 ) полностью устранил эту проблему, а Remove-Item "targetdirectory" -Recurse -Force работает без каких-либо проблем с синхронизацией.

Вы можно проверить свою версию, запустив $ PSVersiontable из командной строки ISE или PowerShell . 4.0 - это версия, которая поставляется с Windows 8.1 и Server 2012 R2 , и ее также можно установить в предыдущих версиях Windows.

7
ответ дан 28 November 2019 в 19:54

@JamesCW: Проблема все еще существует в PowerShell 4.0

Я попробовал другой обходной путь, и он сработал: используйте cmd.exe:

&cmd.exe /c rd /s /q $somedirectory
17
ответ дан 28 November 2019 в 19:54

Вот что у меня работает:

$Target = "c:\folder_to_delete"

Get-ChildItem -Path $Target -Recurse -force |
  Where-Object { -not ($_.psiscontainer) } |
   Remove-Item –Force

Remove-Item -Recurse -Force $Target

Эта первая строка удаляет все файлы в дереве. Второй удаляет все папки, включая верхнюю.

2
ответ дан 28 November 2019 в 19:54

Сначала возьмите права собственности на файлы / каталоги с помощью Takeown.exe, а затем удалите

https://learn-powershell.net/2014/06/24/changing-ownership-of-file-or-folder-using-powershell/

0
ответ дан 28 November 2019 в 19:54

Обновление : По-видимому, есть планы сделать API удаления элементов файловой системы Windows синхронными, но они еще не синхронизированы в Windows 10 версии 1903 - см. этот комментарий на GitHub .


Существующие ответы смягчают проблему, поэтому она возникает реже, но они не устраняют основную причину , поэтому сбои все еще могут происходить.

Remove-Item -Recurse неожиданно асинхронный , в конечном счете потому, что методы Windows API для удаления файлов и каталогов по своей сути асинхронны и Remove-Item не учитывает это.

Это периодически, непредсказуемо проявляется одним из двух способов:

  • Ваш случай: удаление непустого каталога может завершиться ошибкой , если удаление подкаталога или файла в нем еще не завершено к моменту попытки удалить родительский каталог.

  • Меньше co mmonly: воссоздание удаленного каталога сразу после удаления может завершиться ошибкой, поскольку удаление может еще не быть завершено к моменту попытки повторного создания.

Проблема затрагивает не только PowerShell Remove-Item , но также cmd.exe rd / s , а также .NET [System.IO.Directory] :: Delete () :

Начиная с Windows PowerShell v5.1 / PowerShell Core 6.2.0-preview.1 / cmd.exe 10.0.17134.407 / .NET Framework 4.7.03056, .NET Core 2.1, ни Remove-Item , ни rd / s , ни [System.IO.Directory] :: Delete () не работают надежно , потому что они не работают учитывать асинхронное поведение функций удаления файлов / каталогов Windows API :

Для настраиваемая функция PowerShell , обеспечивающая надежную синхронизацию Обходной путь , см. этот ответ SO .

4
ответ дан 28 November 2019 в 19:54

Гоша. Множество ответов. Я честно предпочитаю этот всем им. Он очень простой, полный, читаемый и работает на любом компьютере с Windows. Он использует (надежную) функцию рекурсивного удаления .NET и, если по какой-то причине не удается, генерирует соответствующее исключение, которое может быть обработано блоком try / catch.

$fullPath = (Resolve-Path "directory\to\remove").ProviderPath
[IO.Directory]::Delete($fullPath, $true)

Обратите внимание, что строка Resolve-Path важно, потому что .NET не знает ваш текущий каталог при разрешении относительных путей к файлам. Это единственное, что я могу придумать.

3
ответ дан 28 November 2019 в 19:54

Теги

Похожие вопросы