はじめに
- 普段unit testで使っているpytestについて基本を調べてみました。
基本的な使い方
準備
-
pytest
をインストールしておく -
utils1.py
にはテストしたい関数、test_utils1.py
にはテストコードを準備した。
/
├── utils
│ ├── utils1.py
├── tests
│ ├── test_utils1.py
[utils1.py]
def add_func(x, y):
return x + y
[test_utils1.py]
import sys
sys.path.append("..")
from utils.utils1 import *
def test_add_func():
a = 1
b = 3
result = add_func(a, b)
assert result == a + b
assert type(result) == int
実行(1テスト)
-
test_utils1.py
では、add_funcの結果の値と型が合うかをテストする。 -
/tests
の階層でpytest
またはpytest test_utils1.py
を実行する。 -
pytest
で実行すると、階層にあるすべてのテストコードが実行される。
/tests ❯❯❯ pytest test_util1.py
========================= test session starts =========================
platform darwin -- Python 3.9.16, pytest-7.4.2, pluggy-1.3.0
rootdir: /Users/kodamakeita/python/genaral/0916/tests
collected 1 item
test_util1.py . [100%]
========================= 1 passed in 0.00s =========================
実行(1テスト) fail
-
test_utils1.py
を以下のように変えて失敗を起こしてみる。
def test_add_func():
a = 1
b = 3
result = add_func(a, b)
assert result == a + b +7
assert type(result) == int
/tests ❯❯❯ pytest test_util1.py
========================= test session starts =========================
platform darwin -- Python 3.9.16, pytest-7.4.2, pluggy-1.3.0
rootdir: /Users/kodamakeita/python/genaral/0916/tests
collected 1 item
test_util1.py F
========================= FAILURES =========================
_________________________ test_add_func _________________________
def test_add_func():
a = 1
b = 3
result = add_func(a, b)
> assert result == a + b +7
E assert 4 == ((1 + 3) + 7)
========================= short test summary info =========================
FAILED test_util1.py::test_add_func - assert 4 == ((1 + 3) + 7)
========================= 1 failed in 0.02s =========================
実行(3テスト)
- テストのファイルが複数あると以下のようになる。
/tests ❯❯❯ pytest
========================= test session starts =========================
platform darwin -- Python 3.9.16, pytest-7.4.2, pluggy-1.3.0
rootdir: /Users/kodamakeita/python/genaral/0916/tests
collected 3 items
test_util1.py . [ 33%]
test_util2.py . [ 66%]
test_util3.py . [100%]
========================= 3 passed in 0.06s =========================
mockを使ったテスト
- 例えば、requetsなど外部から結果を取得する関数のテストをしたいが、実際の通信が使えない(サーバを起動していないなどで)などの理由で、外部のモジュールとは切り分けてテストをしたい場合はmockを使う。
- mockとはハリボテ的なイメージです。
TBA
[request_module.py]
import requests
def get_username(id_num):
url = "http://xxxxxxxx"
response = requests.get(url=url, params={"id" : id_num})
response_json = response.json()
username = response_json["username"]
return username
def get_usernames(user_ids):
user_names = {}
for id in user_ids:
user_names[id] = get_username(id)
print(user_names)
return user_names
[test_request_module.py]
import sys
sys.path.append("..")
from utils import request_module
def mock_get_username(id):
return "Hosshey"
def test_get_usernames(monkeypatch):
monkeypatch.setattr(
request_module, "get_username", mock_get_username
)
inputs = ["001", "025"]
result = utils2.get_usernames(inputs)
assert list(result.keys()) == inputs
assert list(result.values()) == ["Hosshey"]*len(inputs)
終わりに
TBA