diff options
author | Tim Peters <tim.peters@gmail.com> | 2001-08-30 22:05:26 (GMT) |
---|---|---|
committer | Tim Peters <tim.peters@gmail.com> | 2001-08-30 22:05:26 (GMT) |
commit | 54a14a373e953365d6ca7c0d4e139563d07b52e7 (patch) | |
tree | 85a92957202cd5c2e977a0b562e290ef22a697c3 /Lib | |
parent | 0e03f588f513249fc6e43c94d30210f9d7558468 (diff) | |
download | cpython-54a14a373e953365d6ca7c0d4e139563d07b52e7.zip cpython-54a14a373e953365d6ca7c0d4e139563d07b52e7.tar.gz cpython-54a14a373e953365d6ca7c0d4e139563d07b52e7.tar.bz2 |
SF bug #456621: normpath on Win32 not collapsing c:\\..
I actually rewrote normpath quite a bit: it had no test cases, and as
soon as I starting writing some I found several cases that didn't make
sense.
Diffstat (limited to 'Lib')
-rw-r--r-- | Lib/ntpath.py | 19 | ||||
-rw-r--r-- | Lib/test/test_ntpath.py | 24 |
2 files changed, 35 insertions, 8 deletions
diff --git a/Lib/ntpath.py b/Lib/ntpath.py index 1be2961..d55cc7c 100644 --- a/Lib/ntpath.py +++ b/Lib/ntpath.py @@ -407,7 +407,7 @@ def expandvars(path): return res -# Normalize a path, e.g. A//B, A/./B and A/foo/../B all become A/B. +# Normalize a path, e.g. A//B, A/./B and A/foo/../B all become A\B. # Previously, this function also truncated pathnames to 8+3 format, # but as this module is called "ntpath", that's obviously wrong! @@ -421,15 +421,18 @@ def normpath(path): comps = path.split("\\") i = 0 while i < len(comps): - if comps[i] == '.': - del comps[i] - elif comps[i] == '..' and i > 0 and comps[i-1] not in ('', '..'): - del comps[i-1:i+1] - i = i - 1 - elif comps[i] == '' and i > 0 and comps[i-1] != '': + if comps[i] in ('.', ''): del comps[i] + elif comps[i] == '..': + if i > 0 and comps[i-1] != '..': + del comps[i-1:i+1] + i -= 1 + elif i == 0 and prefix.endswith("\\"): + del comps[i] + else: + i += 1 else: - i = i + 1 + i += 1 # If the path is now empty, substitute '.' if not prefix and not comps: comps.append('.') diff --git a/Lib/test/test_ntpath.py b/Lib/test/test_ntpath.py index fe997b3..049bbc1 100644 --- a/Lib/test/test_ntpath.py +++ b/Lib/test/test_ntpath.py @@ -74,6 +74,30 @@ tester("ntpath.join('c:', 'd:/')", 'd:/') tester("ntpath.join('c:/', 'd:/')", 'd:/') tester("ntpath.join('c:/', 'd:/a/b')", 'd:/a/b') +tester("ntpath.normpath('A//////././//.//B')", r'A\B') +tester("ntpath.normpath('A/./B')", r'A\B') +tester("ntpath.normpath('A/foo/../B')", r'A\B') +tester("ntpath.normpath('C:A//B')", r'C:A\B') +tester("ntpath.normpath('D:A/./B')", r'D:A\B') +tester("ntpath.normpath('e:A/foo/../B')", r'e:A\B') + +# Next 3 seem dubious, and especially the 3rd, but normpath is possibly +# trying to leave UNC paths alone without actually knowing anything about +# them. +tester("ntpath.normpath('C:///A//B')", r'C:\\\A\B') +tester("ntpath.normpath('D:///A/./B')", r'D:\\\A\B') +tester("ntpath.normpath('e:///A/foo/../B')", r'e:\\\A\B') + +tester("ntpath.normpath('..')", r'..') +tester("ntpath.normpath('.')", r'.') +tester("ntpath.normpath('')", r'.') +tester("ntpath.normpath('/')", '\\') +tester("ntpath.normpath('c:/')", 'c:\\') +tester("ntpath.normpath('/../.././..')", '\\') +tester("ntpath.normpath('c:/../../..')", 'c:\\') +tester("ntpath.normpath('../.././..')", r'..\..\..') +tester("ntpath.normpath('K:../.././..')", r'K:..\..\..') + if errors: raise TestFailed(str(errors) + " errors.") elif verbose: |