我的python应用程序使用urllib2向许多URL发出许多http请求。我想构建一个单元测试套件来测试我的数据解析和错误处理代码。
我有一个充满测试数据的目录,包含许多文件,每个文件包含一个http响应,带有标题和响应数据。 (使用curl -i)在某些情况下,这些文件包含http错误消息(测试错误处理所需)
理想情况下,我想创建一个模拟对象来替换urllib2.urlopen并返回一个模拟响应对象。
我想知道是否有一种简单的方法让urllib2直接从文件加载HTTP响应,并让urllib2解析此数据以创建适当的响应对象(就好像从网址读取响应一样。
我尝试使用“file://”协议构造的url,但是文件顶部的http响应标头未被正确读取或解析。
或者我正在考虑编写一个小型Web服务器类来提供测试文件,但这似乎比我想要的工作多一点。让urllib2从我已经保存在文件中的http响应中以某种方式重建响应对象会更容易(无需构建Web服务器再次为它们提供服务)
有什么想法吗?
答案 0 :(得分:2)
我认为最好的方法是模拟 mockcon类必须提供方法 (可能对 您可以为后一个角色使用实际的 我认为为整个httplib.HTTPConnection
的一个子集(在下面调用结果类mockcon
以获得具体性)并使用它添加一个处理程序并将HTTPHandler
子类化(到在build_opener
中使用 - 子类化意味着它可以替换HTTPHandler
默认使用{/ 1}}:{/ p>
build_opener
class MockHTTPHandler(urllib2.HTTPHandler):
def http_open(self, req):
return self.do_open(mockcon, req)
调用 - 几个可以是假人(即接受并忽略任意args和kwds并且什么也不做):do_open
set_debuglevel
_set_tunnel
request
的第二个arg感兴趣,因为它给出了URL的“选择器”部分。)request
__init__
方法将URL的主机部分作为第一个arg(即当前mockcon
之后的第一个)并且应该忽略以下kwds(用于设置超时)。self
的{{1}}方法(没有args,当然超出get_response
)必须返回一个http响应对象 - 即一个类似文件的可读对象,它也有属性{ {1}},mockcon
和self
以及方法.msg
以返回网址。.status
实例,但必须使用一个具有.reason
参数的模拟/虚拟arg初始化它(忽略其args和kwds并返回任何内容),并且,在初始化之后,将其get_full_url()
参数重置为httplib.HTTPResponse
打开文件,准确提供真实HTTP响应将在其套接字上接收的字节。makefile
调用构建一个完整的模拟可能比重用.fp
(以及内部使用的rb
的大部分功能更为简单),虽然可能不像“本地Web服务器”方法那么简单,你认为它更多的工作。但是值得考虑所有这三种方法(模拟肯定会在操作中最轻量级/快速,本地Web服务器最慢......并且还需要以urllib2.urlopen
为其添加前缀来修改URL,疗程)。
答案 1 :(得分:1)
服务器方法肯定不是更多的工作,它可能是所有替代方案中最简单和最少的工作。
退房:http://docs.python.org/library/simplehttpserver.html
7行python程序,当从某个目录运行时,将通过HTTP提供所有文件(以及递归地,子目录中的任何文件)。
您可以让您的单元测试代码启动并停止服务器,这样即使不进行测试也不需要让它保持运行。