Skip to content

Commit

Permalink
Initial attempt at a type-agnostic equality matcher.
Browse files Browse the repository at this point in the history
  • Loading branch information
Adam Milligan committed Apr 22, 2011
1 parent 3e1bbaa commit 2668236
Show file tree
Hide file tree
Showing 8 changed files with 720 additions and 98 deletions.
34 changes: 22 additions & 12 deletions Cedar.xcodeproj/project.pbxproj
Expand Up @@ -23,16 +23,16 @@
/* End PBXAggregateTarget section */ /* End PBXAggregateTarget section */


/* Begin PBXBuildFile section */ /* Begin PBXBuildFile section */
66AEB6BE123C7CEE001C3DF1 /* CppSpecSpec.mm in Sources */ = {isa = PBXBuildFile; fileRef = AEEE1FEA11DC27B800029872 /* CppSpecSpec.mm */; };
66E33E53123CA82A00D326CC /* CppSpecSpec.mm in Sources */ = {isa = PBXBuildFile; fileRef = AEEE1FEA11DC27B800029872 /* CppSpecSpec.mm */; };
AE0B8563135F94DC001EEA23 /* ActualValue.mm in Sources */ = {isa = PBXBuildFile; fileRef = AEEE1FE511DC27B800029872 /* ActualValue.mm */; };
AE0B8564135F94DC001EEA23 /* ActualValue.mm in Sources */ = {isa = PBXBuildFile; fileRef = AEEE1FE511DC27B800029872 /* ActualValue.mm */; };
AE135D4011DEA6F400A922D4 /* OCMock.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D3111DEA6A900A922D4 /* OCMock.framework */; }; AE135D4011DEA6F400A922D4 /* OCMock.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D3111DEA6A900A922D4 /* OCMock.framework */; };
AE135D4111DEA6F400A922D4 /* OCHamcrest.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D2111DEA69A00A922D4 /* OCHamcrest.framework */; }; AE135D4111DEA6F400A922D4 /* OCHamcrest.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D2111DEA69A00A922D4 /* OCHamcrest.framework */; };
AE135E7011DEB46F00A922D4 /* libOCMock-StaticLib.a in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D3511DEA6A900A922D4 /* libOCMock-StaticLib.a */; }; AE135E7011DEB46F00A922D4 /* libOCMock-StaticLib.a in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D3511DEA6A900A922D4 /* libOCMock-StaticLib.a */; };
AE135E7111DEB46F00A922D4 /* libOCHamcrest-StaticLib.a in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D2311DEA69A00A922D4 /* libOCHamcrest-StaticLib.a */; }; AE135E7111DEB46F00A922D4 /* libOCHamcrest-StaticLib.a in Frameworks */ = {isa = PBXBuildFile; fileRef = AE135D2311DEA69A00A922D4 /* libOCHamcrest-StaticLib.a */; };
AE8C867D135FAE76006C9305 /* ActualValue.h in Headers */ = {isa = PBXBuildFile; fileRef = AEEE1FE411DC27B800029872 /* ActualValue.h */; settings = {ATTRIBUTES = (Public, ); }; }; AE8C867D135FAE76006C9305 /* ActualValue.h in Headers */ = {isa = PBXBuildFile; fileRef = AEEE1FE411DC27B800029872 /* ActualValue.h */; settings = {ATTRIBUTES = (Public, ); }; };
AE8C8680135FB4F7006C9305 /* ActualValue.h in Headers */ = {isa = PBXBuildFile; fileRef = AEEE1FE411DC27B800029872 /* ActualValue.h */; settings = {ATTRIBUTES = (Public, ); }; }; AE8C8680135FB4F7006C9305 /* ActualValue.h in Headers */ = {isa = PBXBuildFile; fileRef = AEEE1FE411DC27B800029872 /* ActualValue.h */; settings = {ATTRIBUTES = (Public, ); }; };
AE8C87541360CF02006C9305 /* AllMatchers.h in Headers */ = {isa = PBXBuildFile; fileRef = AE8C87531360CF02006C9305 /* AllMatchers.h */; settings = {ATTRIBUTES = (); }; };
AE8C877A1360F9EF006C9305 /* Equal.h in Headers */ = {isa = PBXBuildFile; fileRef = AE8C874D135FD1DB006C9305 /* Equal.h */; };
AE8C87A11362071E006C9305 /* EqualSpec.mm in Sources */ = {isa = PBXBuildFile; fileRef = AE8C87A01362071E006C9305 /* EqualSpec.mm */; };
AE8C87A21362071E006C9305 /* EqualSpec.mm in Sources */ = {isa = PBXBuildFile; fileRef = AE8C87A01362071E006C9305 /* EqualSpec.mm */; };
AE91CA6C11DE64A3002BA6B9 /* CDRSharedExampleGroupPool.h in Headers */ = {isa = PBXBuildFile; fileRef = AEFD17B311DD1E8200F4448A /* CDRSharedExampleGroupPool.h */; settings = {ATTRIBUTES = (Public, ); }; }; AE91CA6C11DE64A3002BA6B9 /* CDRSharedExampleGroupPool.h in Headers */ = {isa = PBXBuildFile; fileRef = AEFD17B311DD1E8200F4448A /* CDRSharedExampleGroupPool.h */; settings = {ATTRIBUTES = (Public, ); }; };
AE91CA6D11DE64B3002BA6B9 /* CDRSharedExampleGroupPool.h in Copy headers to framework */ = {isa = PBXBuildFile; fileRef = AEFD17B311DD1E8200F4448A /* CDRSharedExampleGroupPool.h */; }; AE91CA6D11DE64B3002BA6B9 /* CDRSharedExampleGroupPool.h in Copy headers to framework */ = {isa = PBXBuildFile; fileRef = AEFD17B311DD1E8200F4448A /* CDRSharedExampleGroupPool.h */; };
AE9855AE1236E7080024094E /* CDRSharedExampleGroupPool.m in Sources */ = {isa = PBXBuildFile; fileRef = AEFD17B111DD1E7200F4448A /* CDRSharedExampleGroupPool.m */; }; AE9855AE1236E7080024094E /* CDRSharedExampleGroupPool.m in Sources */ = {isa = PBXBuildFile; fileRef = AEFD17B111DD1E7200F4448A /* CDRSharedExampleGroupPool.m */; };
Expand Down Expand Up @@ -216,6 +216,9 @@
AE135D1611DEA69A00A922D4 /* OCHamcrest.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = OCHamcrest.xcodeproj; path = OCHamcrest/Source/OCHamcrest.xcodeproj; sourceTree = "<group>"; }; AE135D1611DEA69A00A922D4 /* OCHamcrest.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = OCHamcrest.xcodeproj; path = OCHamcrest/Source/OCHamcrest.xcodeproj; sourceTree = "<group>"; };
AE135D2611DEA6A900A922D4 /* OCMock.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = OCMock.xcodeproj; path = OCMock/Source/OCMock.xcodeproj; sourceTree = "<group>"; }; AE135D2611DEA6A900A922D4 /* OCMock.xcodeproj */ = {isa = PBXFileReference; lastKnownFileType = "wrapper.pb-project"; name = OCMock.xcodeproj; path = OCMock/Source/OCMock.xcodeproj; sourceTree = "<group>"; };
AE135E8311DEB4E400A922D4 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = folder; name = Foundation.framework; sourceTree = SDKROOT; }; AE135E8311DEB4E400A922D4 /* Foundation.framework */ = {isa = PBXFileReference; lastKnownFileType = folder; name = Foundation.framework; sourceTree = SDKROOT; };
AE8C874D135FD1DB006C9305 /* Equal.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = Equal.h; sourceTree = "<group>"; };
AE8C87531360CF02006C9305 /* AllMatchers.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = AllMatchers.h; sourceTree = "<group>"; };
AE8C87A01362071E006C9305 /* EqualSpec.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = EqualSpec.mm; sourceTree = "<group>"; };
AEC9DEEA12C2CC7E0039512D /* CDRColorizedReporter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CDRColorizedReporter.h; sourceTree = "<group>"; }; AEC9DEEA12C2CC7E0039512D /* CDRColorizedReporter.h */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.h; path = CDRColorizedReporter.h; sourceTree = "<group>"; };
AEC9DEEB12C2CC7E0039512D /* CDRColorizedReporter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRColorizedReporter.m; sourceTree = "<group>"; }; AEC9DEEB12C2CC7E0039512D /* CDRColorizedReporter.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRColorizedReporter.m; sourceTree = "<group>"; };
AEEE1FB611DC271300029872 /* Cedar.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Cedar.framework; sourceTree = BUILT_PRODUCTS_DIR; }; AEEE1FB611DC271300029872 /* Cedar.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Cedar.framework; sourceTree = BUILT_PRODUCTS_DIR; };
Expand Down Expand Up @@ -249,11 +252,9 @@
AEEE1FE111DC27B800029872 /* CDRSpecStatusViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRSpecStatusViewController.m; sourceTree = "<group>"; }; AEEE1FE111DC27B800029872 /* CDRSpecStatusViewController.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRSpecStatusViewController.m; sourceTree = "<group>"; };
AEEE1FE211DC27B800029872 /* CedarApplicationDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CedarApplicationDelegate.m; sourceTree = "<group>"; }; AEEE1FE211DC27B800029872 /* CedarApplicationDelegate.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CedarApplicationDelegate.m; sourceTree = "<group>"; };
AEEE1FE411DC27B800029872 /* ActualValue.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; path = ActualValue.h; sourceTree = "<group>"; }; AEEE1FE411DC27B800029872 /* ActualValue.h */ = {isa = PBXFileReference; explicitFileType = sourcecode.cpp.h; fileEncoding = 4; path = ActualValue.h; sourceTree = "<group>"; };
AEEE1FE511DC27B800029872 /* ActualValue.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = ActualValue.mm; sourceTree = "<group>"; };
AEEE1FE611DC27B800029872 /* SpecHelper.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SpecHelper.m; sourceTree = "<group>"; }; AEEE1FE611DC27B800029872 /* SpecHelper.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SpecHelper.m; sourceTree = "<group>"; };
AEEE1FE811DC27B800029872 /* CDRExampleGroupSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRExampleGroupSpec.m; sourceTree = "<group>"; }; AEEE1FE811DC27B800029872 /* CDRExampleGroupSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRExampleGroupSpec.m; sourceTree = "<group>"; };
AEEE1FE911DC27B800029872 /* CDRExampleSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRExampleSpec.m; sourceTree = "<group>"; }; AEEE1FE911DC27B800029872 /* CDRExampleSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRExampleSpec.m; sourceTree = "<group>"; };
AEEE1FEA11DC27B800029872 /* CppSpecSpec.mm */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.cpp.objcpp; path = CppSpecSpec.mm; sourceTree = "<group>"; };
AEEE1FEC11DC27B800029872 /* CDRExampleStateMapSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRExampleStateMapSpec.m; sourceTree = "<group>"; }; AEEE1FEC11DC27B800029872 /* CDRExampleStateMapSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = CDRExampleStateMapSpec.m; sourceTree = "<group>"; };
AEEE1FED11DC27B800029872 /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = "<group>"; }; AEEE1FED11DC27B800029872 /* main.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = main.m; sourceTree = "<group>"; };
AEEE1FEE11DC27B800029872 /* SlowSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SlowSpec.m; sourceTree = "<group>"; }; AEEE1FEE11DC27B800029872 /* SlowSpec.m */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.c.objc; path = SlowSpec.m; sourceTree = "<group>"; };
Expand Down Expand Up @@ -338,6 +339,14 @@
name = Products; name = Products;
sourceTree = "<group>"; sourceTree = "<group>";
}; };
AE8C879F1362068A006C9305 /* Matchers */ = {
isa = PBXGroup;
children = (
AE8C87A01362071E006C9305 /* EqualSpec.mm */,
);
path = Matchers;
sourceTree = "<group>";
};
AEEE1FA411DC26EA00029872 = { AEEE1FA411DC26EA00029872 = {
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
Expand Down Expand Up @@ -433,7 +442,8 @@
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
AEEE1FE411DC27B800029872 /* ActualValue.h */, AEEE1FE411DC27B800029872 /* ActualValue.h */,
AEEE1FE511DC27B800029872 /* ActualValue.mm */, AE8C87531360CF02006C9305 /* AllMatchers.h */,
AE8C874D135FD1DB006C9305 /* Equal.h */,
); );
path = Matchers; path = Matchers;
sourceTree = "<group>"; sourceTree = "<group>";
Expand All @@ -442,9 +452,9 @@
isa = PBXGroup; isa = PBXGroup;
children = ( children = (
AEEE1FEB11DC27B800029872 /* iPhone */, AEEE1FEB11DC27B800029872 /* iPhone */,
AE8C879F1362068A006C9305 /* Matchers */,
AEEE1FE811DC27B800029872 /* CDRExampleGroupSpec.m */, AEEE1FE811DC27B800029872 /* CDRExampleGroupSpec.m */,
AEEE1FE911DC27B800029872 /* CDRExampleSpec.m */, AEEE1FE911DC27B800029872 /* CDRExampleSpec.m */,
AEEE1FEA11DC27B800029872 /* CppSpecSpec.mm */,
AEEE1FEF11DC27B800029872 /* main.m */, AEEE1FEF11DC27B800029872 /* main.m */,
AEEE1FF011DC27B800029872 /* SpecHelperSpec.m */, AEEE1FF011DC27B800029872 /* SpecHelperSpec.m */,
AEEE1FF111DC27B800029872 /* SpecSpec.m */, AEEE1FF111DC27B800029872 /* SpecSpec.m */,
Expand Down Expand Up @@ -491,6 +501,8 @@
AEEE200811DC27B800029872 /* SpecHelper.h in Headers */, AEEE200811DC27B800029872 /* SpecHelper.h in Headers */,
AE91CA6C11DE64A3002BA6B9 /* CDRSharedExampleGroupPool.h in Headers */, AE91CA6C11DE64A3002BA6B9 /* CDRSharedExampleGroupPool.h in Headers */,
AEC9DEED12C2CC7E0039512D /* CDRColorizedReporter.h in Headers */, AEC9DEED12C2CC7E0039512D /* CDRColorizedReporter.h in Headers */,
AE8C87541360CF02006C9305 /* AllMatchers.h in Headers */,
AE8C877A1360F9EF006C9305 /* Equal.h in Headers */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
}; };
Expand Down Expand Up @@ -726,7 +738,6 @@
AEEE201111DC27B800029872 /* SpecHelper.m in Sources */, AEEE201111DC27B800029872 /* SpecHelper.m in Sources */,
AEFD17BB11DD1E9E00F4448A /* CDRSharedExampleGroupPool.m in Sources */, AEFD17BB11DD1E9E00F4448A /* CDRSharedExampleGroupPool.m in Sources */,
AEC9DEEE12C2CC7E0039512D /* CDRColorizedReporter.m in Sources */, AEC9DEEE12C2CC7E0039512D /* CDRColorizedReporter.m in Sources */,
AE0B8563135F94DC001EEA23 /* ActualValue.mm in Sources */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
}; };
Expand All @@ -740,7 +751,7 @@
AEEE21C211DC290400029872 /* SpecHelperSpec.m in Sources */, AEEE21C211DC290400029872 /* SpecHelperSpec.m in Sources */,
AEEE21C311DC290400029872 /* SpecSpec.m in Sources */, AEEE21C311DC290400029872 /* SpecSpec.m in Sources */,
AEEE21C411DC290400029872 /* SpecSpec2.m in Sources */, AEEE21C411DC290400029872 /* SpecSpec2.m in Sources */,
66E33E53123CA82A00D326CC /* CppSpecSpec.mm in Sources */, AE8C87A11362071E006C9305 /* EqualSpec.mm in Sources */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
}; };
Expand All @@ -763,7 +774,6 @@
AEEE223D11DC2B6D00029872 /* CedarApplicationDelegate.m in Sources */, AEEE223D11DC2B6D00029872 /* CedarApplicationDelegate.m in Sources */,
AE9855AE1236E7080024094E /* CDRSharedExampleGroupPool.m in Sources */, AE9855AE1236E7080024094E /* CDRSharedExampleGroupPool.m in Sources */,
AEC9DEF412C2CC8F0039512D /* CDRColorizedReporter.m in Sources */, AEC9DEF412C2CC8F0039512D /* CDRColorizedReporter.m in Sources */,
AE0B8564135F94DC001EEA23 /* ActualValue.mm in Sources */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
}; };
Expand All @@ -779,7 +789,7 @@
AEEE228611DC2D5800029872 /* CDRExampleStateMapSpec.m in Sources */, AEEE228611DC2D5800029872 /* CDRExampleStateMapSpec.m in Sources */,
AEEE228711DC2D5800029872 /* main.m in Sources */, AEEE228711DC2D5800029872 /* main.m in Sources */,
AEEE228811DC2D5800029872 /* SlowSpec.m in Sources */, AEEE228811DC2D5800029872 /* SlowSpec.m in Sources */,
66AEB6BE123C7CEE001C3DF1 /* CppSpecSpec.mm in Sources */, AE8C87A21362071E006C9305 /* EqualSpec.mm in Sources */,
); );
runOnlyForDeploymentPostprocessing = 0; runOnlyForDeploymentPostprocessing = 0;
}; };
Expand Down
1 change: 1 addition & 0 deletions Source/Headers/CDRSpec.h
Expand Up @@ -21,6 +21,7 @@ void fail(NSString *);
} }


#import "ActualValue.h" #import "ActualValue.h"
#import "AllMatchers.h"


#endif #endif


Expand Down
35 changes: 15 additions & 20 deletions Source/Matchers/ActualValue.h
Expand Up @@ -19,38 +19,33 @@ namespace Cedar { namespace Matchers {
public: public:
ActualValue(const T &); ActualValue(const T &);


template<typename U> template<typename Matcher> void to(const Matcher &) const;
void toEqual(const U &) const; template<typename Matcher> void to_not(const Matcher &) const;


private: private:
const T value_; const T value_;
}; };



template<typename T> template<typename T>
const ActualValue<T> expect(const T & value) { ActualValue<T>::ActualValue(const T & value) : value_(value) {
return ActualValue<T>(value);
} }


template<typename T> template<typename T>
ActualValue<T>::ActualValue(const T & value) : value_(value) { const ActualValue<T> expect(const T & actualValue) {
return ActualValue<T>(actualValue);
} }


#pragma mark toEqual template<typename T> template<typename Matcher>
// Generic method must be defined here, not in the implementation file. void ActualValue<T>::to(const Matcher & matcher) const {
template<typename T> template<typename U> if (!matcher.matches(value_)) {
void ActualValue<T>::toEqual(const U & expectedValue) const { [[CDRSpecFailure specFailureWithReason:matcher.failure_message()] raise];
if (expectedValue != value_) {
std::stringstream message;
message << "Expected <" << value_ << "> to equal <" << expectedValue << ">";

[[CDRSpecFailure specFailureWithReason:[NSString stringWithCString:message.str().c_str() encoding:NSUTF8StringEncoding]] raise];
} }
} }


// Specialized methods must be declared here, but defined in the implementation file. template<typename T> template<typename Matcher>
// If not declared here, OS X build will fail to pick up the specialization. If defined void ActualValue<T>::to_not(const Matcher & matcher) const {
// here, iOS builds will fail with duplicate symbol link errors. if (matcher.matches(value_)) {
template<> template<> [[CDRSpecFailure specFailureWithReason:matcher.negative_failure_message()] raise];
void ActualValue<NSObject *>::toEqual(NSObject * const & expectedValue) const; }
}
}} }}
20 changes: 0 additions & 20 deletions Source/Matchers/ActualValue.mm

This file was deleted.

1 change: 1 addition & 0 deletions Source/Matchers/AllMatchers.h
@@ -0,0 +1 @@
#import "Equal.h"
126 changes: 126 additions & 0 deletions Source/Matchers/Equal.h
@@ -0,0 +1,126 @@
#import <Foundation/Foundation.h>
#import "CDRExampleBase.h"

#include <iostream>
#include <sstream>

namespace Cedar { namespace Matchers {
template<typename T>
class EqualMatcher {
private:
EqualMatcher<T> & operator=(const EqualMatcher<T> &);

public:
EqualMatcher(const T & expectedValue);
~EqualMatcher();
// Allow default copy ctor.

template<typename U>
bool matches(const U &) const;
bool matches(const id &) const;
bool matches(NSObject * const &) const;
bool matches(NSString * const &) const;

NSString * failure_message() const;
NSString * negative_failure_message() const;

private:
template<typename U>
NSString * stringFor(const U &) const;
NSString * stringFor(const id & value) const;
NSString * stringFor(NSObject * const &) const;
NSString * stringFor(NSString * const &) const;

private:
const T & expectedValue_;
mutable NSString *actualValueString_;
};

template<typename T>
EqualMatcher<T> equal(const T & expectedValue) {
return EqualMatcher<T>(expectedValue);
}

template<typename T>
EqualMatcher<T>::EqualMatcher(const T & expectedValue)
: expectedValue_(expectedValue), actualValueString_(nil) {
}

template<typename T>
EqualMatcher<T>::~EqualMatcher() {
[actualValueString_ release]; actualValueString_ = nil;
}

#pragma mark Generic
template<typename T> template<typename U>
bool EqualMatcher<T>::matches(const U & actualValue) const {
actualValueString_ = [this->stringFor(actualValue) retain];
return expectedValue_ == actualValue;
}

template<typename T> template<typename U>
NSString * EqualMatcher<T>::stringFor(const U & value) const {
std::stringstream temp;
temp << value;
return [NSString stringWithCString:temp.str().c_str() encoding:NSUTF8StringEncoding];
}

template<typename T>
NSString * EqualMatcher<T>::failure_message() const {
return [NSString stringWithFormat:@"Expected <%@> to equal <%@>", actualValueString_, this->stringFor(expectedValue_)];
}

template<typename T>
NSString * EqualMatcher<T>::negative_failure_message() const {
return [NSString stringWithFormat:@"Expected <%@> to not equal <%@>", actualValueString_, this->stringFor(expectedValue_)];
}

#pragma mark id
template<typename T>
bool EqualMatcher<T>::matches(const id & actualValue) const {
actualValueString_ = [[NSString alloc] initWithFormat:@"%@", actualValue];
return [actualValue isEqual:expectedValue_];
}

template<> template<typename U>
bool EqualMatcher<id>::matches(const U & actualValue) const {
[[CDRSpecFailure specFailureWithReason:@"Attempt to compare id to incomparable type"] raise];
}

template<typename T>
NSString * EqualMatcher<T>::stringFor(const id & value) const {
return [NSString stringWithFormat:@"%@", value];
}

#pragma mark NSObject
template<typename T>
bool EqualMatcher<T>::matches(NSObject * const & actualValue) const {
return this->matches(static_cast<const id &>(actualValue));
}

template<> template<typename U>
bool EqualMatcher<NSObject *>::matches(const U & actualValue) const {
[[CDRSpecFailure specFailureWithReason:@"Attempt to compare NSObject * to incomparable type"] raise];
}

template<typename T>
NSString * EqualMatcher<T>::stringFor(NSObject * const & value) const {
return this->stringFor(static_cast<const id &>(value));
}

#pragma mark NSString
template<typename T>
bool EqualMatcher<T>::matches(NSString * const & actualValue) const {
return this->matches(static_cast<const id &>(actualValue));
}

template<> template<typename U>
bool EqualMatcher<NSString *>::matches(const U & actualValue) const {
[[CDRSpecFailure specFailureWithReason:@"Attempt to compare NSString * to incomparable type"] raise];
}

template<typename T>
NSString * EqualMatcher<T>::stringFor(NSString * const & value) const {
return this->stringFor(static_cast<const id &>(value));
}
}}
46 changes: 0 additions & 46 deletions Spec/CppSpecSpec.mm

This file was deleted.

0 comments on commit 2668236

Please sign in to comment.