In Python, how can I get the correctly-cased path for a file?
This video explains
In Python, how can I get the correctly-cased path for a file?
--
Become part of the top 3% of the developers by applying to Toptal
https://topt.al/25cXVn
--
Music by Eric Matyas
https://www.soundimage.org
Track title: Ancient Construction
--
Chapters
00:00 Question
00:58 Accepted answer (Score 7)
01:13 Answer 2 (Score 13)
01:44 Answer 3 (Score 9)
01:59 Answer 4 (Score 9)
02:33 Thank you
--
Full question
https://stackoverflow.com/questions/3692...
--
Content licensed under CC BY-SA
https://meta.stackexchange.com/help/lice...
--
Tags
#python #windows #filenames
#avk47
In Python, how can I get the correctly-cased path for a file?
--
Become part of the top 3% of the developers by applying to Toptal
https://topt.al/25cXVn
--
Music by Eric Matyas
https://www.soundimage.org
Track title: Ancient Construction
--
Chapters
00:00 Question
00:58 Accepted answer (Score 7)
01:13 Answer 2 (Score 13)
01:44 Answer 3 (Score 9)
01:59 Answer 4 (Score 9)
02:33 Thank you
--
Full question
https://stackoverflow.com/questions/3692...
--
Content licensed under CC BY-SA
https://meta.stackexchange.com/help/lice...
--
Tags
#python #windows #filenames
#avk47
ANSWER 1
Score 13
Ned's GetLongPathName answer doesn't quite work (at least not for me). You need to call GetLongPathName on the return value of GetShortPathname. Using pywin32 for brevity (a ctypes solution would look similar to Ned's):
>>> win32api.GetLongPathName(win32api.GetShortPathName('stopservices.vbs'))
'StopServices.vbs'
ANSWER 2
Score 9
Ethan answer correct only file name, not subfolders names on the path. Here is my guess:
def get_actual_filename(name):
dirs = name.split('\\')
# disk letter
test_name = [dirs[0].upper()]
for d in dirs[1:]:
test_name += ["%s[%s]" % (d[:-1], d[-1])]
res = glob.glob('\\'.join(test_name))
if not res:
#File not found
return None
return res[0]
ANSWER 3
Score 9
This one unifies, shortens and fixes several approaches: Standard lib only; converts all path parts (except drive letter); relative or absolute paths; drive letter'ed or not; tolarant:
def casedpath(path):
r = glob.glob(re.sub(r'([^:/\\])(?=[/\\]|$)', r'[\1]', path))
return r and r[0] or path
And this one handles UNC paths in addition:
def casedpath_unc(path):
unc, p = os.path.splitunc(path)
r = glob.glob(unc + re.sub(r'([^:/\\])(?=[/\\]|$)', r'[\1]', p))
return r and r[0] or path
ANSWER 4
Score 7
This python-win32 thread has an answer that doesn't require third-party packages or walking the tree:
import ctypes
def getLongPathName(path):
buf = ctypes.create_unicode_buffer(260)
GetLongPathName = ctypes.windll.kernel32.GetLongPathNameW
rv = GetLongPathName(path, buf, 260)
if rv == 0 or rv > 260:
return path
else:
return buf.value