🦁

Python の型チェックを VSCode 上で行いたい

2023/03/29に公開

https://marketplace.visualstudio.com/items?itemName=ms-python.mypy-type-checker

※以下は内容が古くなっています。上記のプラグインを利用した方がいいと思います。

型を明示することの重要性

ロバストPython を読みました。

https://amzn.to/40NzY65

やはり型注釈が果たす文書化の役目はコードの可読性に大きく寄与するなと改めて思いました。
例えば、静的型付けでは、型の不整合がある場合は、実行時ではなくコンパイル時に警告を受けられることがあります。

Python は動的型付け言語に分類されますが、静的解析による型エラーの指摘は受けられます。
具体的には mypy を使います。

$ mypy main.py          
main.py:3: error: Incompatible types in assignment (expression has type "str", variable has type "int")  [assignment]
Found 1 error in 1 file (checked 1 source file)

とはいえ、上記のようなコマンドを逐一実行するのはめんどくさいので、IDE上(ここでは VSCode) でコーディングしているときにはリアルタイムに型チェックを行ってほしいものです。
わかりやすくいうと TypeScript のコードを VSCode で書いているときと同じような開発者体験を Python でも得たいです。

ただ、現状この記事で用いる Python 拡張機能は、ファイル保存時に mypy を実行することで型チェックを行うようになっていて、リアルタイムでチェックはできないようです。
Pylance はリアルタイム対応しているらしいですが、mypy とは別の独自の型チェッカーで解析されてしまうのでここでは扱わないことにします。

※ これらに関してはもし事実誤認だったら教えてください

したがって、この記事ではVSCode上でファイル保存時に自動的に mypy による型チェックを行うことをゴールにします。

mypy と VSCode による型チェックの実現

この記事では mypy と VSCode の統合により、前章の要求を実現する手順を示します。
動作確認環境は以下です。

言語・ライブラリなど バージョン
Mac M2チップ macOS Ventura 13.2
python 3.11.1
VSCode 1.76.2
VSCode Python 拡張機能 2023.4.1
mypy 1.1.1

初期状態の確認

まず適当にテスト用のプロジェクトを作っておきます。

$ cd /path/to/somewhere/work-dir
$ mkdir exam-mypy-vscode
$ cd exam-mypy-vscode
$ python -m venv venv
$ source venv/bin/activate
$ touch main.py
$ open . -a Visual\ Studio\ Code.app

この状態では a: intint の部分は、実行時に何も影響しません。
int を型注釈としてつけた a という変数に文字列を代入しても、VSCode上で警告は表示されませんし、コードの実行もできてしまいます。

if __name__ == '__main__':
  a: int = 5
  a = "string"
  print(a)

$ python main.py
string

mypy を実行すれば、型チェックが行えます。

$ mypy main.py          
main.py:3: error: Incompatible types in assignment (expression has type "str", variable has type "int")  [assignment]
Found 1 error in 1 file (checked 1 source file)

これが初期状態になります。

ファイル保存時に型エラーが表示されるようにする

mypy をインストールします。

$ pip install mypy

VSCodeの"Python"拡張機能をインストールします。
拡張機能のメニューから Marketplace 検索を行い、"python" っていうキーワードを入れるとすぐに見つかると思います。
以下の記事に図解があります。

https://learn.microsoft.com/ja-jp/training/modules/python-install-vscode/5-exercise-install-python-extension?pivots=macos

VSCodeの設定ファイルを以下のように編集します。

{
  "python.defaultInterpreterPath": "venv/bin/python",
  "python.linting.mypyEnabled": true,
  "python.linting.mypyPath": "venv/bin/mypy"
}

すると、今度は VSCode 上で警告が表示されるようになったはずです。

ただし、これはファイル保存時に mypy が作動しているのでリアルタイムではありません。

設定ファイルを反映する

mypy では設定のためのディレクティブが色々用意されています。
ついでに、この段階で、設定ファイルを読むようにしておきます。

プロジェクトのルートに以下の内容で mypy.ini を作成します。

[mypy]
strict=True
warn_return_any=True
check_untyped_defs=True

VSCodeの設定ファイルを以下のように編集します。

{
  "python.defaultInterpreterPath": "venv/bin/python",
  "python.linting.mypyEnabled": true,
  "python.linting.mypyPath": "venv/bin/mypy",
  "python.linting.mypyArgs": ["--config-file=mypy.ini"]
}

さっき保存した設定に抵触するようなコードを書くと、警告が出るはずです。

def add(a, b):
    return a + b

def main():
    result = add(1, "2")

if __name__ == "__main__":
    main()

終わりに

エラーに気づくのは早ければ早いほうがいいのでできればファイル保存時ではなくてリアルタイムで型エラーを見れたほうがいいと思ってるんですが、そういった方法があるかはもう少し調べたいです。

Discussion