Closed
Description
If you make a symbolic link to a directory on Windows (with administrative privileges of course), and then try to delete said link, you get this:
|Y> Yes |A> Yes to All |N> No |L> No to All |S> Suspend [Default is (Y]
PS C:\Users\anschwa\src\PowerShell> remove-item -Force .\foobar\
Confirm
The item at C:\Users\anschwa\src\PowerShell\foobar\ has children and the Recurse parameter was not specified. If you con
tinue, all children will be removed with the item. Are you sure you want to continue?
|Y> Yes |A> Yes to All |N> No |L> No to All |S> Suspend [Default is (Y]
n
PS C:\Users\anschwa\src\PowerShell> remove-item -Force .\foobar\ -Recurse
remove-item : There is a mismatch between the tag specified in the request and the tag present in the reparse point
At line:1 char:1
+ remove-item -Force .\foobar\ -Recurse
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [Remove-Item], Win32Exception
+ FullyQualifiedErrorId : System.ComponentModel.Win32Exception,Microsoft.PowerShell.Commands.RemoveItemCommand
PS C:\Users\anschwa\src\PowerShell> $error[0].Exception.StackTrace
at Microsoft.PowerShell.Commands.InternalSymbolicLinkLinkCodeMethods.DeleteJunction(String junctionPath) in C:\Users\
anschwa\src\PowerShell\src\monad\monad\src\namespaces\FileSystemProvider.cs:line 8447
at Microsoft.PowerShell.Commands.FileSystemProvider.RemoveDirectoryInfoItem(DirectoryInfo directory, Boolean recurse,
Boolean force, Boolean rootOfRemoval) in C:\Users\anschwa\src\PowerShell\src\monad\monad\src\namespaces\FileSystemProvi
der.cs:line 2859
at Microsoft.PowerShell.Commands.FileSystemProvider.RemoveItem(String path, Boolean recurse) in C:\Users\anschwa\src\
PowerShell\src\monad\monad\src\namespaces\FileSystemProvider.cs:line 2733
at System.Management.Automation.Provider.ContainerCmdletProvider.RemoveItem(String path, Boolean recurse, CmdletProvi
derContext context) in C:\Users\anschwa\src\PowerShell\src\monad\monad\src\namespaces\ContainerProviderBase.cs:line 422
at System.Management.Automation.SessionStateInternal.RemoveItem(CmdletProvider providerInstance, String path, Boolean
recurse, CmdletProviderContext context) in C:\Users\anschwa\src\PowerShell\src\monad\monad\src\engine\SessionStateConta
iner.cs:line 1152
Remove-Item
is thinking the link is a directory and so failing to delete it.
If the code is changed such that File.Delete(junction)
is used instead of native calls, you get:
PS C:\Users\anschwa\src\PowerShell> rm .\foobar\ -Force
Confirm
The item at C:\Users\anschwa\src\PowerShell\foobar\ has children and the Recurse parameter was not specified. If you con
tinue, all children will be removed with the item. Are you sure you want to continue?
|Y> Yes |A> Yes to All |N> No |L> No to All |S> Suspend [Default is (Y]
y
rm : Index (zero based) must be greater than or equal to zero and less than the size of the argument list.
At line:1 char:1
+ rm .\foobar\ -Force
+ ~~~~~~~~~~~~~~~~~~~
+ CategoryInfo : NotSpecified: (:) [Remove-Item], FormatException
+ FullyQualifiedErrorId : System.FormatException,Microsoft.PowerShell.Commands.RemoveItemCommand
PS C:\Users\anschwa\src\PowerShell> $error[0].Exception.StackTrace
at System.Text.StringBuilder.AppendFormatHelper(IFormatProvider provider, String format, ParamsArray args)
at System.String.FormatHelper(IFormatProvider provider, String format, ParamsArray args)
at System.String.Format(IFormatProvider provider, String format, Object arg0)
at System.Management.Automation.Internal.StringUtil.Format(String formatSpec, Object o) in C:\Users\anschwa\src\Power
Shell\src\monad\monad\src\utils\StringUtil.cs:line 18
at Microsoft.PowerShell.Commands.FileSystemProvider.RemoveDirectoryInfoItem(DirectoryInfo directory, Boolean recurse,
Boolean force, Boolean rootOfRemoval) in C:\Users\anschwa\src\PowerShell\src\monad\monad\src\namespaces\FileSystemProvi
der.cs:line 2863
at Microsoft.PowerShell.Commands.FileSystemProvider.RemoveItem(String path, Boolean recurse) in C:\Users\anschwa\src\
PowerShell\src\monad\monad\src\namespaces\FileSystemProvider.cs:line 2733
at System.Management.Automation.Provider.ContainerCmdletProvider.RemoveItem(String path, Boolean recurse, CmdletProvi
derContext context) in C:\Users\anschwa\src\PowerShell\src\monad\monad\src\namespaces\ContainerProviderBase.cs:line 422
at System.Management.Automation.SessionStateInternal.RemoveItem(CmdletProvider providerInstance, String path, Boolean
recurse, CmdletProviderContext context) in C:\Users\anschwa\src\PowerShell\src\monad\monad\src\engine\SessionStateConta
iner.cs:line 1152
It fails even sooner (I think because there aren't actually any children to pass delete recursively, so it gets an empty list; just a guess).
If you use Directory.Delete(junctionPath)
, it works just fine!