Python:构建模拟函数的问题

时间:2016-04-11 13:31:17

标签: python unit-testing mocking stub

我正在编写单元测试以验证我的项目功能。我需要用mock函数替换一些函数,我想使用Python模拟库。我使用的实现似乎并没有正常工作,我不明白我做错了什么。这是一个简化的场景:

根/ connector.py

from ftp_utils.py import *

def main():
    config = yaml.safe_load("vendor_sftp.yaml")
    downloaded_files = []

    downloaded_files = get_files(config)
    for f in downloaded_files:
      #do something

根/ utils的/ ftp_utils.py

import os
import sys
import pysftp

def get_files(config):
   sftp = pysftp.Connection(config['host'], username=config['username'])
   sftp.chdir(config['remote_dir'])
   down_files = sftp.listdir()
   if down_files is not None:
     for f in down_files:
       sftp.get(f, os.path.join(config['local_dir'], f), preserve_mtime=True)

   return down_files

根/测试/ connector_tester.py

import unittest
import mock
import ftp_utils
import connector

def get_mock_files():
  return ['digital_spend.csv', 'tv_spend.csv']

class ConnectorTester(unittest.TestCase)
  @mock.patch('ftp_utils.get_files', side_effect=get_mock_files)
  def test_main_process(self, get_mock_files_function):
    # I want to use a mock version of the get_files function
    connector.main() 

当我调试我的测试时,我希望在connector.py主内部调用的get_files函数是get_mock_files(),而是ftp_utils.get_files()。我在这做错了什么?我应该在代码中更改什么来正确调用get_mock_file()模拟?

谢谢, Alessio的

1 个答案:

答案 0 :(得分:1)

我认为您的方案存在一些问题:

  • connector.py无法从ftp_utils.py那样导入
  • 也不能connector_tester.py
  • 作为一种习惯,最好以test_xxx.py
  • 的形式提供测试文件
  • 要使用unittest进行修补,请参阅this example

通常,尝试提供有用的最小示例,以便每个人都可以更轻松地运行代码。

我修改了你的例子以使其工作,但基本上,问题是你补丁'ftp_utils.get_files'虽然它不是connector.main()内部实际调用的引用,但可能是{{1} }}

以下是修改后的示例目录:

'connector.get_files'

test_connector.py:

test_connector.py
ftp_utils.py
connector.py

NB:运行import unittest import sys import mock import connector def get_mock_files(*args, **kwargs): return ['digital_spend.csv', 'tv_spend.csv'] class ConnectorTester(unittest.TestCase): def setUp(self): self.patcher = mock.patch('connector.get_files', side_effect=get_mock_files) self.patcher.start() def test_main_process(self): # I want to use a mock version of the get_files function connector.main() suite = unittest.TestLoader().loadTestsFromTestCase(ConnectorTester) if __name__ == "__main__": unittest.main() 时调用的内容为connector.main()

connector.py:

'connector.get_files'

connector / ftp_utils.py不变。