本文的目的也是非常簡單:
寫一個Python命令行工具,並且發布到PIP上面.並且在這個過程中給出我自己的一些思考.
如何分解這個發布任務?
只需要進行如下的兩個步驟便可以:
1.寫好一個Python命令行工具.
2.發布它.
當然,這樣不夠細致.再細分一下.
1.寫好一個Python命令行工具
1.1.命令行的特點,以及Python的如何編寫命令行
1.2.如何組織代碼結構.
2.發布
2.1.注冊pypi賬戶
2.2.注冊在賬戶下面注冊Python包
2.3.上傳打包好的Python命令行工具.
3.完善代碼
1.寫好一個Python命令行工具
寫好一個命令行工具首先要知道命令行工具是什麼?
在我看來,命令行工具就是一種完成某種類型的任務的終端程序.
也就是基本上沒有什麼用戶界面的程序.
由於基本上沒有什麼用戶界面,所以導致單個命令行的交互能力及其低下.但這種低下的交互性對於一些固定工作而言,簡直就是最靈活的工具.只需要輸入一些命令便可以完成某種類型的工作.實在是方便的很.
所以,某種程度上,終端程序低交互的缺點反而成了優點.
1.1.Python的如何編寫一個簡單的命令行
對於Python和命令行交互,我們很容易想出一個比較方便的方案.
sys.argv就是這樣的嘛!
我們很容易這樣寫代碼.
1
python testargv.py thisisaargv1
甚至我們也可以這樣寫命令行,
1
python testargv.py thisisaargv1 -d -f 0
那麼,這樣寫的後果就是,不方便解析出(不是不能,是不方便) -d -f 0 以及 thisisaargv1.
不信的話,你解析一個下面場景的命令行試試,
1
2
3
4
# 用戶可能這樣輸入
danmu.fm -q 1 -v 2
danmu.fm -q 1 -v 2
# 當然,肯定還有漏寫啦,等等,你得需要轉類型,增加各種blablabla的描述吧,添加默認的參數值吧.
於是Python就提供了一個非常好用的模塊可以使用.叫做argparse.
上面的描述就變成了這個樣子
Python
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
import argparse
APP_DESC="""
這就是描述
"""
print(APP_DESC)
if len(sys.argv) == 1:
sys.argv.append('--help')
parser = argparse.ArgumentParser()
parser.add_argument('-q','--quality',type=int,default=0,help="download video quality : 1 for the standard-definition; 3 for the super-definition")
parser.add_argument('-v','--verbose', default=0,help="print more debuging information")
parser.add_argument('-s','--store',help="保存流媒體文件到指定位置")
parser.add_argument('-c','--config',default=0,help="讀取~/.danmu.fm配置,請~/.danmu.fm指定資料庫")
parser.add_argument('url',metavar='URL',nargs='+', help="zhubo page URL (*/)")
args = parser.parse_args()
# 獲取對應參數只需要args.quality,args.url之類.
url = (args.url)[0]
print(url)
#其他執行邏輯
保存為danmu.py
這樣就可以執行命令
1
python danmu.py -q 1 -v 2
通過args就可以獲取參數,然後進行終端程序的參數初始化.
可是這和我們的要求還是不同嘛,我們不想多寫Python XXX,我們想直接XXX.就像這樣.
1
danmu.fm -q 1 -v 2
不急,下面就是了.
1.2.如何組織代碼結構.
於是,現在就要開始組織代碼結構了.
我們在最終的代碼目錄大概是這樣的.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
danmu.fm
├── README.md
├── danmufm
│ ├── __init__.py
│ ├── client
│ │ ├── __init__.py
│ │ ├── __init__.pyc
│ │ ├── douyu_client.py
│ │ └── douyu_danmu_client.py
│ ├── danmu.py
│ ├── misc
│ │ ├── __init__.py
│ │ ├── color_printer.py
│ │ ├── downloaders.py
│ │ └── player.py
│ └── model
│ ├── __init__.py
│ └── douyu_msg.py
├── docs
├── setup.cfg
├── setup.py
├── sh.py
└── tests
這就是我上次寫的danmu.fm的代碼目錄.
聰明的你這時候你注意到了:
主要的程序不是放在根目錄下面,而是放在第二目錄danmufm下面.
2.setup.cfg 是什麼鬼東西
3.setup.py 是什麼鬼東西
對於上面幾點,我們分別進行解釋
1.2.1 為什麼主要程序在第二目錄下
為了把主要的程序分離出來,放在第二目錄下面,這樣的待會打包以後多出很多文件夾就不會對源碼造成干擾.
當然,由於把程序放在了第二目錄下面,所以,腳本裡面的from import語句應該使用相對路徑導入.
相對路徑導入的的時候需要注意運行的時候使用如下命令
1
python3 -m danmufm.danmu [xxxx]
1.2.2 setup.cfg
填寫如下內容即可.
1
2
[metadata]
description-file = README.md
然後去寫Markdown的Readme就好了.
1.2.3 setup.py
這個是重頭戲了.
setup這個py文件就是打包配置文件.對這個程序是誰的,有什麼依賴,入口是什麼,等等等等的配置.
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
#-*- encoding: UTF-8 -*-
from setuptools import setup, find_packages
"""
打包的用的setup必須引入,
"""
VERSION = '0.1.1'
setup(name='danmu.fm',
version=VERSION,
description="a tiny and smart cli player of douyutv,ximalayad,anmu based on Python",
long_description='just enjoy',
classifiers=[], # Get strings from ?%3Aaction=list_classifiers
keywords='python douyu danmu danmu.fm terminal',
author='twocucao',
author_email='[email protected]',
url='',
license='MIT',
packages=find_packages(),
include_package_data=True,
zip_safe=True,
install_requires=[
'requests',
],
entry_points={
'console_scripts':[
'danmu.fm = danmufm.danmu:main'
]
},
)
官方有distutils這個包管理器工具,設置也非常的簡單,只是,它不支持entry_points屬性,由於無法使用entry_point,也就無法通過命令來跳轉到指定模塊運行程序,這也就意味著,官方工具不方便寫成命令行.還是setuptools好.
上面需要注意的就是install_requires可以添加依賴.其他的你猜都可以猜出來是做什麼的.自己去看代碼,我就不多說了.
2.發布
所謂的發布,就是將打包好的程序的某個版本發布到某個倉庫中.
2.1.注冊pypi賬戶
到這個上面注冊賬號:
2.2.注冊在賬戶下面注冊Python包
進入對應項目根文件,然後執行
1
python3 setup.py register
這一步程序會讓你輸入剛剛注冊的賬號和密碼,然後注冊該包.注冊該包以後,你就有了一個小倉庫.可以存放不同版本的danmu.fm.
注冊的倉庫是可以在這個地址看到的,
2.3.上傳打包好的Python命令行工具.
這里需要藉助一個小工具,twine.twine是一個更加安全方便上傳打包好的代碼的工具.
1
pip3 install twine
接著開始打包,打包成兩個版本,一個是不需要build的版本,另一個是需要build的版本(順帶吐槽下,這兩個詭異的命名).
1
python setup.py sdist bdist_wheel
於是剩下來的就顯而易見了,上傳build完畢的程序到倉庫中.
1
twine upload dist/danmu.fm-0.1.2*
於是,安裝一下,測試是否成功
1
pip3 install danmu.fm --upgrade
命令行的工具是這樣使用的.
1
danmu.fm -q 2 -v 1
3.完善
不斷的完善代碼,然後打包終端程序發布到倉庫給別人用,這就是整個的PIP打包發布流程.
這個時候,你可能需要使用版本控制軟體.
你可能需要增多的代碼的測試.
⑵ 如何將自己的Python代碼打包發布到pypi上
什麼是pypi
簡單的說pypi是一個python包的倉庫,裡面有很多別人寫好的python庫,你可以通過easy_install或者pip進行安裝,方便用戶更方面的使用你的代碼模塊。
將代碼打包並上傳到pypi上,大體上分為以下幾步:
1、整理代碼的目錄結構,方便打包和python的import,為了方便引用,需要將代碼模塊變成一個包,所以需要將功能代碼用目錄來整合方便引用,並且需要創建__init__文件,__init__中可以沒有內容,也可以在__init__文件中進行import(from .extractor import Document)操作,以減少整體模塊引用時import的層數,避免錯誤。
[html]viewplain
├──./tidypage
│├──./tidypage/cleaners.py
│├──./tidypage/extractor.py
│├──./tidypage/__init__.py
│└──./tidypage/titles.py
2、功能模塊的目錄整理好後,就可以開始整理和添加發布到pypi上所使用的文件了
tidy_page
├──LICENSE
├──README.rst
├──requirements.txt
├──setup.py
├──tidypage
│├──cleaners.py
│├──extractor.py
│├──__init__.py
│└──titles.py
就是將原來的目錄深移一層,文件夾名稱可以根據自己意願。然後在到第一層的目錄下創建些特殊文件,具體你可以看看下面這個文件結構你就明白了
LICENSE文件是授權文件,比如:MIT license, APACHElicense
README.rst 文件想必大家都不陌生,其實就是項目介紹和使用說明
setup文件才是重點,是python模塊安裝所需要的文件,它的格式如下:
#!/usr/bin/envpython
from__future__importprint_function
fromsetuptoolsimportsetup,find_packages
importsys
setup(
name="tidy-page",
version="0.1.1",
author="DesionWang",
author_email="[email protected]",
description="htmltextparser,getthecontentformhtmlpage",
long_description=open("README.rst").read(),
license="MIT",
url="https://github.com/desion/tidy_page",
packages=['tidypage'],
install_requires=[
"beautifulsoup4",
lxml_requirement
],
classifiers=[
"Environment::WebEnvironment",
"IntendedAudience::Developers",
"OperatingSystem::OSIndependent",
"Topic::TextProcessing::Indexing",
"Topic::Utilities",
"Topic::Internet",
"Topic::SoftwareDevelopment::Libraries::PythonMoles",
"ProgrammingLanguage::Python",
"ProgrammingLanguage::Python::2",
"ProgrammingLanguage::Python::2.6",
"ProgrammingLanguage::Python::2.7",
],
)
文中的classifiers的內容並不是隨便填寫的,你需要參照本文參考文檔中的PyPI Classifiers來寫
3、開始使用Distutils進行打包
為了保證效果,在打包之前我們可以驗證setup.py的正確性,執行下面的代碼
python setup.py check
輸出一般是running check如果有錯誤或者警告,就會在此之後顯示沒有任何顯示表示Distutils認可你這個setup.py文件。
如果沒有問題,那麼就可以正式打包,執行下面的代碼:
python setup.py sdist
執行完成後,會在頂層目錄下生成dist目錄和egg目錄
tidy_page
├──tidy_page/dist
│├──tidy_page/dist/tidy-page-0.1.0.tar.gz
│└──tidy_page/dist/tidy-page-0.1.1.tar.gz
├──tidy_page/LICENSE
├──tidy_page/README.rst
├──tidy_page/setup.py
├──tidy_page/tidypage
│├──tidy_page/tidypage/cleaners.py
│├──tidy_page/tidypage/extractor.py
│├──tidy_page/tidypage/__init__.py
│└──tidy_page/tidypage/titles.py
├──tidy_page/tidy_page.egg-info
│├──tidy_page/tidy_page.egg-info/dependency_links.txt
│├──tidy_page/tidy_page.egg-info/PKG-INFO
│├──tidy_page/tidy_page.egg-info/requires.txt
│├──tidy_page/tidy_page.egg-info/SOURCES.txt
│└──tidy_page/tidy_page.egg-info/top_level.txt
4、打包完成後就可以准備將打包好的模塊上傳到pypi了,首先你需要在pypi上進行注冊gotoPyPI Live
注冊完成後,你需要在本地創建好pypi的配置文件,不然有可能會出現使用http無法上傳到pypi的問題
Create a.pypircconfiguration file,在用戶的home目錄下創建.pypirc文件,文件的內容如下
[distutils]index-servers=pypi[pypi]repository=https://pypi.python.org/pypiusername=your_usernamepassword=your_passwor
chmod600~/.pypirc
pythonsetup.pyregister-rpypi
在pypi上注冊模塊
python setup.py sdist upload -r pypi
上傳python文件包,沒有問題你就可以在pypi上看到你上傳的包了並且可以使用pip搜索和install你的python包了
⑶ python 程序怎麼打包發布
發布自己的python包
1. 首先先去PyPI注冊帳號
2. 配置~/.pypirc如下:
[distutils]
index-servers =
pypi
pypitest
[pypi]
username:ShaoZhengjiang
password:mypassword
[pypitest]
username:ShaoZhengjiang
password:mypassword
3. 然後注冊並上傳自己的包到測試伺服器
pypi提供了一個測試伺服器,我們可以在這個測試伺服器上做測試。
python setup.py register -r pypitest
然後
python setup.py sdist upload -r pypitest
若沒有問題我們應該不會得到任何錯誤。
4. 上傳至PyPI
若上面的測試成功,我們就可以按照相同的步驟將包注冊並上傳。
python setup.py register -r pypi
python setup.py sdist upload -r pypi
Ok,之後我們就可以在PyPI上看到我們自己的包了。(https://pypi.python.org/pypi/vaspy/)
⑷ python程序如何發布
pyinstaller
py2exe
cxFreeze