簡體   English   中英

Powershell刪除項%1(上下文菜單)

[英]Powershell Remove-Item %1 (Context Menu)

一直在與Powershell戰斗以完成我需要做的事情。 這可能是一個簡單的解決方案,但我沒有找到它。 如果這個問題重復,我會道歉,但是找不到我想要的答案。

TL; DR在底部。

所以,對於我的問題。 我正在嘗試通過regedit將PS腳本添加到上下文菜單中,該腳本刪除其中的文件夾+文件,它在其中沒有任何空格的文件夾上效果很好,但是當我嘗試刪除有空格的文件夾(例如“ New Folder”)時,引發錯誤並關閉。 (試圖通過Remove-Item查找暫停/睡眠命令,但是運氣不好,除了長腳本有錯誤處理等)。

我懷疑錯誤類似於

Remove-Item : A positional parameter cannot be found that accepts argument 'Folder'.

在第1行:char:12 +刪除項<<<<新文件夾+ CategoryInfo:InvalidArgument:(:) [Remove-Item],ParameterBindingException + FullyQualifiedErrorId:PositionalParameterNotFound,Microsoft.PowerShell.Commands.RemoveItemCommand

我當前使用的代碼是

cmd /c  PowerShell Remove-Item "%1" -recurse -force

我嘗試了各種變體,使其無法正常運行。 IE將"%1"替換為“ pathAsString”,添加了另一個"% 1" ,添加了通配符"* *" ,並刪除了這些標志。 我嘗試過的代碼有一些不同的變化:

cmd /c PowerShell Remove-Item \"%1\" -recurse -force
cmd /c PowerShell Remove-Item & "{"%1" -recurse -force"}"

TL; DR cmd /c PowerShell Remove-Item "%1" -recurse -force忽略帶有空格的文件夾,並嘗試了各種操作。 上下文菜單中的用法(通過Regedit)。

可能是一個顯而易見的解決方案,但我沒有看到。

以下為我工作:

cmd /c PowerShell -command "& {Remove-Item -path '%1' -recurse -force -confirm:$false}"

使用cmd.exe時,沒有腳本塊之類的東西。 這意味着傳遞給-command的值將始終是字符串。 我在%1周圍添加了單引號('') ,以將雙引號("")與參數一起使用。 顯然,如果文件路徑中帶有單引號(') ,則此方法將失敗。 此外,即使在線文檔中說明了,也不需要呼叫運營商&

有關如何使用PowerShell.exe更多信息,請參見PowerShell.exe命令行幫助

有關PowerShell單引號和雙引號如何工作的更多信息,請參見關於報價規則

您的嘗試之一:

cmd /c PowerShell Remove-Item \\"%1\\" -recurse -force

確實有效,盡管只有那些具有嵌入式空格的路徑不包含多個相鄰空格(請參閱底部,了解為什么您第一次嘗試使用"%1"而不是\\"%1\\"無效)。

為了使命令強勁 (也更有效),使用下面的變化,這涉及cmd.exe (因為它是沒有必要的),並命令傳遞給PowerShell是封閉在"..." 作為整體帶有嵌入的"轉義為\\" (如您的嘗試):

powershell.exe -noprofile -command "Remove-Item -LiteralPath \"%1\" -Recurse -Force"

使用的PowerShell CLI選項:

  • -noprofile禁止加載當前用戶的配置文件( $PROFILE ),這只會不必要地減慢該命令的速度(或者更糟的是,可以更改其行為)。

  • -command告訴PowerShell其余參數是PowerShell命令(一段源代碼,與-file不同,后者用於調用腳本

    • 盡管您不必嚴格要求在Windows PowerShell中指定-command ,因為它隱含了該內容,但在PowerShell Core中已不再是這種情況,默認情況下,該屬性為-file

傳遞給PowerShell的Remove-Item命令:

  • 整個 PowerShell命令括在"..."可確保命令內的空格按原樣保留 ,這與碰巧包含多個空格的運行路徑有關,例如"c:\\Users\\jdoe\\Invoices<space><space>2018"

  • \\"是PowerShell如何需要嵌套 (嵌入) "字符。 使用-command 從命令行調用時 ,可以使用-進行轉義 -有關說明,請參見下文。

  • -LiteralPath確保Remove-Item字面方式解釋路徑,而不是將其解釋為通配符模式 (默認情況下會使用隱含的-Path參數); 雖然不太可能,但是如果將c:\\tmp\\folder[]這樣的路徑用作通配符,則會破壞該命令。

注意事項

  • 由於(最終)使用雙引號( "..." )括住路徑(文件資源管理器將%1擴展到的目錄路徑),因此它變成了可擴展的字符串 ,即受到字符串插值的影響 ,這意味着包含$字符的文件夾路徑(例如c:\\tmp\\$foo )可能會被誤解。

  • 您可以通過將\\"%1\\"替換為'%1'來抑制這種插值,即使用單引號引起來的字符串(PowerShell始終按字面意義對待),但是問題是您將無法使用路徑碰巧帶有'字符的文件夾上的命令。 在它們中(例如c:\\tmp\\o'reilly


為什么僅使用"%1"還不夠:

cmd /c PowerShell Remove-Item "%1" -recurse -force (您的(第一條)命令行(您將其用作File Explorer上下文菜單命令定義 ))的處理如下:

  • “文件資源管理器”按原樣-用右鍵單擊的文件夾的文件絕對路徑替換%1路徑是否包含嵌入的空格; 例如:

    • c:\\Users\\jdoe\\Invoices 2018
  • 然后執行結果命令行; 例如:

    • cmd /c PowerShell Remove-Item "c:\\Users\\jdoe\\Invoices 2018" -recurse -force
  • cmd /c在這里是偶然的(不需要):它實際上只是將命令行中繼到PowerShell(通過其可執行文件powershell.exe ); 例如:

    • powershell.exe Remove-Item "c:\\Users\\jdoe\\Invoices 2018" -recurse -force
  • PowerShell 首先通過刪除雙引號來處理各個參數Remove-Item"c:\\Users\\jdoe\\Invoices 2018"-recurse-force

  • 由於隱含了-command選項,因此將使用引號分隔的參數重新連接,並使用空格作為分隔符, 然后將其解釋為PowerShell源代碼片段 例如:

    • Remove-Item c:\\Users\\jdoe\\Invoices 2018 -recurse -force

    • 如您所見,雙引號的刪除導致PowerShell命令損壞,因為帶有空格的路徑現在缺少引號,因此c:\\Users\\jdoe\\Invoices 2018不再被視為單個參數,而是被解釋為2個參數,前綴c:\\Users\\jdoe\\Invoices后跟2018作為語法上無關的參數。

    • 當使用\\"%1\\" ,而不是"%1"單獨將阻止的前期報價剝離-告訴PowerShell中,所述"字符是初始參數解析過程中要保留 - 。另外包圍在整個PowerShell命令 "..."對於正確保留多個相鄰空間的文件路徑是必要的(即使這些路徑可能是文件夾創建過程中輸入錯誤的結果):

      • 如果不整體包含"..." ,則使用\\"引號的路徑(例如C:\\Users\\jdoe\\Invoices<space><space>2018將導致以下兩個參數:

        • \\"C:\\Users\\jdoe\\Invoices
        • 2018\\"
        • 當PowerShell稍后在各個參數之間用單個空格重新連接時(在將\\"識別為要保留轉義" ), 將結果字符串解釋為PowerShell代碼之前,它將看到"C:\\Users\\jdoe\\Invoices<space>2018" ,即,僅一個單一的空間。
      • 隨着整體封閉"..." ,整個PowerShell命令被解析為一個單獨的參數,與室內空白保留原樣 ,避免了這個問題。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM