summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorzhanyong.wan <zhanyong.wan@8415998a-534a-0410-bf83-d39667b30386>2010-03-15 21:23:04 +0000
committerzhanyong.wan <zhanyong.wan@8415998a-534a-0410-bf83-d39667b30386>2010-03-15 21:23:04 +0000
commit6794f312a31bd36d59f76b77825eecefc70adfa6 (patch)
treed88a08ccf38d37809112b99742bd38b325eb691e
parent922a0f47eff3a416a73c1d0f70634c6584d7f239 (diff)
downloadgooglemock-6794f312a31bd36d59f76b77825eecefc70adfa6.tar.gz
Adds IsInterested() to MatchResultListener; clarifies the format of matcher description and match result explanation; renames the free function MatchAndExplain() to ExplainMatchResult() to avoid it being hidden inside a MATCHER* definition.
git-svn-id: http://googlemock.googlecode.com/svn/trunk@276 8415998a-534a-0410-bf83-d39667b30386
-rw-r--r--include/gmock/gmock-matchers.h19
-rw-r--r--test/gmock-matchers_test.cc53
2 files changed, 61 insertions, 11 deletions
diff --git a/include/gmock/gmock-matchers.h b/include/gmock/gmock-matchers.h
index 50c0d7b..8dba440 100644
--- a/include/gmock/gmock-matchers.h
+++ b/include/gmock/gmock-matchers.h
@@ -90,6 +90,12 @@ class MatchResultListener {
// Returns the underlying ostream.
::std::ostream* stream() { return stream_; }
+ // Returns true iff the listener is interested in an explanation of
+ // the match result. A matcher's MatchAndExplain() method can use
+ // this information to avoid generating the explanation when no one
+ // intends to hear it.
+ bool IsInterested() const { return stream_ != NULL; }
+
private:
::std::ostream* const stream_;
@@ -106,7 +112,10 @@ class MatcherInterface {
virtual ~MatcherInterface() {}
// Returns true iff the matcher matches x; also explains the match
- // result to 'listener'.
+ // result to 'listener', in the form of a non-restrictive relative
+ // clause ("which ...", "whose ...", etc) that describes x. For
+ // example, the MatchAndExplain() method of the Pointee(...) matcher
+ // should generate an explanation like "which points to ...".
//
// You should override this method when defining a new matcher.
//
@@ -118,7 +127,11 @@ class MatcherInterface {
// listener->stream() may be NULL.
virtual bool MatchAndExplain(T x, MatchResultListener* listener) const = 0;
- // Describes this matcher to an ostream.
+ // Describes this matcher to an ostream. The function should print
+ // a verb phrase that describes the property a value matching this
+ // matcher should have. The subject of the verb phrase is the value
+ // being matched. For example, the DescribeTo() method of the Gt(7)
+ // matcher prints "is greater than 7".
virtual void DescribeTo(::std::ostream* os) const = 0;
// Describes the negation of this matcher to an ostream. For
@@ -2853,7 +2866,7 @@ inline bool Value(const T& value, M matcher) {
// Matches the value against the given matcher and explains the match
// result to listener.
template <typename T, typename M>
-inline bool MatchAndExplain(
+inline bool ExplainMatchResult(
M matcher, const T& value, MatchResultListener* listener) {
return SafeMatcherCast<const T&>(matcher).MatchAndExplain(value, listener);
}
diff --git a/test/gmock-matchers_test.cc b/test/gmock-matchers_test.cc
index 1eaecf9..1ba4c8d 100644
--- a/test/gmock-matchers_test.cc
+++ b/test/gmock-matchers_test.cc
@@ -37,6 +37,7 @@
#include <string.h>
#include <functional>
+#include <iostream>
#include <list>
#include <map>
#include <set>
@@ -88,7 +89,7 @@ using testing::Matcher;
using testing::MatcherCast;
using testing::MatcherInterface;
using testing::Matches;
-using testing::MatchAndExplain;
+using testing::ExplainMatchResult;
using testing::MatchResultListener;
using testing::NanSensitiveDoubleEq;
using testing::NanSensitiveFloatEq;
@@ -110,6 +111,7 @@ using testing::Truly;
using testing::TypedEq;
using testing::Value;
using testing::_;
+using testing::internal::DummyMatchResultListener;
using testing::internal::FloatingEqMatcher;
using testing::internal::FormatMatcherDescriptionSyntaxError;
using testing::internal::GetParamIndex;
@@ -117,6 +119,7 @@ using testing::internal::Interpolation;
using testing::internal::Interpolations;
using testing::internal::JoinAsTuple;
using testing::internal::SkipPrefix;
+using testing::internal::StreamMatchResultListener;
using testing::internal::String;
using testing::internal::Strings;
using testing::internal::StringMatchResultListener;
@@ -187,6 +190,31 @@ string Explain(const MatcherType& m, const Value& x) {
return ss.str();
}
+TEST(MatchResultListenerTest, StreamingWorks) {
+ StringMatchResultListener listener;
+ listener << "hi" << 5;
+ EXPECT_EQ("hi5", listener.str());
+
+ // Streaming shouldn't crash when the underlying ostream is NULL.
+ DummyMatchResultListener dummy;
+ dummy << "hi" << 5;
+}
+
+TEST(MatchResultListenerTest, CanAccessUnderlyingStream) {
+ EXPECT_TRUE(DummyMatchResultListener().stream() == NULL);
+ EXPECT_TRUE(StreamMatchResultListener(NULL).stream() == NULL);
+
+ EXPECT_EQ(&std::cout, StreamMatchResultListener(&std::cout).stream());
+}
+
+TEST(MatchResultListenerTest, IsInterestedWorks) {
+ EXPECT_TRUE(StringMatchResultListener().IsInterested());
+ EXPECT_TRUE(StreamMatchResultListener(&std::cout).IsInterested());
+
+ EXPECT_FALSE(DummyMatchResultListener().IsInterested());
+ EXPECT_FALSE(StreamMatchResultListener(NULL).IsInterested());
+}
+
// Makes sure that the MatcherInterface<T> interface doesn't
// change.
class EvenMatcherImpl : public MatcherInterface<int> {
@@ -205,7 +233,8 @@ class EvenMatcherImpl : public MatcherInterface<int> {
// two methods is optional.
};
-TEST(MatcherInterfaceTest, CanBeImplementedUsingDeprecatedAPI) {
+// Makes sure that the MatcherInterface API doesn't change.
+TEST(MatcherInterfaceTest, CanBeImplementedUsingPublishedAPI) {
EvenMatcherImpl m;
}
@@ -2049,28 +2078,36 @@ TEST(ValueTest, WorksWithMonomorphicMatcher) {
EXPECT_FALSE(Value(1, ref_n));
}
-TEST(MatchAndExplainTest, WorksWithPolymorphicMatcher) {
+TEST(ExplainMatchResultTest, WorksWithPolymorphicMatcher) {
StringMatchResultListener listener1;
- EXPECT_TRUE(MatchAndExplain(PolymorphicIsEven(), 42, &listener1));
+ EXPECT_TRUE(ExplainMatchResult(PolymorphicIsEven(), 42, &listener1));
EXPECT_EQ("% 2 == 0", listener1.str());
StringMatchResultListener listener2;
- EXPECT_FALSE(MatchAndExplain(Ge(42), 1.5, &listener2));
+ EXPECT_FALSE(ExplainMatchResult(Ge(42), 1.5, &listener2));
EXPECT_EQ("", listener2.str());
}
-TEST(MatchAndExplainTest, WorksWithMonomorphicMatcher) {
+TEST(ExplainMatchResultTest, WorksWithMonomorphicMatcher) {
const Matcher<int> is_even = PolymorphicIsEven();
StringMatchResultListener listener1;
- EXPECT_TRUE(MatchAndExplain(is_even, 42, &listener1));
+ EXPECT_TRUE(ExplainMatchResult(is_even, 42, &listener1));
EXPECT_EQ("% 2 == 0", listener1.str());
const Matcher<const double&> is_zero = Eq(0);
StringMatchResultListener listener2;
- EXPECT_FALSE(MatchAndExplain(is_zero, 1.5, &listener2));
+ EXPECT_FALSE(ExplainMatchResult(is_zero, 1.5, &listener2));
EXPECT_EQ("", listener2.str());
}
+MATCHER_P(Really, inner_matcher, "") {
+ return ExplainMatchResult(inner_matcher, arg, result_listener);
+}
+
+TEST(ExplainMatchResultTest, WorksInsideMATCHER) {
+ EXPECT_THAT(0, Really(Eq(0)));
+}
+
TEST(AllArgsTest, WorksForTuple) {
EXPECT_THAT(make_tuple(1, 2L), AllArgs(Lt()));
EXPECT_THAT(make_tuple(2L, 1), Not(AllArgs(Lt())));