如何在for循环中获得单元测试的覆盖率?

时间:2019-10-24 21:56:22

标签: python json unit-testing beautifulsoup mocking

我正在尝试在修补assertRaises时使用BeautifulSoup.select测试异常。

从网页获取ID的方法,采用HTML resultsPage

def parseOutIds(resultsPage):

    soup = BeautifulSoup(resultsPage, "html.parser")

    records = soup.select('some-html-tags')
    parsed = []
    for record in records:
        try:
            ampData = json.loads(record["other-tags"])
            parsed.append(ampData)
        except json.decoder.JSONDecodeError from err # Missing coverage

    return parsed

上面的辅助方法和测试。我之所以提出ValueError,是因为json.decoder.JSONDecodeError基于此answer继承自它。

def loadHtml(self, fileName):
    with open('path/to/test'+filename) as f:
         self.html = file.read().strip()

def test_parseOutIds(self):
    self.loadHtml('test-html.html')

    #errorMock method just raises ValueError exception
    bsPatch = patch('bs4.BeautifulSoup.select', self.errorMock) 
    with bsPatch:
        with self.assertRaises(ValueError):
             parseOutIds(self.html)

我上面的当前测试缺少异常行的含义。

其他要点:

  1. 我也必须修补json.load吗?
  2. 根据我从其他答案中看到的内容,是否还会由于存在循环而模拟另一种方法?

1 个答案:

答案 0 :(得分:0)

您的代码中存在一些误解:

  • ValueError不会被except json.decoder.JSONDecodeError子句捕获-您可以从json.decoder.JSONDecodeError派生的类中捕获对象,但不能捕获json.decoder.JSONDecodeError的父类中的对象。
  • soup.select调用位于try块之外-从soup.select引发的异常因此也不会被捕获。

现在,关于您的测试问题:我认为您可能不必修补任何东西来测试parseOutIds。您只需要为相应的测试用例提供适当的html输入即可。对于您的情况,您想编写一个测试以涵盖异常部分。这意味着,所需的html输入将具有包含无效JSON数据的记录之一。然后,这将导致json.loads抛出json.decoder.JSONDecodeError

相关问题