我正在制作一个 python 桌面应用程序,它将日志作为 .csv 文件保存在 Windows 上用户的文档文件夹中。该应用程序是用 python 2.7 和 kivy 1.8.0 编写的,使用 pyinstaller 2.1 打包为 Windows 程序,并使用 Inno Setup Compiler 制作安装程序。在这篇文章中,我将用 USER 替换用户的真实姓名。
我有以下几行代码:
DOCUMENTS = os.path.expanduser('~\\Documents\\')
print DOCUMENTS
with open(DOCUMENTS + 'data_log.csv', 'ab') as f:
do stuff
在我的计算机和我测试过的另一台计算机上,该程序按预期运行。 DOCUMENTS 的计算结果为“C:\Users\USER\Documents\”。但是,在我尝试过的其他三台计算机上,DOCUMENTS 的计算结果为“C:\Users\USER\AppData\Roaming\SPB_16.6\Documents\”。然后,程序在尝试创建 data_log.csv 时崩溃,并出现以下错误:
IOError: [Errno 2] No such file or directory: 'C:\\Users\\USER\\AppData\Roaming\\SPB_16.6\\Documents\\data_log.csv'
首先,为什么 os.path.expanduser 在某些系统上可能行为不当,而在其他系统上则不然?
其次,即使它位于错误的目录中,如果文件不存在,open() 也应该创建该文件,那么为什么会导致它崩溃呢?
我已经弄清楚是什么导致了这个问题。在大多数系统上,HOME 为 None,因此 os.path.expanduser 使用 USERPROFILE 代替。但是,在极少数情况下,HOME 设置为 C:\SPB\ 或 C:\Users\USER\AppData\Roaming\SPB_16.6 之类的内容。我的解决方案是使用 os.environ 直接访问 USERPROFILE,而不是使用 os.path.expanduser。
从文档expanduser
:
在 Windows 上,如果设置了 HOME 和 USERPROFILE 将被使用,否则会出现
将使用 HOMEPATH 和 HOMEDRIVE 的组合。初始〜用户
通过从创建的目录中剥离最后一个目录组件来处理
上面导出的用户路径。
正如你所看到的,代码非常简单(用inspect
):
def expanduser(path):
"""Expand ~ and ~user constructs.
If user or $HOME is unknown, do nothing."""
if path[:1] != '~':
return path
i, n = 1, len(path)
while i < n and path[i] not in '/\\':
i = i + 1
if 'HOME' in os.environ:
userhome = os.environ['HOME']
elif 'USERPROFILE' in os.environ:
userhome = os.environ['USERPROFILE']
elif not 'HOMEPATH' in os.environ:
return path
else:
try:
drive = os.environ['HOMEDRIVE']
except KeyError:
drive = ''
userhome = join(drive, os.environ['HOMEPATH'])
if i != 1: #~user
userhome = join(dirname(userhome), path[1:i])
return userhome + path[i:]
没有太多可能出错的地方expanduser
本身。您需要检查程序中的这些环境变量,看看它们是否包含正确的值。
import os
for var in ('HOME', 'USERPROFILE', 'HOMEPATH', 'HOMEDRIVE'):
print os.environ.get(var)
一个可能的原因open
失败的原因可能是您尝试打开文件的目录不存在,或者您没有访问该文件的权限。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)