7

I have a Perl script that needs to delete a directory with all its contents. Sometimes this directory contains a junction point into another directory. If I rmtree() naively, the rmtree() call will also delete all the files inside the target folder of the junction. I'm looking for a way to not do that, and instead just remove the junction.

Non Perl solutions would also be appreciated.

brian d foy
  • 129,424
  • 31
  • 207
  • 592
Lucas Meijer
  • 4,424
  • 6
  • 36
  • 53

3 Answers3

6

I just typed "junction point" into Google and found my way to http://en.wikipedia.org/wiki/NTFS_junction_point

Command Prompt (cmd.exe)

  • The dir command in Windows 2000 or later recognizes junction points, displaying instead of in directory listings (use dir with the /A or /AL command-line switch).
  • Any commands that would normally affect files inside a normal directory will act the same here. Thus the command del myjunction should not be used — this will just delete all the files in the targeted directory.
  • The commands rmdir and move work fine with junctions, with the caveat that move won't let the junction move to another volume (as opposed to Windows Explorer, as mentioned above.)
  • The rmdir command is safe in that it only deletes the junction point, not the targeted files. Whilst walking through the directory with the command line interface, files can be deleted, but unlike explorer, directories can also be deleted (using rmdir /s dirname for example.)
  • Using the linkd command with the /d switch is a safe way to delete junction points.

From what I can see you can, for example, use dir and grep the output for <JUNCTION> or use the Windows rmdir. I think you can use either of these from Perl via system.

Community
  • 1
  • 1
4

To find out where are the reparse points (or "junction points", if you will):

dir /a:l /b > myjunctions.txt

Will show all reparse points in the current directory. You can add /s, but beware that reparse points inside reparse points will be listed as well.

Suppose myjunctions.txt contains the line x:\subdir\foo. To remove it, you issue

fsutil reparsepoint "x:\subdir\foo"

And voilá! Your junction point is gone, and the original directory is untouched!

Glenn Slayden
  • 17,543
  • 3
  • 114
  • 108
fernacolo
  • 7,012
  • 5
  • 40
  • 61
  • Warning: if you use the list obtained as shown here to remove the junctions (incidentally, the command `linkd "x:\subdir\foo" /D` works for this also) ***do not sort the listing*** or change its order in any way. The order as given ensures that bulk removal (such as is shown here) will not follow links into another volume or drive letter *first*, leading to unintended and possibly disastrous consequences. See my comment elsewhere on this page for details. – Glenn Slayden Mar 04 '17 at 07:59
3

FastCopy utility does this: http://ipmsg.org/tools/fastcopy.html.en

I am using this program for copying or deleting folders that may contain junctions as subfolders so that the junction targets remain untouched. The junction points are properly copied while copying, even when the target drive is different.

From the program's "Main Options" you need to go to "Shell Extension" section and enable it. After that you will have Fast Copy-s delete functionality available in the Explorer's right click menu.

Windows Explorer at least in Windows 7 Ultimate works also as wanted while deleting - junction targets remain intact. But copying folders that contain junctions as subfolders in Explorer still does not work as intended - it actually does something that I cannot yet perhaps quite entirely describe: the junction folders seem to be copied as normal folders, but their content is empty.

Roland Pihlakas
  • 4,246
  • 2
  • 43
  • 64
  • Beware moving a whole directory structure containing junctions to a different drive letter. When copy utilities move junctions, most will leave them pointing to the original directory **on the source volume**. In this case, any (putative) traversal of the new structure (i.e., starting from the new drive letter) will include substructure **from the original drive**, which is never desirable for the scenario here. It's a catastrophe if recursively deleting on the (intended) copy--even using the most well-behaved tools, since the error is already established at the time of the original copy. – Glenn Slayden Mar 04 '17 at 03:13
  • 1
    @GlennSlayden "Windows Explorer at least in Windows 7 Ultimate works also as wanted while deleting - junction targets remain intact." – Roland Pihlakas Mar 04 '17 at 07:19