pythonpip从pipfreeze的输出中找出基本需求

pythonpip从pipfreeze的输出中找出基本需求,python,pip,Python,Pip,我的朋友刚开始学习Python和Flask,缺少很多“最佳实践”,例如requirements.txt文件 他最近向我寻求帮助,为了使项目干净,我想建立一个CI服务(Travis),但我需要先解决这个文件 因为他最初没有requirements.txt,所以我能得到的所有信息都是他的import语句,以及他的pip freeze输出 由于无法区分项目的直接需求和其中一个包的间接需求,我想从列表中找出所有“顶级”包。“顶级包”是列表中其他包不需要的包。例如,requests需要urlib3,因此当

我的朋友刚开始学习Python和Flask,缺少很多“最佳实践”,例如
requirements.txt
文件

他最近向我寻求帮助,为了使项目干净,我想建立一个CI服务(Travis),但我需要先解决这个文件

因为他最初没有
requirements.txt
,所以我能得到的所有信息都是他的
import
语句,以及他的
pip freeze
输出

由于无法区分项目的直接需求和其中一个包的间接需求,我想从列表中找出所有“顶级”包。“顶级包”是列表中其他包不需要的包。例如,
requests
需要
urlib3
,因此当出现
requests
时,
urlib3
最好不要出现在最终结果中

有没有办法做到这一点


如果有人想帮助我处理这个特定实例,下面是
pip freeze
的输出:

apturl==0.5.2
arrow==0.12.1
asn1crypto==0.24.0
binaryornot==0.4.4
blinker==1.4
Bootstrap-Flask==1.0.9
Brlapi==0.6.6
certifi==2018.1.18
chardet==3.0.4
Click==7.0
colorama==0.3.7
command-not-found==0.3
configparser==3.5.0
cookiecutter==1.6.0
cryptography==2.1.4
cupshelpers==1.0
decorator==4.1.2
defer==1.0.6
distro-info==0.18
dominate==2.3.5
Flask==1.0.2
Flask-Bootstrap4==4.0.2
Flask-Login==0.4.1
Flask-Mail==0.9.1
Flask-Moment==0.6.0
Flask-SQLAlchemy==2.3.2
Flask-WTF==0.14.2
future==0.17.1
httpie==0.9.8
httplib2==0.9.2
idna==2.6
ipython==5.5.0
ipython-genutils==0.2.0
itsdangerous==1.1.0
Jinja2==2.10
jinja2-time==0.2.0
keyring==10.6.0
keyrings.alt==3.0
language-selector==0.1
launchpadlib==1.10.6
lazr.restfulclient==0.13.5
lazr.uri==1.0.3
louis==3.5.0
macaroonbakery==1.1.3
Mako==1.0.7
MarkupSafe==1.1.0
mysqlclient==1.3.14
netifaces==0.10.4
oauth==1.0.1
olefile==0.45.1
pexpect==4.2.1
pickleshare==0.7.4
Pillow==5.1.0
poyo==0.4.2
prompt-toolkit==1.0.15
protobuf==3.0.0
pycairo==1.16.2
pycrypto==2.6.1
pycups==1.9.73
Pygments==2.2.0
pygobject==3.26.1
pymacaroons==0.13.0
PyNaCl==1.1.2
pyRFC3339==1.0
python-apt==1.6.3
python-dateutil==2.7.5
python-debian==0.1.32
pytz==2018.3
pyxdg==0.25
PyYAML==3.12
reportlab==3.4.0
requests==2.18.4
requests-unixsocket==0.1.5
ruamel.yaml==0.15.34
SecretStorage==2.3.1
simplegeneric==0.8.1
simplejson==3.13.2
six==1.11.0
SQLAlchemy==1.2.14
system-service==0.3
systemd-python==234
traitlets==4.3.2
ubuntu-drivers-common==0.0.0
ufw==0.35
unattended-upgrades==0.1
urllib3==1.22
usb-creator==0.3.3
visitor==0.1.3
wadllib==1.3.2
wcwidth==0.1.7
Werkzeug==0.14.1
whichcraft==0.5.2
WTForms==2.2.1
xkit==0.0.0
zope.interface==4.3.2
下面是他告诉我的
import
语句,还有一个
pymysql

导入操作系统
从烧瓶进口*
从flask_引导导入引导
从零力矩导入力矩
来自flask_wtf进口FlaskForm
从wtforms导入*
从wtforms.validators导入*
从flask_sqlalchemy导入sqlalchemy
从电子邮件导入邮件、消息
从werkzeug.security导入生成密码散列,检查密码散列
从flask_login导入需要的登录、登录用户、登录刷新、登录url、登录管理器、UserMixin、注销用户

首先,我想建议使用pip的API,但建议仅将pip用作cmdline工具()。请注意,我成功地使用了它,我只是不公开代码(至少现在是这样)
这里有一个使用北大资源的方法

code.py:

#/usr/bin/env蟒蛇3
导入系统
导入操作系统
导入pkg_资源
def get_包装(reqs_file=“requirements_orig.txt”):
如果请求文件和os.path.isfile(请求文件):
ret=dict()
打开(需求文件)为f时:
对于f.readlines()中的项:
名称,版本=item.strip(“\n”).split(“=”)[:2]
ret[name]=版本,()
回程网
其他:
返回{
item.project_name:(item.version,用于pkg_resources.working_集中的项的tuple([dep.name for dep in item.requires()])
}
def打印包装数据(文本、包装信息):
打印({:s}\n大小:{:d}\n\n{:s}).format(文本,len(pkg_信息),“\n”.join([{:s}=={:s}.format(*item)表示pkg_信息中的项])
def main():
包装=获取包装(要求文件=无)
完整_pkg_info=[(名称,数据[0])表示名称,已排序的数据(pkgs.items())]
打印包装数据(完整列表,完整包装信息)
deps=set()
对于pkgs中的名称:
deps=deps.union(pkgs[name][1])
min_pkg_info=[(名称,数据[0])表示名称,如果名称不在deps中,则数据在排序(pkgs.items())中]
打印包装数据(“\n------最小列表------------”,最小包装信息)
如果名称=“\uuuuu main\uuuuuuuu”:
打印(“Python{:s}on{:s}\n.”格式(sys.version,sys.platform))
main()
输出

注释

  • (显而易见):为了获得pkg信息,需要安装该pkg。这就是为什么在我的示例中,我没有使用您的文件(我将其命名为requirements_orig.txt),而是使用安装在我的VEnv上的PKG
  • 如您所见,在我的例子中,pkg编号从133下降到37,我认为这是非常容易管理的(当然,可以进行更多过滤)
  • 我基于pkg名称是主键(唯一标识pkg)的假设创建了数据结构。如果这是错误的,代码将需要一些更改

<强>最终注释< /强>:如果你还想考虑你的模块的导入列表(如果可能的话,甚至要删除更多的PKG),你也可以尝试(我只在CMDLIN中使用它,但是从脚本中使用它应该是微不足道的)

你应该这样做:创建一个新的虚拟环境→ 通过
pip
→ 检查是否一切正常→ 使用
pip冻结
@klauds。是 啊作为一名经验丰富的Python开发人员,我尝试遵循这些良好实践。但问题是,我的朋友没有,现在是个问题,我不明白这个问题。为什么只需要顶级软件包?安装它们将自动安装其余的(它们所依赖的),因此列表中是否只包含顶层或全部似乎无关紧要。我错过了什么?@CristiFati是的。虽然安装最小列表确实会安装完整列表,但是将
pip freeze
的完整输出放在
requirements.txt
中不是一个好主意。因此,我想要一个最小且可维护的列表为基于导入的任何项目生成
requirements.txt
文件。确定。正如我在开始时所说的,这是一种“方式”,意味着也可以有其他方式(也许更好)。
(py_064_03.06.08_test0) e:\Work\Dev\StackOverflow\q054292236>"e:\Work\Dev\VEnvs\py_064_03.06.08_test0\Scripts\python.exe" code.py
Python 3.6.8 (tags/v3.6.8:3c6b436a57, Dec 24 2018, 00:16:47) [MSC v.1916 64 bit (AMD64)] on win32

----------FULL LIST----------
Size: 133

Babel==2.6.0
Click==7.0
Django==2.1.4
Flask==1.0.2
Jinja2==2.10
Keras==2.2.4
Keras-Applications==1.0.6
Keras-Preprocessing==1.0.5
Markdown==3.0.1
MarkupSafe==1.1.0
Pillow==5.3.0
PyQt5==5.9.2
PyQt5-sip==4.19.13
PyYAML==3.13
Pygments==2.3.1
QtAwesome==0.5.3
QtPy==1.5.2
Send2Trash==1.5.0
Sphinx==1.8.3
Werkzeug==0.14.1
absl-py==0.6.1
alabaster==0.7.12
asn1crypto==0.24.0
astor==0.7.1
astroid==2.1.0
backcall==0.1.0
bleach==3.0.2
certifi==2018.11.29
cffi==1.11.5
chardet==3.0.4
cloudpickle==0.6.1
colorama==0.4.1
cryptography==2.4.2
cycler==0.10.0
decorator==4.3.0
defusedxml==0.5.0
djangorestframework==3.9.0
docutils==0.14
entrypoints==0.2.3
fatiando==0.5
funcsigs==1.0.2
future==0.17.1
gast==0.2.0
grpcio==1.17.1
h5py==2.9.0
html5lib==1.0.1
idna==2.8
imagesize==1.1.0
ipaddr==2.2.0
ipykernel==5.1.0
ipython==7.2.0
ipython-genutils==0.2.0
ipywidgets==7.4.2
isort==4.3.4
itsdangerous==1.1.0
jedi==0.13.2
jsonschema==2.6.0
jupyter==1.0.0
jupyter-client==5.2.4
jupyter-console==6.0.0
jupyter-core==4.4.0
keyboard==0.13.2
keyring==17.1.1
kiwisolver==1.0.1
lazy-object-proxy==1.3.1
llvmlite==0.26.0
lxml==4.2.5
matplotlib==3.0.2
mccabe==0.6.1
mistune==0.8.4
nbconvert==5.4.0
nbformat==4.4.0
notebook==5.7.4
numba==0.41.0
numpy==1.15.4
numpydoc==0.8.0
opencv-python==3.4.4.19
packaging==18.0
pandas==0.23.4
pandocfilters==1.4.2
parso==0.3.1
patsy==0.5.1
pickleshare==0.7.5
pip==18.1
prometheus-client==0.5.0
prompt-toolkit==2.0.7
protobuf==3.6.1
psutil==5.4.8
pyOpenSSL==18.0.0
pycodestyle==2.4.0
pycparser==2.19
pycryptodome==3.7.2
pyflakes==2.0.0
pygame==1.9.4
pylint==2.2.2
pynput==1.4
pyparsing==2.3.0
python-dateutil==2.7.5
pytz==2018.7
pywin32==224
pywin32-ctypes==0.2.0
pywinpty==0.5.5
pyzmq==17.1.2
qtconsole==4.4.3
requests==2.21.0
rope==0.11.0
scapy==2.4.0
scipy==1.2.0
setuptools==40.6.3
sip==4.19.8
six==1.12.0
snowballstemmer==1.2.1
sphinxcontrib-websupport==1.1.0
spyder==3.3.2
spyder-kernels==0.3.0
statsmodels==0.9.0
tensorboard==1.12.1
tensorflow-gpu==1.12.0
tensorflow-tensorboard==1.5.1
termcolor==1.1.0
terminado==0.8.1
testpath==0.4.2
thrift==0.11.0
tornado==5.1.1
traitlets==4.3.2
typed-ast==1.1.1
urllib3==1.24.1
wcwidth==0.1.7
webencodings==0.5.1
wheel==0.32.3
widgetsnbextension==3.4.2
wrapt==1.10.11
xlrd==1.2.0

----------MINIMAL LIST----------
Size: 37

Babel==2.6.0
Click==7.0
Django==2.1.4
Flask==1.0.2
Keras==2.2.4
Keras-Applications==1.0.6
Keras-Preprocessing==1.0.5
Markdown==3.0.1
Pillow==5.3.0
PyQt5==5.9.2
PyQt5-sip==4.19.13
PyYAML==3.13
QtAwesome==0.5.3
QtPy==1.5.2
Sphinx==1.8.3
djangorestframework==3.9.0
fatiando==0.5
funcsigs==1.0.2
ipaddr==2.2.0
keyboard==0.13.2
lxml==4.2.5
opencv-python==3.4.4.19
pandas==0.23.4
patsy==0.5.1
pip==18.1
pyOpenSSL==18.0.0
pycryptodome==3.7.2
pygame==1.9.4
pynput==1.4
pywin32==224
scapy==2.4.0
spyder==3.3.2
statsmodels==0.9.0
tensorflow-gpu==1.12.0
tensorflow-tensorboard==1.5.1
thrift==0.11.0
xlrd==1.2.0