コマンドラインインターフェース

pip._internal.cli パッケージは、pipのコマンドラインインターフェースの処理と提供を担当しています。このパッケージは以下を処理します。

  • CLIオプションの定義と解析

  • オートコンプリート

  • さまざまなコマンドへのディスパッチ

  • プログレスバーやスピナーなどのユーティリティ

ドキュメントのこのセクションは現在執筆中です。pip開発者は、このドキュメントの完成にご協力いただける方を歓迎します。ご協力いただける方は、トラッキングIssueまでご連絡ください。

概要

ConfigOptionParser インスタンスは、トップレベルの引数を解析するための「メインパーサー」として使用されます。

Command は、コマンド固有の引数を解析するために、別の ConfigOptionParser インスタンスを使用します。

コマンド構造

このセクションでは、すべてのコマンドのクラスが継承するクラス階層を示します。

base_command.py は、ベースとなる Command クラスを定義します。他のすべてのコマンドは、直接的または間接的にこのクラスを継承します(このセクションの最後にあるコマンドツリーを参照してください)。

ConfigOptionParser を使用して(設定とCLIの「ブレンド」を参照)、このクラスは一般的なオプションを追加し、すべての他の特定のオプションが各コマンドのクラスで必要に応じて追加される cmd_opts グループをインスタンス化します。pip install コマンドの --dry-run のように、特定のオプションを定義するコマンドの場合、オプションは cmd_opts に追加する必要があります。これは、Command の初期化時に自動的に呼び出される add_options メソッドの仕事です。

ベースとなる Command には、以下のメソッドがあります。

class Command
main()

クラスのメインメソッド。常に呼び出されます(main.py の main を参照)。クラスの特定の run メソッドの呼び出しと、起こりうるエラーの処理を担当します。

run()

コマンドの実際のアクションが定義される抽象メソッド。

add_options()

クラスに追加のオプションを挿入するためのオプションのメソッド。 Command の初期化時に呼び出されます。

一部のコマンドには、より特殊な動作があります(たとえば、pip index を参照)。これらのコマンドは代わりに IndexGroupCommand から継承されます。これは、CommandSessionCommandMixin から継承して、対応するリクエストの pip セッションを構築します。

最後に、IndexGroupCommand から継承する RequirementCommand は、pip install のように、何らかの形式で要件を使用するコマンドのベースクラスです。

前のクラスに加えて、CommandSessionCommandMixin が継承する最後のミックスインクラス、CommandContextMixIn について言及する必要があります。これは、コマンドのコンテキストを担当します。

次のコマンドツリーでは、さまざまな pip コマンドに定義された階層を見ることができます。各コマンドは、継承元のベースクラスの下に定義されています。

Command
├─ cache, check, completion, configuration, debug, freeze, hash, help, inspect, show, search, uninstall
└─ IndexGroupCommand
├─ index, list
└─ RequirementCommand
└─ wheel, download, install

オプションの定義

共有オプションのセットは、cmdoptions.py モジュールで定義されています。これは、コマンドのヘルプを呼び出したとき、または pip index のヘルプメッセージを呼び出したときに表示される、一般的なオプションパッケージインデックスオプションのグループです。すべてのオプションは、呼び出されると optparse.Option インスタンスを返す関数の形で定義されています。一方、pip config設定オプション のような特定のオプションのグループは、各特定のコマンドファイルで定義されています(たとえば、configuration.py を参照)。

引数の解析

アプリケーションのメインエントリポイントは、main.py モジュールの main 関数で定義されています。この関数は、オートコンプリートparse_command 関数の呼び出し、および create_command によるサブプログラムの作成と実行を担当します。このプログラムで main メソッドが呼び出されます。

parse_command は、main_parser.py モジュールで定義されており、次の2つの関数を定義しています。

parse_command()

pip のプログラムの初期解析を担当する関数。メインパーサーを作成し(次の関数 create_main_parser を参照)、一般的なオプションと残りの引数を抽出します。たとえば、pip --timeout=5 install --user INITools を実行すると、['--timeout=5'] は一般的なオプションとして分割され、['install', '--user', 'INITools'] は残りの引数として分割されます。

このステップでは、プログラムはオプション --python--versionpip、または pip help を処理します。前のオプションが見つからない場合は、コマンド名と引数を抽出しようとします。

create_main_parser()

メインパーサーを作成します(プログラムの説明を表示するには、コンソールで pip と入力してください)。内部パーサー(ConfigOptionParser)は、一般的なオプショングループと、この時点で cmdoptions.py から取得したコマンドのリストを追加します。

初期パースが完了した後、create_command は、commands_dict 変数に格納された情報を使用して適切なコマンドを作成し、その main メソッドを呼び出す役割を担います (「コマンド構造」を参照)。

2回目の引数パースは、各特定のコマンド(ベースの Command クラスで定義)で、再び ConfigOptionParser を使用して実行されます。

引数アクセス

すべてのオプションと引数にアクセスするために、Command.run() は、オプションを optparse.Values として、引数を文字列のリストとして受け取ります ( Command.main() でパースされます)。ベースの Command クラスの内部メソッドは、特定のコマンドに対して parse_args が呼び出された後、これらの変数を渡す役割を担います。

設定とCLIの「ブレンド」

ベースの Command は、パース処理を担当するクラス ConfigOptionParser をインスタンス化します(親クラス optparse.OptionParser を介して)。その主な追加機能は以下の関数で構成されています。

class ConfigOptionParser(OptionParser)
get_default_values()

オプションパーサーのインスタンス化後にデフォルトを更新できるように、元のメソッドをオーバーライドします。

Configuration クラスを使用してデフォルトのオプションと引数をオーバーライドできます(詳細については、Configurationを参照してください)。これにより、環境変数や設定ファイルからの設定を含めることができます。

プログレスバーとスピナー

cli サブパッケージには、プログラムの状態を表示する役割を担う2つのモジュールがあります。

  • progress_bars.py

    このモジュールには、次の関数が含まれています。

    get_download_progress_renderer()

    ダウンロードの進捗状況をレンダリングするために、rich の機能を使用します。

    この関数(download.pyDownloader クラス内で使用)を使用すると、大きなパッケージに pip install を実行する際のダウンロードプロセスを監視できます。

  • spinner.py

    このモジュールの主な機能は次のとおりです。

    open_spinner()

    適切なタイプのスピナーを生成します。これは、subprocess.py モジュール内の call_subprocess 関数で使用され、ユーザーにプログラムが実行中であることを知らせます。

  • TODO: 癖 / 標準的な慣習 / 幅広いアイデア。(オプション定義でのリストの回避、特殊な場合分けされたオプション値の型など)

将来のリファクタリングのアイデア

  • オプション定義を、より宣言的で一貫性のある静的なデータ構造に変更し、現在の partial(Option, ...) 形式を置き換えます。

  • プログレスバーとスピナーを cli.ui サブパッケージに移動します。

  • すべての Command クラスを cli.commands サブパッケージに移動します(ベースクラスを含む)。