はじめに
ナイスゲーム!!👏👏👏 nikkieです。
今週のPyCoder's Weeklyから興味深かった記事に沿って手を動かしました。
未来は、意外と近くにある🤗
目次
- はじめに
- 目次
- 「Inline run dependencies in pipx 1.4.2」
- PEP 723 – Inline script metadata (Status: Accepted)
- pipxは(あくまで今は)dependenciesのみ限定サポート
- 終わりに
- P.S. pipxの「Found a space in the home path」
「Inline run dependencies in pipx 1.4.2」
PyPIをアプリストアのように使っちゃおう構想のpipx。
PyPIにあるCLIアプリケーションをpipxで環境を分けて管理できちゃいます(pipx install
)
(↑ macOSにpipxをインストールする手順も上の記事にあります)
記事「Inline run dependencies in pipx 1.4.2」ではpipx run
の新機能が取り上げられます1。
題材はこちらのスクリプト
# /// script # dependencies = ["rich"] # /// import rich rich.print("[blue]This worked!")
richはサードパーティライブラリです。
サードパーティライブラリを使うオススメ手順は、仮想環境2を切ってpip install rich
。
richをインストールせずにこのスクリプトは実行できません。
% python -V Python 3.10.9 % python ./print_blue.py Traceback (most recent call last): File "/..././print_blue.py", line 5, in <module> import rich ModuleNotFoundError: No module named 'rich'
richというライブラリが見つからずに落ちています。
で す が、pipx run
にスクリプトを渡すと、実行できちゃうんです!!3
% pipx run ./print_blue.py This worked!
青字で出力されています。
未来ずら〜〜
秘密を明かすと、このスクリプトの冒頭には# /// script
で始まるコメントで表したメタデータがあります。
pipxはそれを解釈して、richをインストールしてくれます。
richがある環境でスクリプトを流すので、実行できるのです。
ちなみに./print_blue.py
という渡し方ですが、pipxがPyPIにパッケージを探しに行かないようにするため、「カレントディレクトリのスクリプト」と指定するそうです。
Remember to include the ./ to ensure pipx run doesn’t try to find a PyPI package named print-blue-py
PEP 723 – Inline script metadata (Status: Accepted)
Abstractより
This PEP specifies a metadata format that can be embedded in single-file Python scripts (略)
(意訳)このPEPは、単一ファイルのPythonスクリプトに埋め込むメタデータの形式を具体的に示したもの
How to Teach Thisがキャッチアップしやすいです。
メタデータのフィールドは2つ
- dependencies
- requires-python
スクリプトの実行に必要な依存ライブラリと、実行するPython処理系のバージョンをメタデータとして記載できるわけですね。
Exampleのスクリプトをpipxで動かしましょう(内容としてはrichの例と同じです)
# /// script # requires-python = ">=3.11" # dependencies = [ # "requests<3", # "rich", # ] # /// import requests from rich.pretty import pprint resp = requests.get("https://peps.python.org/api/peps.json") data = resp.json() pprint([(k, v["title"]) for k, v in data.items()][:10])
% pipx run ./script.py [ │ ('1', 'PEP Purpose and Guidelines'), │ ('2', 'Procedure for Adding New Modules'), │ ('3', 'Guidelines for Handling Bug Reports'), │ ('4', 'Deprecation of Standard Modules'), │ ('5', 'Guidelines for Language Evolution'), │ ('6', 'Bug Fix Releases'), │ ('7', 'Style Guide for C Code'), │ ('8', 'Style Guide for Python Code'), │ ('9', 'Sample Plaintext PEP Template'), │ ('10', 'Voting Guidelines') ]
pipxは(あくまで今は)dependenciesのみ限定サポート
% pipx --version 1.5.0
今回取り上げた記事にもあるのですが、執筆時点のpipxのPEP 723 サポートはdependenciesのみと限定的です。
There’s also a requries-python field, which is currently ignored by pipx, (略) (原文ママ)
requires-python
が無視されるので、Exampleはpython3.104でもpipx run
できちゃいます。
% pipx run ./script.py --python=python3.10 [ │ ('1', 'PEP Purpose and Guidelines'), (略)
プルリクチャンスですね
終わりに
PEP 723のInline script metadataのdependenciesをサポートしたpipx(1.4.2以降)を触ってみました。
これはかなり便利な気がします。
パッケージまでいかないPythonスクリプトにこのメタデータ(コメント行)を書けば、他の人の環境でも高い再現度で動かせるわけです!
「Pythonってちょっとしたスクリプトが書きやすいな〜」と思っているのですが、このPEPはそこをさらに強化するという印象です。
PEPのTooling buy-inには、Hatchが挙がっています5。
興味を惹かれますね。
P.S. pipxの「Found a space in the home path」
この記事を書くにあたり1.5.0に上げて使ったところ、pipx側になにか変更が入ったのか、以下のメッセージが出ていました。
⚠️ Found a space in the home path. We heavily discourage this, due to multiple incompatibilities. Please check our docs for more information on this, as well as some pointers on how to migrate to a different home path.
discussionに沿ってre-installしたら解消しました(「How to fix」参照)