在 Heroku 上缺少 Python headers (Python.h)

Missing Python headers (Python.h) on Heroku

我正在尝试向 Heroku 部署一个需要一些 C 扩展的 Python 应用程序。问题是,当我通过 git push heroku master 将应用程序部署到 Heroku 时,出现以下错误:

Counting objects: 9, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (7/7), done.
Writing objects: 100% (9/9), 1.04 KiB | 534.00 KiB/s, done.
Total 9 (delta 3), reused 0 (delta 0)
remote: Compressing source files... done.
remote: Building source:
remote: 
remote: -----> Building on the Heroku-20 stack
remote: -----> Python app detected
remote:  !     Python has released a security update! Please consider upgrading to python-3.7.10
remote:        Learn More: https://devcenter.heroku.com/articles/python-runtimes
remote: -----> Requirements file has been changed, clearing cached dependencies
remote: -----> Installing python-3.7.9
remote: -----> Installing pip 20.1.1, setuptools 47.1.1 and wheel 0.34.2
remote: -----> Installing SQLite3
remote: -----> Installing requirements with pip
remote:        Obtaining file:///tmp/build_003b7c25 (from -r /tmp/build_003b7c25/requirements.txt (line 9))
remote:        Collecting click==7.1.2
remote:          Downloading click-7.1.2-py2.py3-none-any.whl (82 kB)
remote:        Collecting Flask==1.1.2
remote:          Downloading Flask-1.1.2-py2.py3-none-any.whl (94 kB)
remote:        Collecting gunicorn==20.0.4
remote:          Downloading gunicorn-20.0.4-py2.py3-none-any.whl (77 kB)
remote:        Collecting itsdangerous==1.1.0
remote:          Downloading itsdangerous-1.1.0-py2.py3-none-any.whl (16 kB)
remote:        Collecting Jinja2==2.11.2
remote:          Downloading Jinja2-2.11.2-py2.py3-none-any.whl (125 kB)
remote:        Collecting MarkupSafe==1.1.1
remote:          Downloading MarkupSafe-1.1.1-cp37-cp37m-manylinux2010_x86_64.whl (33 kB)
remote:        Collecting Werkzeug==1.0.1
remote:          Downloading Werkzeug-1.0.1-py2.py3-none-any.whl (298 kB)
remote:        Collecting youtube-dl==2020.12.14
remote:          Downloading youtube_dl-2020.12.14-py2.py3-none-any.whl (1.8 MB)
remote:        Installing collected packages: click, Werkzeug, MarkupSafe, Jinja2, itsdangerous, Flask, gunicorn, youtube-dl, c-rename
remote:          Running setup.py develop for c-rename
remote:            ERROR: Command errored out with exit status 1:
remote:             command: /app/.heroku/python/bin/python -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/tmp/build_003b7c25/setup.py'"'"'; __file__='"'"'/tmp/build_003b7c25/setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' develop --no-deps
remote:                 cwd: /tmp/build_003b7c25/
remote:            Complete output (20 lines):
remote:            running develop
remote:            running egg_info
remote:            creating c_rename.egg-info
remote:            writing c_rename.egg-info/PKG-INFO
remote:            writing dependency_links to c_rename.egg-info/dependency_links.txt
remote:            writing top-level names to c_rename.egg-info/top_level.txt
remote:            writing manifest file 'c_rename.egg-info/SOURCES.txt'
remote:            reading manifest file 'c_rename.egg-info/SOURCES.txt'
remote:            writing manifest file 'c_rename.egg-info/SOURCES.txt'
remote:            running build_ext
remote:            building 'c_rename' extension
remote:            creating build
remote:            creating build/temp.linux-x86_64-3.7
remote:            creating build/temp.linux-x86_64-3.7/c_extensions
remote:            gcc -pthread -Wno-unused-result -Wsign-compare -DNDEBUG -g -fwrapv -O3 -Wall -fPIC -I/app/.heroku/python/include/python3.7m -c c_extensions/rename.c -o build/temp.linux-x86_64-3.7/c_extensions/rename.o
remote:            c_extensions/rename.c:2:10: fatal error: python3.6m/Python.h: No such file or directory
remote:                2 | #include <python3.6m/Python.h>
remote:                  |          ^~~~~~~~~~~~~~~~~~~~~
remote:            compilation terminated.
remote:            error: command 'gcc' failed with exit status 1
remote:            ----------------------------------------
remote:        ERROR: Command errored out with exit status 1: /app/.heroku/python/bin/python -c 'import sys, setuptools, tokenize; sys.argv[0] = '"'"'/tmp/build_003b7c25/setup.py'"'"'; __file__='"'"'/tmp/build_003b7c25/setup.py'"'"';f=getattr(tokenize, '"'"'open'"'"', open)(__file__);code=f.read().replace('"'"'\r\n'"'"', '"'"'\n'"'"');f.close();exec(compile(code, __file__, '"'"'exec'"'"'))' develop --no-deps Check the logs for full command output.
remote:  !     Push rejected, failed to compile Python app.
remote: 
remote:  !     Push failed
remote: Verifying deploy...
remote: 
remote: !   Push rejected to free-music-web.
remote: 
To https://git.heroku.com/free-music-web.git
 ! [remote rejected] master -> master (pre-receive hook declined)
error: failed to push some refs to 'https://git.heroku.com/free-music-web.git'

据我所知,我缺少 Python.h header 文件,它是构建我的 C 扩展程序所必需的。 我已经试过了 apt install python-devpython-develpython3-dev 等等,但都产生相同的输出:

Reading package lists... Done
Building dependency tree       
Reading state information... Done
W: Not using locking for read only lock file /var/lib/dpkg/lock-frontend
W: Not using locking for read only lock file /var/lib/dpkg/lock
E: Unable to locate package python-dev

cat /etc/os-release的输出如下

NAME="Ubuntu"
VERSION="20.04.2 LTS (Focal Fossa)"
ID=ubuntu
ID_LIKE=debian
PRETTY_NAME="Ubuntu 20.04.2 LTS"
VERSION_ID="20.04"
HOME_URL="https://www.ubuntu.com/"
SUPPORT_URL="https://help.ubuntu.com/"
BUG_REPORT_URL="https://bugs.launchpad.net/ubuntu/"
PRIVACY_POLICY_URL="https://www.ubuntu.com/legal/terms-and-policies/privacy-policy"
VERSION_CODENAME=focal
UBUNTU_CODENAME=focal

现在,我该如何安装 python header? 提前致谢

#include <python3.6m/Python.h>

在我看来,这就像一个写得不好的 C 扩展,它被硬编码为只能在“Python 3.6 with PyMalloc”上工作。由于您使用的是 Python 3.7.9 路径显然不存在。

通常的做法是

#include <Python.h>

当 setuptools/distutils 构建模块时,它会适当地设置包含路径(您可以在输出中看到它是通过 -I/app/.heroku/python/include/python3.7m 完成的)。

就我个人而言,我对像这样对路径进行硬编码的任何 C 扩展持怀疑态度 - 这是一件很奇怪的事情,它不会让您对其余代码的质量抱有太大信心。也有可能此扩展仅经过测试或设计用于 Python 3.6,因此不能保证它可以在 Python 3.7 上运行(通常版本之间没有巨大的兼容性变化,但随后我们已经知道这个扩展作者做了一些奇怪的决定...)