Pythonでコマンドラインツールを作りたいと思ったことはありませんか?
例えば、
- python app.py input.txt
- python app.py –mode fast
- python app.py –help
このような「引数付き実行」を扱うのがargparseです。
この記事では、
- sys.argvとの違い
- argparseの基本
- 実務で使えるCLI設計
- 小さなツールの完成
を解説します。
なぜ argparse を使うのか?(sys.argvとの違い)
まずは多くの人が最初に触れる sys.argv から見てみましょう。コマンドライン引数については以下の記事も参考にしてみてください。

import sys
print(sys.argv)これをapp.pyに書いて実行すると下のようになります。
# 実行コマンド
python app.py hello world
# 出力結果
['app.py', 'hello', 'world']
問題点
一見簡単に使えるのでこれで十分な気がしますが、実はかなり扱いにくいです。
具体的には、
- 型変換が必要
- 順番依存になる
- エラーメッセージが自分で必要
- –helpが作れない
具体的に見てみましょう。
①型変換が必要
例えば、年齢を受け取るコードを書いてみます。
import sys
age = sys.argv[1]
print(age + 10)実行します。
# 実行コマンド
python app.py 20
# 結果
TypeError: can only concatenate str (not "int") to str
TypeErrorが発生しました。原因は、引数で渡してる20は文字列型だからです。
なので、コードを次のように修正する必要があります。
age = int(sys.argv[1])
print(age + 10)このように毎回型変換を実施する必要があります。
②順番依存になる
次に、名前と年齢を受け取る場合を考えてみましょう。
import sys
name = sys.argv[1]
age = int(sys.argv[2])
print(f"{name} is {age} years old")これも実行してみます。
# 実行コマンド
python app.py 20 Taro
# 出力結果
ValueError: invalid literal for int()
引数の順番を間違えるとエラーになります。(順番がTaro 20ならOK)
③エラーメッセージを自分で書く必要がある
例えば下記のプログラムの実行時に引数が足りない場合を考えてみます。
name = sys.argv[1]
age = int(sys.argv[2])# 実行
python app.py Taro
# 出力結果
IndexError: list index out of range
これはユーザーにとっては意味不明なエラーです。
そのため次のようにコードを書く必要があります。
import sys
if len(sys.argv) < 3:
print("使い方: python app.py 名前 年齢")
sys.exit()
name = sys.argv[1]
age = int(sys.argv[2])毎回このようなコードを全てのエラーに対して実装するのは面倒です。
④–helpが作れない
例えば、こんなことをしたくなります。
python app.py --help
しかし、sys.argvでは特に何も起きません。
オプションを作る場合は全部実装する必要があります。
import sys
if "--help" in sys.argv:
print("使い方: python app.py 名前 年齢")
sys.exit()コードが分岐だらけになり可読性も下がります。
これらの問題を解決してくれるのがargparseです。
argparseの基本的な使い方
import argparse
parser = argparse.ArgumentParser()
parser.add_argument("name")
args = parser.parse_args()
print(args.name)実行してみます。
# 実行
python app.py Taro
# 結果
Taro
簡単に解説
- ArgumentParser() → CLIの設定を作る
- add_argument → 引数を定義する
- parse_args → 引数を解析してくれる
先ほど挙げたsys.argvの問題点をどう解決しているのか見てみましょう
① 型変換が不要
parser.add_argument("--age", type=int)このように書くことで自動的にint型に変換してくれます。
# 実行
python app.py --age abc
# 出力結果
error: argument --age: invalid int value: 'abc'
また、intに変換できない引数がきた場合などは、わかりやすいエラーを出してくれます。
②引数の順番は自動で解決
parser.add_argument("--name")
parser.add_argument("--age", type=int)このようなプログラムの場合、オプションごとに引数を設定するので順番を考える必要はありません。
またユーザーからしても、–ageのようにオプションを指定するため使い方が非常にわかりやすくなります。
# 実行
python app.py --age 20 --name Taro
python app.py --name Taro --age 20
③エラーメッセージは自動生成
sys.argvの場合には、
IndexError: list index out of range
のようなユーザー向けではないエラーメッセージが出ていました。
argparseを使うと、
parser.add_argument("name")
parser.add_argument("age", type=int)# 実行
python app.py Taro
# 結果
usage: app.py [-h] name age
app.py: error: the following arguments are required: age
このようにユーザーがどこが間違っているのか、何をすればいいのかがわかるメッセージが出力されます。
④–helpは自動で作られる
次のような–helpオプションが自動で作成されます。
usage: app.py [-h] name age
positional arguments:
name
age
options:
-h, --help show this help message and exit
argparseでよく使うオプション
次にargparseを利用する際によく使うオプションを紹介します。
choices(選択肢制限)
parser.add_argument("--mode", choices=["easy", "hard"])required(必須オプション)
実際に簡単なCLIツールを作成して理解を深めましょう。
要件
- 名前を受け取る
- 回数を指定して表示
- モードで挙動変更
コード
import argparse
def main():
parser = argparse.ArgumentParser(description="あいさつツール")
parser.add_argument("name", help="名前")
parser.add_argument("--count", type=int, default=1, help="回数")
parser.add_argument("--mode", choices=["normal", "shout"], default="normal")
args = parser.parse_args()
for _ in range(args.count):
if args.mode == "shout":
print(f"HELLO {args.name.upper()}!")
else:
print(f"Hello {args.name}")
if __name__ == "__main__":
main()実行例
# 実行
python app.py Taro --count 3 --mode shout
# 結果
HELLO TARO!
HELLO TARO!
HELLO TARO!
まとめ
この記事では、
- sys.argvとの違い
- argparseの基本
- 実践CLI作成
を解説しました。AIでなんでも作れる時代ですが、基礎を知ってる人がAIで作成したアプリと何も知らない人がAIで作ったアプリには明らかな差があります。
AIが出したコードを理解するためにも少しずつ基礎を学んでいきましょう!


コメント