LoginSignup
7
6

More than 3 years have passed since last update.

こんなのがあったのか!? Python用VCR(vcrpy)

Posted at

はじめに

Webサイトからスクレイピングする際、テストのために多くのリクエストを飛ばしてしまい、相手に迷惑をかけてしまう恐れがあります。:worried:

Rubyでは、VCRというgemがあり、1度投げたリクエスト結果をローカルのファイルに保存しておいて、再度同じリクエストが投げれられた場合に保存したファイルを参照しにいくという便利なものがあると噂に聞きました。

ちょうどPythonでスクレイピングのコードを書いていた私は、これのPython版がないか探したところ、見つけた&使ってみて感動したので記事を書くことにしました。

Python版VCR - vcrpy

公式ドキュメントにThis is a Python version of Ruby’s VCR library.と書いてあるあたりが、まさに求めていたものですね。

VCRとは?

VCR 【Video Cassette Recorder】
主にアメリカで使われる言葉で日本でのVTRと同じ。 家庭に普及しているVHS等のカセットに入ったテープを使用するVTRのこと。

なるほど。公式ドキュメントのイメージ画像がVHSのカセットテープなのもなっとくです。

使い方

メソッドの上に@vcr.use_cassette()と書くだけです。
これだけで、対象のメソッドから呼ばれるrequestsの結果をファイルに保存してくれます。

デフォルトだと、実行ファイルと同ディレクトリ上にrequestsの結果のyamlファイルを保存します。
保存先のディレクトリを変更したい場合やyamlではなくjsonでファイルを保存したい場合、保存方法やVCR対象のrequestsを選びたい場合は、以下のように設定を変更できます。

vcr_sample.py
my_vcr = vcr.VCR(
    serializer           = 'yaml',
    cassette_library_dir = 'vcr',
    record_mode          = 'once',
    match_on             = ['uri', 'method'],
)

@my_vcr.use_cassette()
def hoge():
    requests.get('https://qiita.com')

テストで使ってみる

qiita.comのrequests結果が一致することを確認するテストを書いてみます。

hoge.py
import requests

class Hoge():
    def __init__(self):
        pass

    def getQiita(self):
        r = requests.get('https://qiita.com')
        return r
test_hoge.py
import pytest
import requests
import vcr

import hoge

# 保存先をvcrフォルダに変更
my_vcr = vcr.VCR(
    serializer           = 'yaml',
    cassette_library_dir = 'vcr',
    record_mode          = 'once',
    match_on             = ['uri', 'method'],
)

@my_vcr.use_cassette()
def test_hoge(mocker):
    r = requests.get('https://qiita.com')

    # requestsの結果をMockを使って埋め込む
    responseMock      = mocker.Mock()
    responseMock.text = r.text
    mocker.patch('requests.get', return_value=responseMock)

    h      = hoge.Hoge()
    hoge_r = h.getQiita()
    assert r.text == hoge_r.text

テストコードでqiita.comのrequests結果をVCR化して取得します。
その結果をrequests.getに対して、Mockでpatchを当てます。

これでtest_hoge.pyはVCR化が完了。hoge.pytest_hoge.pyから取得したrequests結果を参照しているので、多くのリクエストを飛ばして相手に迷惑をかけることが無くなります。:smile:

いやぁ、便利だっ:clap::clap::clap:

7
6
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
6