0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

urllib.request の fixture

Last updated at Posted at 2014-01-04

HTTPretty が python3.3 の urllib.request.urlopen() でうまく動かなかったので探してきました。で参考にさせて頂いたソースがあったのですが、どこか忘れてしまった・・・手順は以下のとおり。urllib2 を使えば python2 でもたぶん大丈夫。

仕込み
from io import StringIO
import urllib.request as urllib2

def generate_response(req, return_data):
	resp = urllib2.addinfourl(StringIO(return_data),
								'mock header',
								req.get_full_url())
	resp.code = 200
	resp.msg = 'OK'
	return resp

expect_url = {}

def register(url, return_data):
	expect_url[url] = lambda req:generate_response(req, return_data)

def mock_response(req):
	return expect_url[req.get_full_url()](req)

class MyHTTPHandler(urllib2.HTTPHandler):
	def http_open(self, req):
		return mock_response(req)

これを install_opener します。あとは、expect_url にハックする URL と戻り値を入れればいいです。

テスト本体
from nose.tools import *

class TestUrlopen(object):
	def __init__(self):
		my_opener = urllib2.build_opener(MyHTTPHandler)
		urllib2.install_opener(my_opener)

	def test_urlopen(self):
		url = 'http://mock_server'
		register(url, "hello world")

		ret = urllib2.urlopen(url).read()
		eq_(ret, "hello world")

expect_url を global に置いて動的にレスポンスをつけるのは私のアイデアですが、他はまんまコードを頂いてます。どこだったかな・・・

ここではやってませんが、同じURLで違うデータを返す(副作用を入れる)場合は register() で push して、mock_response() で pop すれば良いかと。

なんとなくクラスも作ってみました。https://gist.github.com/norobust/8254063

0
1
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
0
1

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?