from hamcrest.core.base_matcher import BaseMatcher
from hamcrest.core.string_description import StringDescription
class MetaMatcher(BaseMatcher):
def __init__(self, item, expected_match_result=True):
self.expected_match_result = expected_match_result
self.item = item
self.match_result = None
self.description = None
self.wrong_description = None
self.mismatch_description = None
self.wrong_mismatch_description = None
def _matches(self, matcher):
ret = True
self.match_result = matcher._matches(self.item)
if self.expected_match_result:
ret &= self.match_result
else:
ret &= not self.match_result
if self.description:
descr = StringDescription()
matcher.describe_to(descr)
descr = str(descr)
descr_is_correct = descr == self.description
if not descr_is_correct:
self.wrong_description = descr
ret = False
if self.mismatch_description:
if ret == self.expected_match_result:
self.wrong_mismatch_description = (
"the matcher matched, but a mismatch description was provided")
return False
descr = StringDescription()
matcher.describe_mismatch(self.item, descr)
descr = str(descr)
descr_is_correct = descr == self.mismatch_description
if not descr_is_correct:
self.wrong_mismatch_description = "the mismatch_description was <{}>".format(
descr)
ret = False
return ret
def describe_to(self, description):
ret = []
descriptions = []
ret.append("A matcher that {} the item".format(
"matches" if self.expected_match_result else "does not match"))
if self.description:
descriptions.append(
"with the description: <{}>".format(self.description))
if self.mismatch_description:
descriptions.append(
"with tne mismatch_description: <{}>".format(
self.mismatch_description))
ret.append(" and ".join(descriptions))
string = "{}.".format(" ".join(filter(None, ret)))
description.append_text(_sentence_case(string))
def describe_mismatch(self, item, mismatch_description):
ret = []
if self.match_result != self.expected_match_result:
ret.append("the matcher {}".format(
"matched" if self.match_result else "did not match"
))
if self.wrong_description:
ret.append("the description was <{}>".format(
self.wrong_description
))
if self.wrong_mismatch_description:
ret.append(
self.wrong_mismatch_description
)
string = "{}.".format(", ".join(ret))
mismatch_description.append_text(_sentence_case(string))
[docs]def matches(a_matcher):
"""Checks that the matcher under test matches the value
:param a_matcher: The matcher that needs to be checked.
:return: :py:class:`pyhamcrest_metamatchers.metamatchers.MetaMatcher<MetaMatcher>`
"""
return MetaMatcher(a_matcher)
[docs]def doesnt_match(a_matcher):
"""Checks that the matcher under test doesn't match the value
:param a_matcher: The matcher that needs to be checked.
:return: :py:class:`pyhamcrest_metamatchers.metamatchers.MetaMatcher<MetaMatcher>`
"""
return MetaMatcher(a_matcher, False)
def _sentence_case(string):
return "{}{}".format(string[0].capitalize(), string[1:])