Python and Windows Symbolic Links

Python, like many other popular OSS (Git anyone?), does not support symbolic links on Windows platforms , although they have been around since Windows Vista. Note, I am referring to actual symbolic links, not NTFS directory junctions or shortcuts.

I’m not really sure why is that. Maybe because they do not distinguish between different Windows revisions?

My current approach is to use the OS commands to create/delete symlinks. It’s not very elegant but it works without compatibility issues, unlike other solutions (calling win32 api through DLLs, manipulating file attributes, and other stuff you find in StackOverflow or tech blogs)

For example, to create a symbolic link of directories, one can use:

 child = subprocess.Popen(['MKLINK', '/D', link, target], stdout = subprocess.PIPE, stderr = subprocess.STDOUT, shell = True)
 streamdata = child.communicate()[0]

And check child.returncode for the result (and the output – stdout and stderr combined – available in the streamdata variable)

To remove a symbolic link to a directory, use the windows RMDIR command (os.rmdir or os.unlink won’t work)

 

Advertisements

cmd /c doesn’t like quotes

I was quite baffled at first.

This works:

cmd /c "C:\Program Files\7-Zip\7z.exe" C:\Temp\MyFile.7z

But this fails:

cmd /c "C:\Program Files\7-Zip\7z.exe" "C:\Temp\My Other File.7z"
'C:\Program' is not recognized as an internal or external command, operable program or batch file.

Turns out it’s an issue as old as Windows 2000.

The solution is to add another pair of quotes around the entire command:

cmd /c ""C:\Program Files\7-Zip\7z.exe" "C:\Temp\My Other File.7z""

Thank you, Microsoft.