2013-07-26 70 views
2

我有一个python函数可以下载几个文件。如何单元测试下载功能?

例如

def downloader(): 
    file_list=['fileone.htm','filetwo.htm','filethree.htm'] 
    for f in file_list: 
     (filename,headers) = urllib.urlretrieve(f,'c:\\temp\\'+f) 

单元测试函数的正确方法是什么?它是否工作取决于urlretrieve函数的行为方式,这取决于外部因素。

+1

该方法是否执行任何操作*但下载?否则,你真的想在这里测试什么?基本上,我们假设下载成功了,你想测试什么?如果失败会怎样?你有逻辑来处理? *那*你想测试什么? –

+0

完整的方法会生成url和目标文件名。然后它遍历它们并进行下载。我对单元测试相当陌生,因此只是试图学习如何正确地做事情。 – Ginger

回答

0

基本上,如果您需要测试逻辑如何响应urlretrieve函数的行为,则需要将模拟行为注入到程序流中。执行此操作的一种方法是将urllib功能包装在运行单元测试时生成此行为的模块或类中。例如,如果你的下载功能是它自己的模块中,你可以做这样的事情(简化的伪代码):

文件:dowloader.py

class UrllibWrapper: 
    # thin wrapper for urllib 

class Downloader: 
    def __init__(self, urllib_class=None): 
     if urllib_class is None: 
      self.ul = UrllibWrapper() 
     else: 
      self.ul = urllib_class 

    def download(self, f, dest): 
     self.ul.urlretrieve(f, dest) 

if __name__ == '__main__': 
    class FakeUrllibWrapper: 
     # implement desired behaviour of urrlib 

    ul = FakeUrllibWrapper() 
    dl = Downloader(ul) 
    # do unit tests 

在你的编程'你会怎么做:

# ... 
from downloader import Downloader 
dl = Downloader() 
for f in files: 
    dl.download(f, dest) 
2

如果你要测试的是函数调用urlretrieve上file_list中,你可以修改函数取检索功能作为参数的所有元素:

def downloder(urlretrieve): 
    file_list=['fileone.htm','filetwo.htm','filethree.htm'] 
    for f in file_list: 
    (filename,headers) = urlretrieve(f,'c:\\temp\\'+f) 

然后在您的单元测试中,您可以创建一个自定义函数并检查被称为正确的时间量和正确的参数。

calls = [] 
def retrieve(url, local) : 
    calls.append([url,local]) 

assert(len(calls) == 3) 
assert(calls[0][0] == 'fileone.html') 
assert(calls[0][2] == 'c:\\temp\\fileone.html') 
... 

您可以使用库Mock简化创建自己的检索功能单元测试的一部分。