🍱

Python おすすめライブラリ

2023/07/22に公開

Python開発時にとりあえず使うツール達まとめ

開発時にツール入れれば実質静的型付け言語になります。多分。

ロバストPythonで学んだことが多いのでお勧めします。
https://www.oreilly.co.jp/books/9784814400171/

poetry

パッケージマネージャーの1つ
pipenvと似てるぞ
大きくは変わらないがなんかオシャレなので使ってる

https://github.com/python-poetry/poetry

taskipy

タスクランナー
poetryのscriptsはタスクランナーとして使うものではないのでサードパーティのタスクランナーが必要になる。
taskipyは使いやすそうだったので使ってみたが良い感じです。
以下のような感じでフォーマットやテストなどをタスク登録しています。(無駄にdividerとか使ってます)

pyproject.toml
# 定義例
[tool.taskipy.tasks]
# divider
s = "echo && echo ------------------------------"
e = "echo ------------------------------"

# proto complie
proto_compile = "task s && echo Proto compile!!! 🚀 && task e && python -m grpc_tools.protoc -I ./protos --python_out=./ouranos/gen --pyi_out=./ouranos/gen --grpc_python_out=./ouranos/gen ./protos/profile.proto"
# black format
format = "task s && echo Format with black!!! 💰 && task e && black ."
# isort
isort = "task s && echo Sort with isort!!! 🎁 && task e && isort ."
# mypy
mypy = "task s && echo Type Check with mypy!!! 🌈 && task e && mypy --config-file mypy.ini ouranos tests"
# flake8
flake8 = "task s && echo Lint with flake8!!! 🐈 && task e && flake8 --exclude=./ouranos/gen/ ouranos tests"
# bandit
bandit = "task s && echo Security check with bandit!!! 🔑 && task e && bandit -r ouranos -f json -o ./bandit/result.json"
# test
tests = "task s && echo Test with pytest!!! 🤡 && task e && pytest -s -vv --cov=. --cov-branch --cov-report=html"
# all check
all_check = "task format && task isort && task mypy && task flake8 && task bandit && task tests"

実行結果(コマンド: task all_check)
※bandit以外
all_check

https://github.com/taskipy/taskipy

black

フォーマッター
これはautopep8でも好きなものを使えば良いと思うが
line-lengthだけ調整しています

pyproject.toml
[tool.black]
line-length = 79

https://github.com/psf/black

flake8

所謂リンター
pylinter等も有名だがこの辺も好きなものを使用すると良いかと思います

https://github.com/pycqa/flake8

mypy

型チェック用のライブラリ
これがあれば実質静的型付け言語です

以下のような感じで色々設定できます

pyproject.toml
[tool.mypy]
show_error_context = true
show_column_numbers = true
disallow_untyped_defs = true
no_implicit_optional = true
warn_return_any = true
warn_unused_ignores = true
warn_redundant_casts = true

https://github.com/python/mypy

isort

importの順番を並び替えてくれるやつ
なんか綺麗なので使ってる

https://pycqa.github.io/isort/

pytest

とりあえずテストはこいつ。
gRPCサーバのテストかけた

test_servicer.py
from concurrent import futures

import grpc
import pytest
from google.protobuf.empty_pb2 import Empty

from ouranos.gen import profile_pb2_grpc
from ouranos.servicer import ProfileServicer


@pytest.fixture(scope="module")
def grpc_server():
    """Start gRPC server"""
    server = grpc.server(futures.ThreadPoolExecutor(max_workers=10))
    profile_pb2_grpc.add_ProfileServicer_to_server(ProfileServicer(), server)
    server.add_insecure_port("[::]:5001")

    server.start()

    yield server

    server.stop(0)


def test_get_profile(grpc_server):  # NOQA
    """Test get profile"""
    with grpc.insecure_channel("localhost:5001") as channel:
        stub = profile_pb2_grpc.ProfileStub(channel)
        response = stub.get_profile(Empty())
        assert response.name == "yuya-morimoto"

bandit

コードのセキュリティチェックをしてくれる
jsonで吐き出したりコンソールに出すだけも可能

※proto compileで生成したコードも対象にとりあえず入れてるけど問題なさそう。

以下実行結果例

bandit.json
{
  "errors": [],
  "generated_at": "2023-07-22T11:43:55Z",
  "metrics": {
    "_totals": {
      "CONFIDENCE.HIGH": 0,
      "CONFIDENCE.LOW": 0,
      "CONFIDENCE.MEDIUM": 0,
      "CONFIDENCE.UNDEFINED": 0,
      "SEVERITY.HIGH": 0,
      "SEVERITY.LOW": 0,
      "SEVERITY.MEDIUM": 0,
      "SEVERITY.UNDEFINED": 0,
      "loc": 94,
      "nosec": 0,
      "skipped_tests": 0
    },
    "xxx/__init__.py": {
      "CONFIDENCE.HIGH": 0,
      "CONFIDENCE.LOW": 0,
      "CONFIDENCE.MEDIUM": 0,
      "CONFIDENCE.UNDEFINED": 0,
      "SEVERITY.HIGH": 0,
      "SEVERITY.LOW": 0,
      "SEVERITY.MEDIUM": 0,
      "SEVERITY.UNDEFINED": 0,
      "loc": 0,
      "nosec": 0,
      "skipped_tests": 0
    },
    "xxx/yyy/__init__.py": {
      "CONFIDENCE.HIGH": 0,
      "CONFIDENCE.LOW": 0,
      "CONFIDENCE.MEDIUM": 0,
      "CONFIDENCE.UNDEFINED": 0,
      "SEVERITY.HIGH": 0,
      "SEVERITY.LOW": 0,
      "SEVERITY.MEDIUM": 0,
      "SEVERITY.UNDEFINED": 0,
      "loc": 2,
      "nosec": 0,
      "skipped_tests": 0
    },
    "xxx/yyy/profile_pb2.py": {
      "CONFIDENCE.HIGH": 0,
      "CONFIDENCE.LOW": 0,
      "CONFIDENCE.MEDIUM": 0,
      "CONFIDENCE.UNDEFINED": 0,
      "SEVERITY.HIGH": 0,
      "SEVERITY.LOW": 0,
      "SEVERITY.MEDIUM": 0,
      "SEVERITY.UNDEFINED": 0,
      "loc": 17,
      "nosec": 0,
      "skipped_tests": 0
    },
    "xxx/yyy/profile_pb2_grpc.py": {
      "CONFIDENCE.HIGH": 0,
      "CONFIDENCE.LOW": 0,
      "CONFIDENCE.MEDIUM": 0,
      "CONFIDENCE.UNDEFINED": 0,
      "SEVERITY.HIGH": 0,
      "SEVERITY.LOW": 0,
      "SEVERITY.MEDIUM": 0,
      "SEVERITY.UNDEFINED": 0,
      "loc": 52,
      "nosec": 0,
      "skipped_tests": 0
    },
    "xxx/servicer.py": {
      "CONFIDENCE.HIGH": 0,
      "CONFIDENCE.LOW": 0,
      "CONFIDENCE.MEDIUM": 0,
      "CONFIDENCE.UNDEFINED": 0,
      "SEVERITY.HIGH": 0,
      "SEVERITY.LOW": 0,
      "SEVERITY.MEDIUM": 0,
      "SEVERITY.UNDEFINED": 0,
      "loc": 23,
      "nosec": 0,
      "skipped_tests": 0
    }
  },
  "results": []
}

https://github.com/PyCQA/bandit

その他

  • pre-commit
    • コミット前に前述したツールでチェックすることができる
  • pydantic
    • 実行時のバリデーションを行える
  • pipdeptree
    • パッケージの依存関係をtree上に表示してくれる

Discussion