这个报错在 3 月 8 号 setuptools 发布新版本之后出现,通常会在安装 Python 依赖时触发。
报错信息
使用 pip 安装依赖时的报错如下:
Collecting markupsafe==1.0 Downloading https://.../MarkupSafe-1.0.tar.gz (14 kB) ERROR: Command errored out with exit status 1: command: '...\python.exe' -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'...\\pip-install-bsormril\\markupsafe\\setup.py'"'"'; __file__='"'"'...\\pip-install-bsormril\\markupsafe\\setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' egg_info --egg-base '...\pip-install-bsormril\markupsafe\pip-egg-info' cwd: ...\pip-install-bsormril\markupsafe\ Complete output (5 lines): Traceback (most recent call last): File "<string>", line 1, in <module> File "...\pip-install-bsormril\markupsafe\setup.py", line 6, in <module> from setuptools import setup, Extension, Feature ImportError: cannot import name 'Feature' ---------------------------------------- ERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.
使用 Pipenv 安装依赖时的报错如下:
An error occurred while installing markupsafe==1.0 --hash=sha256:a6be69091dac236ea9c6bc7d012beab42010fa914c459791d627dad4910eb665! Will try again. Installing initially failed dependencies… [pipenv.exceptions.InstallError]: File "...\Python\Python36\site-packages\pipenv\core.py", line 1874, in do_install [pipenv.exceptions.InstallError]: keep_outdated=keep_outdated [pipenv.exceptions.InstallError]: File "...Python\Python36\site-packages\pipenv\core.py", line 1253, in do_init [pipenv.exceptions.InstallError]: pypi_mirror=pypi_mirror, [pipenv.exceptions.InstallError]: File "...\Python\Python36\site-packages\pipenv\core.py", line 859, in do_install_dependencies [pipenv.exceptions.InstallError]: retry_list, procs, failed_deps_queue, requirements_dir, **install_kwargs [pipenv.exceptions.InstallError]: File "...\Python\Python36\site-packages\pipenv\core.py", line 763, in batch_install [pipenv.exceptions.InstallError]: _cleanup_procs(procs, not blocking, failed_deps_queue, retry=retry) [pipenv.exceptions.InstallError]: File "...\Python\Python36\site-packages\pipenv\core.py", line 681, in _cleanup_procs [pipenv.exceptions.InstallError]: raise exceptions.InstallError(c.dep.name, extra=err_lines) [pipenv.exceptions.InstallError]: ['Looking in indexes: https://.../pypi/simple', 'Collecting markupsafe==1.0', ' Using cached https://.../MarkupSafe-1.0.tar.gz (14 kB)'] [pipenv.exceptions.InstallError]: ['ERROR: Command errored out with exit status 1:', ' command: \'...\\.virtualenvs\\helloflask-evdb6idn\\scripts\\python.exe\' -c \'import sys, setuptools, tokenize; sys.argv[0] = \'"\'"\'...\pip-install-pkgojp4t\\\\markupsafe\\\\setup.py\'"\'"\'; __file__=\'"\'"\'...\\\\pip-install-pkgojp4t\\\\markupsafe\\\\setup.py\'"\'"\';f=getattr(tokenize, \'"\'"\'open\'"\'"\', open)(__file__);code=f.read().replace(\'"\'"\'\\r\\n\'"\'"\', \'"\'"\'\\n\'"\'"\');f.close();exec(compile(code, __file__, \'"\'"\'exec\'"\'"\'))\' egg_info --egg-base \'...\\pip-install-pkgojp4t\\markupsafe\\pip-egg-info\'', ' cwd: ...\\pip-install-pkgojp4t\\markupsafe\\', ' Complete output (5 lines):', ' Traceback (most recent call last):', ' File "<string>", line 1, in <module>', ' File "...\\pip-install-pkgojp4t\\markupsafe\\setup.py", line 6, in <module>', ' from setuptools import setup, Extension, Feature', " ImportError: cannot import name 'Feature'", '----------------------------------------', 'ERROR: Command errored out with exit status 1: python setup.py egg_info Check the logs for full command output.'] ERROR: ERROR: Package installation failed...
其他工具输出类似,主要异常信息是 MarkupSafe setup.py: ImportError: cannot import name Feature。通常会在安装 Flask 项目的依赖时发生,因为 MarkupSafe 是 Flask 的依赖之一。
原因和解决方法
出现这个报错的原因是因为 Python 打包工具 setuptools 在 46.0.0 版本删掉了弃用的 Feature
,而 MarkupSafe 刚好在 setup.py 文件里导入了这个类,所以会出现报错。
解决方法很多,最直接的是更新 MarkupSafe 到最新版本(1.1.1),新版本去掉了对 Feature 类的导入。如果使用 requirements.txt 存储依赖列表,那就把 MarkupSafe 的版本号改成 1.1.1(找到 MarkupSafe 开头那一行,替换版本号):
MarkupSafe==1.1.1
然后重新执行:
$ pip install -r requirements.txt
对于 Pipenv,可以直接执行:
$ pipenv install markupsafe==1.1.1
如果你是《Flask Web 开发实战》的读者,正在为第一部分的示例程序安装依赖,那你还需要执行下面的命令固定 sendgrid-python 的版本(它在新版本添加了不向后兼容的 API 变动):
$ pipenv install sendgrid==5.3.0
《Flask Web 开发实战》读者备注
如果你在 2020 年 3 月 8 号到 4 月 5 号之间买了《Flask Web 开发实战》,把示例程序克隆到了本地,然后尝试运行 pipenv install 或 pip install -r requirements.txt 命令来安装依赖,那很大概率你会遇到这个问题。
除了使用上面的方法之外,你还可以通过更新本地代码来解决。我最近给所有示例程序的依赖文件做了一次更新,除了书里涉及的 API 产生变动的依赖,其他依赖都已经更新到最新版本。
你可以使用下面的命令来更新你在本地的程序仓库(注意这会重置你对源码进行的修改):
$ git fetch --all $ git fetch --tags $ git reset --hard origin/master
然后重新执行一次 pipenv install 或 pip install -r requirements.txt 即可解决这个问题。如果遇到其他虚拟环境和依赖安装的问题可以参考这篇文章解决。
相关链接: