8000 Change behavior of Remove-Item on symbolic links (#621) by jeffbi · Pull Request #3637 · PowerShell/PowerShell · GitHub
[go: up one dir, main page]

Skip to content

Change behavior of Remove-Item on symbolic links (#621) #3637

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 5 commits into from
Apr 28, 2017
Merged

Change behavior of Remove-Item on symbolic links (#621) #3637

merged 5 commits into from
Apr 28, 2017

Conversation

jeffbi
Copy link
Contributor
@jeffbi jeffbi commented Apr 24, 2017

When Remove-Item is used to remove a symbolic link in Windows, only the link itself is removed. The -Force switch is no longer required.

If the directory pointed to by the link has child items, the cmdlet no longer prompts the user to remove the child items---those child items are not removed. The -Recurse switch, if given, is ignored.

This brings Remove-Item more in line with the behavior of the 'rm' command on Unix.

Partially fix #621

When Remove-Item is used to remove a symbolic link, only the link itself is removed. The -Recurse switch, if given, is ignored.
@PaulHigin
Copy link
Contributor

Please provide more information on the issue along with example of current behavior and example of expected behavior. What do you expect the recursive switch parameter to do, remove all files as well? This sounds like a breaking change (Remove-Item no longer just removes a symbolic link) and if so we should mark this PR accordingly. Also please discuss the fix. It is not clear to me how these changes solve the problem.

@daxian-dbw
Copy link
Member

Close/Reopen the PR to trigger the stuck CI build.

@daxian-dbw daxian-dbw self-assigned this Apr 25, 2017
@daxian-dbw daxian-dbw requested a review from PaulHigin April 25, 2017 16:53
@@ -2863,15 +2863,6 @@ private void RemoveDirectoryInfoItem(DirectoryInfo directory, bool recurse, bool
continueRemoval = ShouldProcess(directory.FullName, action);
}

//if this is a reparse point and force is not specified then warn user but dont remove the directory.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Why is this removed. It seems like the -Force parameter was required before removing and was Windows only. So I assume removing this requirement makes Windows and Linux behavior the same. Please make this clear in the PR description.

Also if we remove this code we should also remove the associated FileSystemProviderStrings.DirectoryReparsePoint message string since it is no longer used.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I've updated the PR description and removed the unused DirectoryReparsePoint message string.

try
{
DirectoryInfo directory = new DirectoryInfo(path);

// If the above didn't throw an exception, check to
// see if it contains any directories
// see if we should proceed and if it contains any children
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is a bit surprising. What case does this cover where an exception is not thrown but Attributes is not Directory? Please add a comment to clarify.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The DirectoryInfo constructor will succeed if the given path does not exist or if it actually refers to a file. In the former case the Exists property will be false, in the latter the Attributes property will lack the Directory attribute.

The myriad other ways the constructor will fail are explicitly called out in the various catch blocks.

@@ -246,6 +246,171 @@ Describe "Basic FileSystem Provider Tests" -Tags "CI" {
}
}

Describe "Hard link and symbolic link tests" -Tags "CI", "RequireAdminOnWindows" {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Your description mentions that the -Recurse parameter switch was ignored. But I don't see any tests to verify that it is fixed.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test using the -Recurse parameter when removing a symlink to a directory

$childB = Get-ChildItem folder
$childB.Count | Should Be 1
$childB.Count -eq $childA.Count | Should Be $true
$childB.Name -eq $childA.Name | Should Be $true
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Please use common template:

$childB.Count | Should BeExactly $childA.Count
$childB.Name  | Should BeExactly $childA.Name 

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed

New-Item -ItemType File -Path $file -Value "some content" >$null
New-Item -ItemType SymbolicLink -Path $link -value $folder >$null
$childA = Get-Childitem $folder
Remove-Item -Path $link -Recurse
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Should we use -Force and -ErrorAction SilentlyContinue or maybe -ErrorAction Continue?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Not quite clear on this one. This test shows that when we use -Recurse when deleting a symlink, it is ignored. Remove-Item should not fail in this circumstance, it should just remove the symlink without even trying to recurse into the linked-to directory.

Test-Path $hardLinkToFile | Should Be $true
$link = Get-Item -Path $hardLinkToFile
$link.LinkType | Should Be "HardLink"
Get-Content -Path $hardLinkToFile | Should be $fileContent
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would prefer BeExactly for strings in all test in the file.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

# New-Item on Windows will not create a "plain" symlink to a directory
$unixTestCases = @(
@{
Name = "Remove-Item can remove a symbolic link to a directory"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Plaese add "on Unix" in titles.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

# Junctions and directory symbolic links are Windows and NTFS only
$windowsTestCases = @(
@{
Name = "Remove-Item can remove a symbolic link to a directory"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Plaese add "on Windows" in titles.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Fixed.

@jeffbi
Copy link
Contributor Author
jeffbi commented Apr 27, 2017

@PaulHigin @iSazonov Can I get an updated review, please?

Copy link
Contributor
@PaulHigin PaulHigin left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

LGTM

9E88

@daxian-dbw
Copy link
Member

@jeffbi The tests are beautiful. Thanks!

@daxian-dbw daxian-dbw merged commit f1769fe into PowerShell:master Apr 28, 2017
@daxian-dbw
Copy link
Member

Thanks @iSazonov and @PaulHigin for the review!

@iSazonov
Copy link
Collaborator

@jeffbi Great work! Thanks!

Target = $realDir
}
@{
Name = "Remove-Item can remove a junction to a directory"
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

"on Windows" skipped 😄

@jeffbi jeffbi deleted the remove-item-621 branch May 8, 2017 05:05
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

Fix Remove-Item <symbolic link to directory>
5 participants
0