diff --git a/Cuckoo.xcodeproj/project.pbxproj b/Cuckoo.xcodeproj/project.pbxproj index ab183d0..d6fa6f5 100644 --- a/Cuckoo.xcodeproj/project.pbxproj +++ b/Cuckoo.xcodeproj/project.pbxproj @@ -7,15 +7,9 @@ objects = { /* Begin PBXBuildFile section */ - 181C6C2A1C6A67B5009A8CA7 /* TestedClass.swift in Sources */ = {isa = PBXBuildFile; fileRef = 181C6C281C6A6591009A8CA7 /* TestedClass.swift */; }; 183D03FF1C4691C600EBAEF3 /* Cuckoo.h in Headers */ = {isa = PBXBuildFile; fileRef = 183D03FE1C4691C600EBAEF3 /* Cuckoo.h */; settings = {ATTRIBUTES = (Public, ); }; }; 183D04061C4691C600EBAEF3 /* Cuckoo.framework in Frameworks */ = {isa = PBXBuildFile; fileRef = 183D03FB1C4691C600EBAEF3 /* Cuckoo.framework */; }; 183D04161C46926A00EBAEF3 /* CuckooFunctions.swift in Sources */ = {isa = PBXBuildFile; fileRef = 183D04151C46926A00EBAEF3 /* CuckooFunctions.swift */; }; - 1890298B1C4C318A002FF826 /* CuckooAPITest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 183D040A1C4691C600EBAEF3 /* CuckooAPITest.swift */; }; - 1894D0F21C4D09CF00879512 /* TestedProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1894D0F01C4D09AB00879512 /* TestedProtocol.swift */; }; - 1894D0F71C4D127D00879512 /* GeneratedMocks.swift in Sources */ = {isa = PBXBuildFile; fileRef = 1894D0F51C4D123000879512 /* GeneratedMocks.swift */; }; - 18F354A31D0747530053E119 /* DescriptionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18F354A11D0745D20053E119 /* DescriptionTest.swift */; }; - 18F354A61D0749C90053E119 /* SelfDescribingTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = 18F354A41D0748C50053E119 /* SelfDescribingTest.swift */; }; DC4094EE1D211563006FB137 /* StubFunction.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC4094EC1D211563006FB137 /* StubFunction.swift */; }; DC4094EF1D211563006FB137 /* StubThrowingFunction.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC4094ED1D211563006FB137 /* StubThrowingFunction.swift */; }; DC4094F31D211598006FB137 /* ToBeStubbedProperty.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC4094F11D211598006FB137 /* ToBeStubbedProperty.swift */; }; @@ -37,6 +31,27 @@ DC40952C1D2A5155006FB137 /* CallMatcher.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC40952B1D2A5155006FB137 /* CallMatcher.swift */; }; DC5600F11CFAD4A4001F339D /* __DoNotUse.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC5600EF1CFAD4A4001F339D /* __DoNotUse.swift */; }; DC5A3A5D1CF6F8D600F520E3 /* Cuckoo.podspec in Resources */ = {isa = PBXBuildFile; fileRef = DC5A3A5C1CF6F8D600F520E3 /* Cuckoo.podspec */; }; + DC70D0A81D2AB5B700014C5F /* CuckooFunctionsTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0A61D2AB5B300014C5F /* CuckooFunctionsTest.swift */; }; + DC70D0AB1D2AB5F800014C5F /* ClassTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0A91D2AB5F500014C5F /* ClassTest.swift */; }; + DC70D0AD1D2AB62100014C5F /* ProtocolTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0AC1D2AB62100014C5F /* ProtocolTest.swift */; }; + DC70D0AF1D2AB64A00014C5F /* ParameterMatcherFunctionsTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0AE1D2AB64A00014C5F /* ParameterMatcherFunctionsTest.swift */; }; + DC70D0B11D2AB67000014C5F /* CallMatcherFunctionsTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0B01D2AB67000014C5F /* CallMatcherFunctionsTest.swift */; }; + DC70D0B31D2AB6B900014C5F /* MatchableTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0B21D2AB6B900014C5F /* MatchableTest.swift */; }; + DC70D0B41D2AB70F00014C5F /* SelfDescribingTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0A31D2AB58700014C5F /* SelfDescribingTest.swift */; }; + DC70D0B51D2AB71200014C5F /* DescriptionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0A21D2AB58700014C5F /* DescriptionTest.swift */; }; + DC70D0B81D2ABA3100014C5F /* TestUtils.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0B71D2ABA3100014C5F /* TestUtils.swift */; }; + DC70D0BE1D2AF40800014C5F /* TestedClass.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0BB1D2AF40800014C5F /* TestedClass.swift */; }; + DC70D0BF1D2AF40800014C5F /* TestedProtocol.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0BC1D2AF40800014C5F /* TestedProtocol.swift */; }; + DC70D0C21D2AF4FF00014C5F /* ArgumentCaptorTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0C11D2AF4FF00014C5F /* ArgumentCaptorTest.swift */; }; + DC70D0C51D2AFA8E00014C5F /* StubFunctionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0C41D2AFA8E00014C5F /* StubFunctionTest.swift */; }; + DC70D0C91D2AFAD200014C5F /* StubNoReturnFunctionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0C81D2AFAD200014C5F /* StubNoReturnFunctionTest.swift */; }; + DC70D0CB1D2AFAF200014C5F /* StubNoReturnThrowingFunctionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0CA1D2AFAF200014C5F /* StubNoReturnThrowingFunctionTest.swift */; }; + DC70D0CD1D2AFB1100014C5F /* StubThrowingFunctionTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0CC1D2AFB1100014C5F /* StubThrowingFunctionTest.swift */; }; + DC70D0CF1D2AFD0D00014C5F /* StubbingTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0CE1D2AFD0D00014C5F /* StubbingTest.swift */; }; + DC70D0D21D2B007300014C5F /* GeneratedMocks.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0D11D2B007300014C5F /* GeneratedMocks.swift */; }; + DC70D0D41D2B026200014C5F /* VerificationTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0D31D2B026200014C5F /* VerificationTest.swift */; }; + DC70D0D61D2B9FBE00014C5F /* ParameterMatcherTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0D51D2B9FBE00014C5F /* ParameterMatcherTest.swift */; }; + DC70D0D81D2B9FD400014C5F /* CallMatcherTest.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC70D0D71D2B9FD400014C5F /* CallMatcherTest.swift */; }; DC9EF9FE1CFAD4F10034DFE5 /* Stub.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC9EF9FD1CFAD4F10034DFE5 /* Stub.swift */; }; DC9EFA001CFAD5660034DFE5 /* StubCall.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC9EF9FF1CFAD5660034DFE5 /* StubCall.swift */; }; DC9EFA1A1CFADAD70034DFE5 /* Matchable.swift in Sources */ = {isa = PBXBuildFile; fileRef = DC9EFA161CFADAD70034DFE5 /* Matchable.swift */; }; @@ -61,18 +76,12 @@ /* End PBXContainerItemProxy section */ /* Begin PBXFileReference section */ - 181C6C281C6A6591009A8CA7 /* TestedClass.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = TestedClass.swift; sourceTree = ""; }; 183D03FB1C4691C600EBAEF3 /* Cuckoo.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = Cuckoo.framework; sourceTree = BUILT_PRODUCTS_DIR; }; 183D03FE1C4691C600EBAEF3 /* Cuckoo.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = Cuckoo.h; sourceTree = ""; }; 183D04001C4691C600EBAEF3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 183D04051C4691C600EBAEF3 /* CuckooTests.xctest */ = {isa = PBXFileReference; explicitFileType = wrapper.cfbundle; includeInIndex = 0; path = CuckooTests.xctest; sourceTree = BUILT_PRODUCTS_DIR; }; - 183D040A1C4691C600EBAEF3 /* CuckooAPITest.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = CuckooAPITest.swift; sourceTree = ""; }; 183D040C1C4691C600EBAEF3 /* Info.plist */ = {isa = PBXFileReference; lastKnownFileType = text.plist.xml; path = Info.plist; sourceTree = ""; }; 183D04151C46926A00EBAEF3 /* CuckooFunctions.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CuckooFunctions.swift; sourceTree = ""; }; - 1894D0F01C4D09AB00879512 /* TestedProtocol.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = TestedProtocol.swift; sourceTree = ""; }; - 1894D0F51C4D123000879512 /* GeneratedMocks.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = GeneratedMocks.swift; sourceTree = ""; }; - 18F354A11D0745D20053E119 /* DescriptionTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = DescriptionTest.swift; sourceTree = ""; }; - 18F354A41D0748C50053E119 /* SelfDescribingTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = SelfDescribingTest.swift; sourceTree = ""; }; DC4094EC1D211563006FB137 /* StubFunction.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubFunction.swift; path = Stubbing/StubFunction/StubFunction.swift; sourceTree = ""; }; DC4094ED1D211563006FB137 /* StubThrowingFunction.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubThrowingFunction.swift; path = Stubbing/StubFunction/StubThrowingFunction.swift; sourceTree = ""; }; DC4094F11D211598006FB137 /* ToBeStubbedProperty.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = ToBeStubbedProperty.swift; path = Stubbing/ToBeStubbedProperty/ToBeStubbedProperty.swift; sourceTree = ""; }; @@ -94,6 +103,27 @@ DC40952B1D2A5155006FB137 /* CallMatcher.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = CallMatcher.swift; path = Matching/CallMatcher.swift; sourceTree = ""; }; DC5600EF1CFAD4A4001F339D /* __DoNotUse.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = __DoNotUse.swift; path = verification/__DoNotUse.swift; sourceTree = ""; }; DC5A3A5C1CF6F8D600F520E3 /* Cuckoo.podspec */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = text; path = Cuckoo.podspec; sourceTree = ""; }; + DC70D0A21D2AB58700014C5F /* DescriptionTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = DescriptionTest.swift; path = Describing/DescriptionTest.swift; sourceTree = ""; }; + DC70D0A31D2AB58700014C5F /* SelfDescribingTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = SelfDescribingTest.swift; path = Describing/SelfDescribingTest.swift; sourceTree = ""; }; + DC70D0A61D2AB5B300014C5F /* CuckooFunctionsTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = CuckooFunctionsTest.swift; sourceTree = ""; }; + DC70D0A91D2AB5F500014C5F /* ClassTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ClassTest.swift; sourceTree = ""; }; + DC70D0AC1D2AB62100014C5F /* ProtocolTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = ProtocolTest.swift; sourceTree = ""; }; + DC70D0AE1D2AB64A00014C5F /* ParameterMatcherFunctionsTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = ParameterMatcherFunctionsTest.swift; path = Matching/ParameterMatcherFunctionsTest.swift; sourceTree = ""; }; + DC70D0B01D2AB67000014C5F /* CallMatcherFunctionsTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = CallMatcherFunctionsTest.swift; path = Matching/CallMatcherFunctionsTest.swift; sourceTree = ""; }; + DC70D0B21D2AB6B900014C5F /* MatchableTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = MatchableTest.swift; path = Matching/MatchableTest.swift; sourceTree = ""; }; + DC70D0B71D2ABA3100014C5F /* TestUtils.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; path = TestUtils.swift; sourceTree = ""; }; + DC70D0BB1D2AF40800014C5F /* TestedClass.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = TestedClass.swift; path = Source/TestedClass.swift; sourceTree = ""; }; + DC70D0BC1D2AF40800014C5F /* TestedProtocol.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = TestedProtocol.swift; path = Source/TestedProtocol.swift; sourceTree = ""; }; + DC70D0C11D2AF4FF00014C5F /* ArgumentCaptorTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = ArgumentCaptorTest.swift; path = Verification/ArgumentCaptorTest.swift; sourceTree = ""; }; + DC70D0C41D2AFA8E00014C5F /* StubFunctionTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubFunctionTest.swift; path = Stubbing/StubFunctionTest.swift; sourceTree = ""; }; + DC70D0C81D2AFAD200014C5F /* StubNoReturnFunctionTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubNoReturnFunctionTest.swift; path = Stubbing/StubNoReturnFunctionTest.swift; sourceTree = ""; }; + DC70D0CA1D2AFAF200014C5F /* StubNoReturnThrowingFunctionTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubNoReturnThrowingFunctionTest.swift; path = Stubbing/StubNoReturnThrowingFunctionTest.swift; sourceTree = ""; }; + DC70D0CC1D2AFB1100014C5F /* StubThrowingFunctionTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubThrowingFunctionTest.swift; path = Stubbing/StubThrowingFunctionTest.swift; sourceTree = ""; }; + DC70D0CE1D2AFD0D00014C5F /* StubbingTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubbingTest.swift; path = Stubbing/StubbingTest.swift; sourceTree = ""; }; + DC70D0D11D2B007300014C5F /* GeneratedMocks.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = GeneratedMocks.swift; path = Generated/GeneratedMocks.swift; sourceTree = ""; }; + DC70D0D31D2B026200014C5F /* VerificationTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = VerificationTest.swift; path = Verification/VerificationTest.swift; sourceTree = ""; }; + DC70D0D51D2B9FBE00014C5F /* ParameterMatcherTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = ParameterMatcherTest.swift; path = Matching/ParameterMatcherTest.swift; sourceTree = ""; }; + DC70D0D71D2B9FD400014C5F /* CallMatcherTest.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = CallMatcherTest.swift; path = Matching/CallMatcherTest.swift; sourceTree = ""; }; DC9EF9FD1CFAD4F10034DFE5 /* Stub.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = Stub.swift; path = stubbing/Stub.swift; sourceTree = ""; }; DC9EF9FF1CFAD5660034DFE5 /* StubCall.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = StubCall.swift; path = stubbing/StubCall.swift; sourceTree = ""; }; DC9EFA161CFADAD70034DFE5 /* Matchable.swift */ = {isa = PBXFileReference; fileEncoding = 4; lastKnownFileType = sourcecode.swift; name = Matchable.swift; path = matching/Matchable.swift; sourceTree = ""; }; @@ -148,16 +178,16 @@ 183D03FD1C4691C600EBAEF3 /* Source */ = { isa = PBXGroup; children = ( - DC9EFA3A1CFC2FA30034DFE5 /* Mock */, - DC9EFA221CFADB8B0034DFE5 /* Describing */, - DC9EFA151CFADAA00034DFE5 /* Matching */, - DC5600EE1CFAD499001F339D /* Verification */, - DC5600E91CFAD467001F339D /* Stubbing */, 183D03FE1C4691C600EBAEF3 /* Cuckoo.h */, 183D04001C4691C600EBAEF3 /* Info.plist */, 183D04151C46926A00EBAEF3 /* CuckooFunctions.swift */, DC9EFA2C1CFAE16C0034DFE5 /* MockManager.swift */, DC9EFA451CFC43A70034DFE5 /* Utils.swift */, + DC9EFA221CFADB8B0034DFE5 /* Describing */, + DC9EFA151CFADAA00034DFE5 /* Matching */, + DC9EFA3A1CFC2FA30034DFE5 /* Mock */, + DC5600E91CFAD467001F339D /* Stubbing */, + DC5600EE1CFAD499001F339D /* Verification */, ); path = Source; sourceTree = ""; @@ -165,13 +195,17 @@ 183D04091C4691C600EBAEF3 /* Tests */ = { isa = PBXGroup; children = ( - 1894D0F51C4D123000879512 /* GeneratedMocks.swift */, - 183D040A1C4691C600EBAEF3 /* CuckooAPITest.swift */, 183D040C1C4691C600EBAEF3 /* Info.plist */, - 1894D0F01C4D09AB00879512 /* TestedProtocol.swift */, - 181C6C281C6A6591009A8CA7 /* TestedClass.swift */, - 18F354A11D0745D20053E119 /* DescriptionTest.swift */, - 18F354A41D0748C50053E119 /* SelfDescribingTest.swift */, + DC70D0A91D2AB5F500014C5F /* ClassTest.swift */, + DC70D0A61D2AB5B300014C5F /* CuckooFunctionsTest.swift */, + DC70D0AC1D2AB62100014C5F /* ProtocolTest.swift */, + DC70D0B71D2ABA3100014C5F /* TestUtils.swift */, + DC70D0A01D2AB53D00014C5F /* Describing */, + DC70D0D01D2B006200014C5F /* Generated */, + DC70D0A11D2AB54700014C5F /* Matching */, + DC70D0B91D2AF3FA00014C5F /* Source */, + DC70D0C31D2AFA3200014C5F /* Stubbing */, + DC70D0C01D2AF4E500014C5F /* Verification */, ); path = Tests; sourceTree = ""; @@ -179,11 +213,11 @@ DC4094EB1D211540006FB137 /* StubFunction */ = { isa = PBXGroup; children = ( - DC4094F51D21169B006FB137 /* Trait */, DC4094EC1D211563006FB137 /* StubFunction.swift */, - DC4094ED1D211563006FB137 /* StubThrowingFunction.swift */, DC4095061D2120E6006FB137 /* StubNoReturnFunction.swift */, DC4095071D2120E6006FB137 /* StubNoReturnThrowingFunction.swift */, + DC4094ED1D211563006FB137 /* StubThrowingFunction.swift */, + DC4094F51D21169B006FB137 /* Trait */, ); name = StubFunction; sourceTree = ""; @@ -200,12 +234,12 @@ DC4094F51D21169B006FB137 /* Trait */ = { isa = PBXGroup; children = ( - DC4095001D2120D0006FB137 /* StubFunctionThenDoNothingTrait.swift */, - DC4094F81D2116DA006FB137 /* StubFunctionThenThrowTrait.swift */, - DC4094F91D2116DA006FB137 /* StubFunctionThenCallRealImplementationTrait.swift */, - DC4094FA1D2116DA006FB137 /* StubFunctionThenReturnTrait.swift */, - DC4094FB1D2116DA006FB137 /* StubFunctionThenTrait.swift */, DC4094F61D2116B1006FB137 /* BaseStubFunctionTrait.swift */, + DC4094F91D2116DA006FB137 /* StubFunctionThenCallRealImplementationTrait.swift */, + DC4095001D2120D0006FB137 /* StubFunctionThenDoNothingTrait.swift */, + DC4094FA1D2116DA006FB137 /* StubFunctionThenReturnTrait.swift */, + DC4094F81D2116DA006FB137 /* StubFunctionThenThrowTrait.swift */, + DC4094FB1D2116DA006FB137 /* StubFunctionThenTrait.swift */, ); name = Trait; sourceTree = ""; @@ -222,11 +256,11 @@ DC5600E91CFAD467001F339D /* Stubbing */ = { isa = PBXGroup; children = ( - DC4094F01D21158B006FB137 /* ToBeStubbedProperty */, - DC4094EB1D211540006FB137 /* StubFunction */, - DC9EFA411CFC31B10034DFE5 /* StubAction.swift */, DC9EF9FD1CFAD4F10034DFE5 /* Stub.swift */, + DC9EFA411CFC31B10034DFE5 /* StubAction.swift */, DC9EF9FF1CFAD5660034DFE5 /* StubCall.swift */, + DC4094EB1D211540006FB137 /* StubFunction */, + DC4094F01D21158B006FB137 /* ToBeStubbedProperty */, ); name = Stubbing; sourceTree = ""; @@ -234,21 +268,80 @@ DC5600EE1CFAD499001F339D /* Verification */ = { isa = PBXGroup; children = ( - DC40951C1D294899006FB137 /* VerifyProperty */, DC5600EF1CFAD4A4001F339D /* __DoNotUse.swift */, DC40950A1D23A813006FB137 /* ArgumentCaptor.swift */, + DC40951C1D294899006FB137 /* VerifyProperty */, ); name = Verification; sourceTree = ""; }; + DC70D0A01D2AB53D00014C5F /* Describing */ = { + isa = PBXGroup; + children = ( + DC70D0A21D2AB58700014C5F /* DescriptionTest.swift */, + DC70D0A31D2AB58700014C5F /* SelfDescribingTest.swift */, + ); + name = Describing; + sourceTree = ""; + }; + DC70D0A11D2AB54700014C5F /* Matching */ = { + isa = PBXGroup; + children = ( + DC70D0B01D2AB67000014C5F /* CallMatcherFunctionsTest.swift */, + DC70D0D71D2B9FD400014C5F /* CallMatcherTest.swift */, + DC70D0B21D2AB6B900014C5F /* MatchableTest.swift */, + DC70D0AE1D2AB64A00014C5F /* ParameterMatcherFunctionsTest.swift */, + DC70D0D51D2B9FBE00014C5F /* ParameterMatcherTest.swift */, + ); + name = Matching; + sourceTree = ""; + }; + DC70D0B91D2AF3FA00014C5F /* Source */ = { + isa = PBXGroup; + children = ( + DC70D0BB1D2AF40800014C5F /* TestedClass.swift */, + DC70D0BC1D2AF40800014C5F /* TestedProtocol.swift */, + ); + name = Source; + sourceTree = ""; + }; + DC70D0C01D2AF4E500014C5F /* Verification */ = { + isa = PBXGroup; + children = ( + DC70D0C11D2AF4FF00014C5F /* ArgumentCaptorTest.swift */, + DC70D0D31D2B026200014C5F /* VerificationTest.swift */, + ); + name = Verification; + sourceTree = ""; + }; + DC70D0C31D2AFA3200014C5F /* Stubbing */ = { + isa = PBXGroup; + children = ( + DC70D0C41D2AFA8E00014C5F /* StubFunctionTest.swift */, + DC70D0C81D2AFAD200014C5F /* StubNoReturnFunctionTest.swift */, + DC70D0CA1D2AFAF200014C5F /* StubNoReturnThrowingFunctionTest.swift */, + DC70D0CC1D2AFB1100014C5F /* StubThrowingFunctionTest.swift */, + DC70D0CE1D2AFD0D00014C5F /* StubbingTest.swift */, + ); + name = Stubbing; + sourceTree = ""; + }; + DC70D0D01D2B006200014C5F /* Generated */ = { + isa = PBXGroup; + children = ( + DC70D0D11D2B007300014C5F /* GeneratedMocks.swift */, + ); + name = Generated; + sourceTree = ""; + }; DC9EFA151CFADAA00034DFE5 /* Matching */ = { isa = PBXGroup; children = ( + DC40952B1D2A5155006FB137 /* CallMatcher.swift */, + DC4095271D2A50CC006FB137 /* CallMatcherFunctions.swift */, DC9EFA161CFADAD70034DFE5 /* Matchable.swift */, DC4095291D2A5143006FB137 /* ParameterMatcher.swift */, DC4095251D2A50BE006FB137 /* ParameterMatcherFunctions.swift */, - DC4095271D2A50CC006FB137 /* CallMatcherFunctions.swift */, - DC40952B1D2A5155006FB137 /* CallMatcher.swift */, ); name = Matching; sourceTree = ""; @@ -384,14 +477,14 @@ files = ( ); inputPaths = ( - "$(SRCROOT)/Tests/TestedProtocol.swift", + "$(SRCROOT)/Tests/Source/TestedProtocol.swift", ); name = "Generate mocks"; outputPaths = ( ); runOnlyForDeploymentPostprocessing = 0; shellPath = /bin/sh; - shellScript = "./run generate --output \"$PROJECT_DIR/Tests/GeneratedMocks.swift\" \"$PROJECT_DIR/Tests/TestedClass.swift\""; + shellScript = "./run generate --output \"$PROJECT_DIR/Tests/Generated/GeneratedMocks.swift\" \"$PROJECT_DIR/Tests/Source/TestedClass.swift\""; }; /* End PBXShellScriptBuildPhase section */ @@ -439,12 +532,27 @@ isa = PBXSourcesBuildPhase; buildActionMask = 2147483647; files = ( - 1894D0F21C4D09CF00879512 /* TestedProtocol.swift in Sources */, - 18F354A61D0749C90053E119 /* SelfDescribingTest.swift in Sources */, - 1894D0F71C4D127D00879512 /* GeneratedMocks.swift in Sources */, - 1890298B1C4C318A002FF826 /* CuckooAPITest.swift in Sources */, - 18F354A31D0747530053E119 /* DescriptionTest.swift in Sources */, - 181C6C2A1C6A67B5009A8CA7 /* TestedClass.swift in Sources */, + DC70D0C21D2AF4FF00014C5F /* ArgumentCaptorTest.swift in Sources */, + DC70D0C91D2AFAD200014C5F /* StubNoReturnFunctionTest.swift in Sources */, + DC70D0CD1D2AFB1100014C5F /* StubThrowingFunctionTest.swift in Sources */, + DC70D0B51D2AB71200014C5F /* DescriptionTest.swift in Sources */, + DC70D0CB1D2AFAF200014C5F /* StubNoReturnThrowingFunctionTest.swift in Sources */, + DC70D0B81D2ABA3100014C5F /* TestUtils.swift in Sources */, + DC70D0B11D2AB67000014C5F /* CallMatcherFunctionsTest.swift in Sources */, + DC70D0BF1D2AF40800014C5F /* TestedProtocol.swift in Sources */, + DC70D0CF1D2AFD0D00014C5F /* StubbingTest.swift in Sources */, + DC70D0AF1D2AB64A00014C5F /* ParameterMatcherFunctionsTest.swift in Sources */, + DC70D0D61D2B9FBE00014C5F /* ParameterMatcherTest.swift in Sources */, + DC70D0AB1D2AB5F800014C5F /* ClassTest.swift in Sources */, + DC70D0B31D2AB6B900014C5F /* MatchableTest.swift in Sources */, + DC70D0BE1D2AF40800014C5F /* TestedClass.swift in Sources */, + DC70D0D21D2B007300014C5F /* GeneratedMocks.swift in Sources */, + DC70D0D41D2B026200014C5F /* VerificationTest.swift in Sources */, + DC70D0AD1D2AB62100014C5F /* ProtocolTest.swift in Sources */, + DC70D0C51D2AFA8E00014C5F /* StubFunctionTest.swift in Sources */, + DC70D0D81D2B9FD400014C5F /* CallMatcherTest.swift in Sources */, + DC70D0B41D2AB70F00014C5F /* SelfDescribingTest.swift in Sources */, + DC70D0A81D2AB5B700014C5F /* CuckooFunctionsTest.swift in Sources */, ); runOnlyForDeploymentPostprocessing = 0; }; diff --git a/Source/Matching/CallMatcher.swift b/Source/Matching/CallMatcher.swift index 31d7c7b..f522e06 100644 --- a/Source/Matching/CallMatcher.swift +++ b/Source/Matching/CallMatcher.swift @@ -13,9 +13,9 @@ public struct CallMatcher { self.matchesFunction = matchesFunction } - public init(numberOfExpectedCalls: Int, compareCallsFunction: (Int, Int) -> Bool) { + public init(numberOfExpectedCalls: Int, compareCallsFunction: (expected: Int, actual: Int) -> Bool) { self.matchesFunction = { - return compareCallsFunction(numberOfExpectedCalls, $0.count) + return compareCallsFunction(expected: numberOfExpectedCalls, actual: $0.count) } } @@ -26,4 +26,16 @@ public struct CallMatcher { return false } } + + public func or(otherMatcher: CallMatcher) -> CallMatcher { + return CallMatcher { + return self.matches($0) || otherMatcher.matches($0) + } + } + + public func and(otherMatcher: CallMatcher) -> CallMatcher { + return CallMatcher { + return self.matches($0) && otherMatcher.matches($0) + } + } } \ No newline at end of file diff --git a/Source/Matching/CallMatcherFunctions.swift b/Source/Matching/CallMatcherFunctions.swift index b45d23f..ad5d870 100644 --- a/Source/Matching/CallMatcherFunctions.swift +++ b/Source/Matching/CallMatcherFunctions.swift @@ -27,11 +27,11 @@ public func atLeastOnce() -> CallMatcher { /// Returns a matcher ensuring call was made at least `count` times. @warn_unused_result public func atLeast(count: Int) -> CallMatcher { - return CallMatcher(numberOfExpectedCalls: count, compareCallsFunction: >=) + return CallMatcher(numberOfExpectedCalls: count, compareCallsFunction: <=) } /// Returns a matcher ensuring call was made at most `count` times. @warn_unused_result public func atMost(count: Int) -> CallMatcher { - return CallMatcher(numberOfExpectedCalls: count, compareCallsFunction: <=) + return CallMatcher(numberOfExpectedCalls: count, compareCallsFunction: >=) } diff --git a/Source/Matching/Matchable.swift b/Source/Matching/Matchable.swift index f253ba0..432df10 100644 --- a/Source/Matching/Matchable.swift +++ b/Source/Matching/Matchable.swift @@ -18,13 +18,13 @@ public protocol Matchable { } public extension Matchable { - public func or(otherMatchable: Self) -> ParameterMatcher { + public func or(otherMatchable: M) -> ParameterMatcher { return ParameterMatcher { return self.matcher.matches($0) || otherMatchable.matcher.matches($0) } } - public func and(otherMatchable: Self) -> ParameterMatcher { + public func and(otherMatchable: M) -> ParameterMatcher { return ParameterMatcher { return self.matcher.matches($0) && otherMatchable.matcher.matches($0) } diff --git a/Source/Matching/ParameterMatcherFunctions.swift b/Source/Matching/ParameterMatcherFunctions.swift index 61b16ca..a4b19dc 100644 --- a/Source/Matching/ParameterMatcherFunctions.swift +++ b/Source/Matching/ParameterMatcherFunctions.swift @@ -56,18 +56,18 @@ public func anyString() -> ParameterMatcher { return ParameterMatcher() } -/// Returns a matcher matching any T value or nil. -@warn_unused_result -public func any(type: T.Type = T.self) -> ParameterMatcher { - return ParameterMatcher() -} - /// Returns a matcher matching any closure. @warn_unused_result public func anyClosure() -> ParameterMatcher OUT> { return ParameterMatcher() } +/// Returns a matcher matching any T value or nil. +@warn_unused_result +public func any(type: T.Type = T.self) -> ParameterMatcher { + return ParameterMatcher() +} + /// Returns an equality matcher. A shorthand for `equalTo`. @warn_unused_result public func eq(value: T?) -> ParameterMatcher { diff --git a/Source/MockManager.swift b/Source/MockManager.swift index d7cbc00..316a009 100644 --- a/Source/MockManager.swift +++ b/Source/MockManager.swift @@ -9,6 +9,8 @@ import XCTest public class MockManager { + static var fail: (message: String, file: StaticString, line: UInt) -> () = XCTFail + private var stubs: [Stub] = [] private var stubCalls: [StubCall] = [] private var unverifiedStubCallsIndexes: [Int] = [] @@ -51,16 +53,16 @@ public class MockManager { if let original = original { return try original(parameters) } else { - fail("No real implementation found for method `\(method)`. This may happend because stubbed object is mock or spy of protocol.") + failAndCrash("No real implementation found for method `\(method)`. This may happend because stubbed object is mock or spy of protocol.") } } } else { - fail("Stubbing of method `\(method)` using parameters \(parameters) wasn't finished (missing thenReturn()).") + failAndCrash("Stubbing of method `\(method)` using parameters \(parameters) wasn't finished (missing thenReturn()).") } } else if let original = original { return try original(parameters) } else { - fail("No stub for method `\(method)` using parameters \(parameters) and no original implementation was provided.") + failAndCrash("No stub for method `\(method)` using parameters \(parameters) and no original implementation was provided.") } } @@ -83,7 +85,7 @@ public class MockManager { if callMatcher.matches(calls) == false { let description = Description() - XCTFail(description.description, file: sourceLocation.file, line: sourceLocation.line) + MockManager.fail(message: description.description, file: sourceLocation.file, line: sourceLocation.line) } return __DoNotUse() } @@ -105,13 +107,13 @@ public class MockManager { func verifyNoMoreInteractions(sourceLocation: SourceLocation) { if unverifiedStubCallsIndexes.isEmpty == false { let unverifiedCalls = unverifiedStubCallsIndexes.map { stubCalls[$0] }.map { String($0) }.joinWithSeparator(", ") - XCTFail("Found unverified call(s): " + unverifiedCalls, file: sourceLocation.file, line: sourceLocation.line) + MockManager.fail(message: "Found unverified call(s): " + unverifiedCalls, file: sourceLocation.file, line: sourceLocation.line) } } @noreturn - private func fail(message: String) { - XCTFail(message) + private func failAndCrash(message: String, file: StaticString = #file, line: UInt = #line) { + MockManager.fail(message: message, file: file, line: line) fatalError(message) } } diff --git a/Source/Utils.swift b/Source/Utils.swift index a4e161e..8899ca5 100644 --- a/Source/Utils.swift +++ b/Source/Utils.swift @@ -22,7 +22,7 @@ public func markerFunction(input: IN.Type = IN.self, _ output: OUT.Type } } -// TODO Refactor +// TODO Refactor wrapMatchable public func parameterMatcher(matcher: ParameterMatcher, mapping: IN -> PARAM) -> ParameterMatcher { return ParameterMatcher { return matcher.matches(mapping($0)) diff --git a/Tests/ClassTest.swift b/Tests/ClassTest.swift new file mode 100644 index 0000000..85a53a5 --- /dev/null +++ b/Tests/ClassTest.swift @@ -0,0 +1,150 @@ +// +// ClassTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class ClassTest: XCTestCase { + + private var mock: MockTestedClass! + + override func setUp() { + super.setUp() + + mock = MockTestedClass() + } + + func testReadOnlyProperty() { + stub(mock) { mock in + when(mock.readOnlyProperty.get).thenReturn("a") + } + + XCTAssertEqual(mock.readOnlyProperty, "a") + verify(mock).readOnlyProperty.get + } + + func testReadWriteProperty() { + var called = false + stub(mock) { mock in + when(mock.readWriteProperty.get).thenReturn(1) + when(mock.readWriteProperty.set(anyInt())).then { _ in called = true } + } + + mock.readWriteProperty = 0 + + XCTAssertEqual(mock.readWriteProperty, 1) + XCTAssertTrue(called) + verify(mock).readWriteProperty.get + verify(mock).readWriteProperty.set(0) + } + + func testOptionalProperty() { + var called = false + stub(mock) { mock in + when(mock.optionalProperty.get).thenReturn(nil) + when(mock.optionalProperty.set(anyInt())).then { _ in called = true } + } + + mock.optionalProperty = 0 + + XCTAssertNil(mock.optionalProperty) + XCTAssertTrue(called) + verify(mock).optionalProperty.get + verify(mock).optionalProperty.set(eq(0)) + } + + func testNoReturn() { + var called = false + stub(mock) { mock in + when(mock.noReturn()).then { _ in called = true } + } + + mock.noReturn() + + XCTAssertTrue(called) + verify(mock).noReturn() + } + + func testCountCharacters() { + stub(mock) { mock in + when(mock.countCharacters("a")).thenReturn(1) + } + + XCTAssertEqual(mock.countCharacters("a"), 1) + verify(mock).countCharacters("a") + } + + func testWithThrows() { + stub(mock) { mock in + when(mock.withThrows()).thenThrow(TestError.Unknown) + } + + var catched = false + do { + try mock.withThrows() + } catch { + catched = true + } + + XCTAssertTrue(catched) + verify(mock).withThrows() + } + + func testWithNoReturnThrows() { + stub(mock) { mock in + when(mock.withNoReturnThrows()).thenThrow(TestError.Unknown) + } + + var catched = false + do { + try mock.withNoReturnThrows() + } catch { + catched = true + } + + XCTAssertTrue(catched) + verify(mock).withNoReturnThrows() + } + + func testWithClosure() { + stub(mock) { mock in + when(mock.withClosure(anyClosure())).thenReturn(0) + } + + XCTAssertEqual(mock.withClosure { _ in 1 }, 0) + verify(mock).withClosure(anyClosure()) + } + + func testWithNoescape() { + var called = false + stub(mock) { mock in + when(mock.withNoescape(anyString(), closure: anyClosure())).then { _ in called = true } + } + + mock.withNoescape("a") { _ in 1 } + + XCTAssertTrue(called) + verify(mock).withNoescape(anyString(), closure: anyClosure()) + } + + func testWithOptionalClosure() { + var called = false + stub(mock) { mock in + when(mock.withOptionalClosure(anyString(), closure: anyClosure())).then { _ in called = true } + } + + mock.withOptionalClosure("a") { _ in 1 } + + XCTAssertTrue(called) + verify(mock).withOptionalClosure(anyString(), closure: anyClosure()) + } + + private enum TestError: ErrorType { + case Unknown + } +} diff --git a/Tests/CuckooAPITest.swift b/Tests/CuckooAPITest.swift deleted file mode 100644 index d2459dc..0000000 --- a/Tests/CuckooAPITest.swift +++ /dev/null @@ -1,302 +0,0 @@ -// -// CuckooAPITest.swift -// CuckooTests -// -// Created by Tadeas Kriz on 13/01/16. -// Copyright © 2016 Brightify. All rights reserved. -// - -import XCTest -import Cuckoo - -class CuckooAPITest: XCTestCase { - - func testProtocol() { - let mock = MockTestedProtocol() - - // FIXME Should be fatalError when method was not throwing - - stub(mock) { mock in - when(mock.readOnlyProperty.get).thenReturn("properties!") - when(mock.readWriteProperty.get).thenReturn(10) - when(mock.readWriteProperty.set(anyInt())).then { - print($0) - } - when(mock.optionalProperty.set(equalTo(nil))).then { _ in - when(mock.optionalProperty.get).thenReturn(nil) - } - when(mock.optionalProperty.set(anyInt())).then { _ in - - when(mock.optionalProperty.get).thenReturn(10) - } - when(mock.optionalProperty.set(eq(1))).then { _ in - when(mock.optionalProperty.get).thenReturn(1) - } - - when(mock.noParameter()).thenDoNothing() - when(mock.countCharacters("hello")).thenReturn(1000) - when(mock.withReturn()).thenReturn("hello world!") - when(mock.withThrows()).thenThrow(TestError.Unknown) - - when(mock.withClosure(anyClosure())).then { - $0("hello world") - } - when(mock.withClosureReturningInt(anyClosure())).thenReturn(1000) - when(mock.withNoescape("hello", closure: anyClosure())).then { - $1($0 + " world") - } - when(mock.withOptionalClosure("hello", closure: anyClosure())).then { - $1?($0 + " world") - } - } - - XCTAssertEqual(mock.readOnlyProperty, "properties!") - XCTAssertEqual(mock.readWriteProperty, 10) - mock.readWriteProperty = 400 - XCTAssertEqual(mock.readWriteProperty, 10) - - mock.optionalProperty = nil - XCTAssertNil(mock.optionalProperty) - mock.optionalProperty = 5 - XCTAssertEqual(mock.optionalProperty, 10) - mock.optionalProperty = 1 - XCTAssertEqual(mock.optionalProperty, 1) - - mock.noParameter() - - XCTAssertEqual(mock.countCharacters("hello"), 1000) - - XCTAssertEqual(mock.withReturn(), "hello world!") - - XCTAssertEqual(mock.withClosureReturningInt { _ in 10 }, 1000) - - var helloWorld: String = "" - mock.withClosure { - helloWorld = $0 - return 10 - } - XCTAssertEqual(helloWorld, "hello world") - - // Calling @noescape closure is not currently supported - /*var helloWorld: String = "" - mock.withNoescape("hello") { - helloWorld = $0 - } - XCTAssertEqual(helloWorld, "hello world") - */ - - helloWorld = "" - mock.withOptionalClosure("hello") { - helloWorld = $0 - } - XCTAssertEqual(helloWorld, "hello world") - - verify(mock).readOnlyProperty.get - verify(mock, times(2)).readWriteProperty.get - verify(mock).readWriteProperty.set(400) - - verify(mock).noParameter() - verify(mock).countCharacters(eq("hello")) - verify(mock).withReturn() - verify(mock, never()).withThrows() - verify(mock).withClosureReturningInt(anyClosure()) - verify(mock).withOptionalClosure("hello", closure: anyClosure()) - } - - func testClass() { - let mock = MockTestedClass() - - stub(mock) { mock in - when(mock.readOnlyProperty.get).thenReturn("properties!") - when(mock.readWriteProperty.get).thenReturn(10) - when(mock.readWriteProperty.set(anyInt())).then { - print($0) - } - when(mock.optionalProperty.set(equalTo(nil))).then { _ in - when(mock.optionalProperty.get).thenReturn(nil) - } - when(mock.optionalProperty.set(anyInt())).then { _ in - when(mock.optionalProperty.get).thenReturn(10) - } - when(mock.optionalProperty.set(eq(1))).then { _ in - when(mock.optionalProperty.get).thenReturn(1) - } - - when(mock.noParameter()).thenDoNothing() - when(mock.countCharacters("hello")).thenReturn(1000) - when(mock.withReturn()).thenReturn("hello world!") - when(mock.withThrows()).thenThrow(TestError.Unknown) - - when(mock.withClosure(anyClosure())).then { - $0("hello world") - } - when(mock.withClosureReturningInt(anyClosure())).thenReturn(1000) - when(mock.withNoescape("hello", closure: anyClosure())).then { - $1($0 + " world") - } - when(mock.withOptionalClosure("hello", closure: anyClosure())).then { - $1?($0 + " world") - } - } - - XCTAssertEqual(mock.readOnlyProperty, "properties!") - XCTAssertEqual(mock.readWriteProperty, 10) - mock.readWriteProperty = 400 - XCTAssertEqual(mock.readWriteProperty, 10) - - mock.optionalProperty = nil - XCTAssertNil(mock.optionalProperty) - mock.optionalProperty = 5 - XCTAssertEqual(mock.optionalProperty, 10) - mock.optionalProperty = 1 - XCTAssertEqual(mock.optionalProperty, 1) - - mock.noParameter() - - XCTAssertEqual(mock.countCharacters("hello"), 1000) - - XCTAssertEqual(mock.withReturn(), "hello world!") - - XCTAssertEqual(mock.withClosureReturningInt { _ in 10 }, 1000) - - var helloWorld: String = "" - mock.withClosure { - helloWorld = $0 - return 10 - } - XCTAssertEqual(helloWorld, "hello world") - - // Calling @noescape closure is not currently supported - /*var helloWorld: String = "" - mock.withNoescape("hello") { - helloWorld = $0 - } - XCTAssertEqual(helloWorld, "hello world") - */ - - helloWorld = "" - mock.withOptionalClosure("hello") { - helloWorld = $0 - } - XCTAssertEqual(helloWorld, "hello world") - - verify(mock).readOnlyProperty.get - verify(mock, times(2)).readWriteProperty.get - verify(mock).readWriteProperty.set(400) - verify(mock).noParameter() - verify(mock).countCharacters(eq("hello")) - verify(mock).withReturn() - verify(mock, never()).withThrows() - verify(mock).withClosureReturningInt(anyClosure()) - verify(mock).withOptionalClosure("hello", closure: anyClosure()) - } - - func testReset() { - let mock = MockTestedClass(spyOn: TestedClass()) - stub(mock) { mock in - when(mock.countCharacters(anyString())).thenReturn(10) - } - XCTAssertEqual(mock.countCharacters("a"), 10) - - reset(mock) - - verify(mock, never()).countCharacters("a") - XCTAssertEqual(mock.countCharacters("a"), 1) - verify(mock).countCharacters("a") - } - - func testClearStubs() { - let mock = MockTestedClass(spyOn: TestedClass()) - stub(mock) { mock in - when(mock.countCharacters(anyString())).thenReturn(10) - } - XCTAssertEqual(mock.countCharacters("a"), 10) - - clearStubs(mock) - - verify(mock).countCharacters("a") - XCTAssertEqual(mock.countCharacters("a"), 1) - verify(mock, times(2)).countCharacters("a") - } - - func testClearInvocations() { - let mock = MockTestedClass(spyOn: TestedClass()) - stub(mock) { mock in - when(mock.countCharacters(anyString())).thenReturn(10) - } - XCTAssertEqual(mock.countCharacters("a"), 10) - - clearInvocations(mock) - - verify(mock, never()).countCharacters("a") - XCTAssertEqual(mock.countCharacters("a"), 10) - verify(mock).countCharacters("a") - } - - func testThenCallRealImplementation() { - let mock = MockTestedClass(spyOn: TestedClass()) - stub(mock) { mock in - when(mock.countCharacters("a")).thenReturn(10) - when(mock.countCharacters(anyString())).thenCallRealImplementation() - } - - XCTAssertEqual(mock.countCharacters("a"), 1) - } - - func testMultipleStubsInRow() { - let mock = MockTestedClass() - stub(mock) { mock in - when(mock.readOnlyProperty.get).thenReturn("a").thenReturn("b", "c") - } - - XCTAssertEqual(mock.readOnlyProperty, "a") - XCTAssertEqual(mock.readOnlyProperty, "b") - XCTAssertEqual(mock.readOnlyProperty, "c") - XCTAssertEqual(mock.readOnlyProperty, "c") - } - - func testThenDoNothing() { - let mock = MockTestedClass() - stub(mock) { mock in - when(mock.noParameter()).thenDoNothing() - when(mock.withThrows()).thenDoNothing() - } - - mock.noParameter() - try! mock.withThrows() - } - - func testVerifyNoMoreInteractions() { - let mock = MockTestedClass() - stub(mock) { mock in - when(mock.noParameter()).thenDoNothing() - } - - mock.noParameter() - verify(mock).noParameter() - - verifyNoMoreInteractions(mock) - } - - func testArgumentCaptor() { - let mock = MockTestedClass() - stub(mock) { mock in - when(mock.readWriteProperty.set(anyInt())).thenDoNothing() - } - mock.readWriteProperty = 10 - mock.readWriteProperty = 20 - mock.readWriteProperty = 30 - let captor = ArgumentCaptor() - - XCTAssertNil(captor.value) - XCTAssertTrue(captor.allValues.isEmpty) - - verify(mock, times(3)).readWriteProperty.set(captor.capture()) - XCTAssertEqual(captor.value, 30) - XCTAssertEqual(captor.allValues, [10, 20, 30]) - } - - private enum TestError: ErrorType { - case Unknown - } -} diff --git a/Tests/CuckooFunctionsTest.swift b/Tests/CuckooFunctionsTest.swift new file mode 100644 index 0000000..427faa4 --- /dev/null +++ b/Tests/CuckooFunctionsTest.swift @@ -0,0 +1,82 @@ +// +// CuckooFunctionsTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class CuckooFunctionsTest: XCTestCase { + + func testReset() { + let mock = MockTestedClass(spyOn: TestedClass()) + stub(mock) { mock in + when(mock.countCharacters(anyString())).thenReturn(10) + } + XCTAssertEqual(mock.countCharacters("a"), 10) + + reset(mock) + + verify(mock, never()).countCharacters("a") + XCTAssertEqual(mock.countCharacters("a"), 1) + verify(mock).countCharacters("a") + } + + func testClearStubs() { + let mock = MockTestedClass(spyOn: TestedClass()) + stub(mock) { mock in + when(mock.countCharacters(anyString())).thenReturn(10) + } + XCTAssertEqual(mock.countCharacters("a"), 10) + + clearStubs(mock) + + verify(mock).countCharacters("a") + XCTAssertEqual(mock.countCharacters("a"), 1) + verify(mock, times(2)).countCharacters("a") + } + + func testClearInvocations() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.countCharacters(anyString())).thenReturn(10) + } + XCTAssertEqual(mock.countCharacters("a"), 10) + + clearInvocations(mock) + + verify(mock, never()).countCharacters("a") + XCTAssertEqual(mock.countCharacters("a"), 10) + verify(mock).countCharacters("a") + } + + func testVerifyNoMoreInteractions() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.noReturn()).thenDoNothing() + } + + mock.noReturn() + verify(mock).noReturn() + + verifyNoMoreInteractions(mock) + } + + func testVerifyNoMoreInteractionsFail() { + let error = TestUtils.catchCuckooFail { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.noReturn()).thenDoNothing() + } + + mock.noReturn() + + verifyNoMoreInteractions(mock) + } + + XCTAssertNotNil(error) + } +} diff --git a/Tests/DescriptionTest.swift b/Tests/Describing/DescriptionTest.swift similarity index 98% rename from Tests/DescriptionTest.swift rename to Tests/Describing/DescriptionTest.swift index 22ebcf1..5c6fe41 100644 --- a/Tests/DescriptionTest.swift +++ b/Tests/Describing/DescriptionTest.swift @@ -23,7 +23,7 @@ class DescriptionTest: XCTestCase { let description = Description() test.appendTo(description) - + XCTAssertEqual(description.description, test.expected, test.message) } } diff --git a/Tests/SelfDescribingTest.swift b/Tests/Describing/SelfDescribingTest.swift similarity index 100% rename from Tests/SelfDescribingTest.swift rename to Tests/Describing/SelfDescribingTest.swift diff --git a/Tests/Matching/CallMatcherFunctionsTest.swift b/Tests/Matching/CallMatcherFunctionsTest.swift new file mode 100644 index 0000000..fd26386 --- /dev/null +++ b/Tests/Matching/CallMatcherFunctionsTest.swift @@ -0,0 +1,37 @@ +// +// CallMatcherFunctionsTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class CallMatcherFunctionsTest: XCTestCase { + private let tests: [(message: String, matcher: CallMatcher, argument: Int, expected: Bool)] = [ + ("times(2) - true", times(2), 2, true), + ("times(2) - false", times(2), 3, false), + ("never - true", never(), 0, true), + ("never - false", never(), 1, false), + ("atLeastOnce - 2", atLeastOnce(), 2, true), + ("atLeastOnce - 1", atLeastOnce(), 1, true), + ("atLeastOnce - 0", atLeastOnce(), 0, false), + ("atLeast(2) - 3", atLeast(2), 3, true), + ("atLeast(2) - 2", atLeast(2), 2, true), + ("atLeast(2) - 1", atLeast(2), 1, false), + ("atMost(2) - 1", atMost(2), 1, true), + ("atMost(2) - 2", atMost(2), 2, true), + ("atMost(2) - 3", atMost(2), 3, false) + ] + + func testParameterizedTests() { + let call: StubCall = ConcreteStubCall(method: "A", parameters: Void()) + tests.forEach { test in + let calls = (0.. 4 }) + + XCTAssertTrue(matcher.matches(5)) + XCTAssertFalse(matcher.matches(4)) + } + + func testBool() { + XCTAssertTrue(true.matcher.matches(true)) + XCTAssertFalse(true.matcher.matches(false)) + } + + func testInt() { + XCTAssertTrue(1.matcher.matches(1)) + XCTAssertFalse(1.matcher.matches(2)) + } + + func testString() { + XCTAssertTrue("a".matcher.matches("a")) + XCTAssertFalse("a".matcher.matches("b")) + } + + func testFloat() { + XCTAssertTrue(Float(1.1).matcher.matches(1.1)) + XCTAssertFalse(Float(1.1).matcher.matches(1.2)) + } + + func testDouble() { + XCTAssertTrue(1.1.matcher.matches(1.1)) + XCTAssertFalse(1.1.matcher.matches(1.2)) + } + + func testCharacter() { + XCTAssertTrue(Character("a").matcher.matches("a")) + XCTAssertFalse(Character("a").matcher.matches("b")) + } +} \ No newline at end of file diff --git a/Tests/Matching/ParameterMatcherFunctionsTest.swift b/Tests/Matching/ParameterMatcherFunctionsTest.swift new file mode 100644 index 0000000..b6a4d94 --- /dev/null +++ b/Tests/Matching/ParameterMatcherFunctionsTest.swift @@ -0,0 +1,134 @@ +// +// ParameterMatcherFunctionsTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class ParameterMatcherFunctionsTest: XCTestCase { + + func testEqualToEquatable() { + XCTAssertTrue(eq(1).matches(1)) + XCTAssertFalse(eq(1).matches(2)) + + XCTAssertTrue(equalTo(1).matches(1)) + XCTAssertFalse(equalTo(1).matches(2)) + } + + func testEqualToAnyObject() { + let x = X() + + XCTAssertTrue(eq(x).matches(x)) + XCTAssertFalse(eq(x).matches(X())) + + XCTAssertTrue(equalTo(x).matches(x)) + XCTAssertFalse(equalTo(x).matches(X())) + } + + func testEqualToWithFunction() { + let tuple = (1, 1) + let function = { (a: (Int, Int), b: (Int, Int)) -> Bool in + return a.0 == b.0 && a.1 == b.1 + } + + XCTAssertTrue(eq(tuple, equalWhen: function).matches((1, 1))) + XCTAssertFalse(eq(tuple, equalWhen: function).matches((1, 2))) + + XCTAssertTrue(equalTo(tuple, equalWhen: function).matches((1, 1))) + XCTAssertFalse(equalTo(tuple, equalWhen: function).matches((1, 2))) + } + + func testAnyInt() { + XCTAssertTrue(anyInt().matches(1)) + } + + func testAnyString() { + XCTAssertTrue(anyString().matches("a")) + } + + func testAny() { + XCTAssertTrue(any().matches(X())) + } + + func testAnyClosure() { + XCTAssertTrue(anyClosure().matches({ 0 })) + } + + func testOptionalEqualToEquatable() { + XCTAssertTrue(eq(nil as Int?).matches(nil)) + XCTAssertTrue(eq(1 as Int?).matches(1)) + XCTAssertFalse(equalTo(1 as Int?).matches(2)) + XCTAssertFalse(eq(nil).matches(1)) + + XCTAssertTrue(equalTo(nil as Int?).matches(nil)) + XCTAssertTrue(equalTo(1 as Int?).matches(1)) + XCTAssertFalse(equalTo(1 as Int?).matches(2)) + XCTAssertFalse(equalTo(nil).matches(1)) + } + + func testOptionalEqualToAnyObject() { + let x: X? = X() + + XCTAssertTrue(eq(nil as X?).matches(nil)) + XCTAssertTrue(eq(x).matches(x)) + XCTAssertFalse(eq(x).matches(X())) + XCTAssertFalse(eq(nil).matches(x)) + + XCTAssertTrue(eq(nil as X?).matches(nil)) + XCTAssertTrue(equalTo(x).matches(x)) + XCTAssertFalse(equalTo(x).matches(X())) + XCTAssertFalse(eq(nil).matches(x)) + } + + func testOptionalEqualToWithFunction() { + let tuple: (Int, Int)? = (1, 1) + let function = { (a: (Int, Int)?, b: (Int, Int)?) -> Bool in + guard let x = a, let y = b else { + return a == nil && b == nil + } + return x.0 == y.0 && x.1 == y.1 + } + + XCTAssertTrue(eq(nil, equalWhen: function).matches(nil)) + XCTAssertTrue(eq(tuple, equalWhen: function).matches((1, 1))) + XCTAssertFalse(eq(tuple, equalWhen: function).matches((1, 2))) + XCTAssertFalse(eq(nil, equalWhen: function).matches(tuple)) + + XCTAssertTrue(equalTo(nil, equalWhen: function).matches(nil)) + XCTAssertTrue(equalTo(tuple, equalWhen: function).matches((1, 1))) + XCTAssertFalse(equalTo(tuple, equalWhen: function).matches((1, 2))) + XCTAssertFalse(equalTo(nil, equalWhen: function).matches(tuple)) + } + + func testOptionalAnyInt() { + XCTAssertTrue(anyInt().matches(1 as Int?)) + XCTAssertFalse(anyString().matches(nil as String?)) + } + + func testOptionalAnyString() { + XCTAssertTrue(anyString().matches("a" as String?)) + XCTAssertFalse(anyString().matches(nil as String?)) + } + + func testOptionalAny() { + XCTAssertTrue(any().matches(X() as X?)) + XCTAssertTrue(any().matches(nil as X?)) + } + + func testOptionalAnyClosure() { + XCTAssertTrue(anyClosure().matches({ 0 } as (() -> Int)?)) + XCTAssertFalse(anyClosure().matches(nil as (() -> Int)?)) + } + + func testNotNil() { + XCTAssertTrue(notNil().matches(X())) + XCTAssertFalse(notNil().matches(nil as X?)) + } + + private class X { + } +} \ No newline at end of file diff --git a/Tests/Matching/ParameterMatcherTest.swift b/Tests/Matching/ParameterMatcherTest.swift new file mode 100644 index 0000000..43bae26 --- /dev/null +++ b/Tests/Matching/ParameterMatcherTest.swift @@ -0,0 +1,35 @@ +// +// ParameterMatcherTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 05.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class ParameterMatcherTest: XCTestCase { + + func testMatches() { + let matcher = ParameterMatcher { $0 == 5 } + + XCTAssertTrue(matcher.matches(5)) + XCTAssertFalse(matcher.matches(4)) + } + + func testOr() { + let matcher = ParameterMatcher { $0 == 5 }.or(ParameterMatcher { $0 == 4 }) + + XCTAssertTrue(matcher.matches(5)) + XCTAssertTrue(matcher.matches(4)) + XCTAssertFalse(matcher.matches(3)) + } + + func testAnd() { + let matcher = ParameterMatcher { $0 > 3 }.and(ParameterMatcher { $0 < 5 }) + + XCTAssertTrue(matcher.matches(4)) + XCTAssertFalse(matcher.matches(3)) + } +} \ No newline at end of file diff --git a/Tests/ProtocolTest.swift b/Tests/ProtocolTest.swift new file mode 100644 index 0000000..c195f58 --- /dev/null +++ b/Tests/ProtocolTest.swift @@ -0,0 +1,150 @@ +// +// ProtocolTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class ProtocolTest: XCTestCase { + + private var mock: MockTestedProtocol! + + override func setUp() { + super.setUp() + + mock = MockTestedProtocol() + } + + func testReadOnlyProperty() { + stub(mock) { mock in + when(mock.readOnlyProperty.get).thenReturn("a") + } + + XCTAssertEqual(mock.readOnlyProperty, "a") + verify(mock).readOnlyProperty.get + } + + func testReadWriteProperty() { + var called = false + stub(mock) { mock in + when(mock.readWriteProperty.get).thenReturn(1) + when(mock.readWriteProperty.set(anyInt())).then { _ in called = true } + } + + mock.readWriteProperty = 0 + + XCTAssertEqual(mock.readWriteProperty, 1) + XCTAssertTrue(called) + verify(mock).readWriteProperty.get + verify(mock).readWriteProperty.set(0) + } + + func testOptionalProperty() { + var called = false + stub(mock) { mock in + when(mock.optionalProperty.get).thenReturn(nil) + when(mock.optionalProperty.set(anyInt())).then { _ in called = true } + } + + mock.optionalProperty = 0 + + XCTAssertNil(mock.optionalProperty) + XCTAssertTrue(called) + verify(mock).optionalProperty.get + verify(mock).optionalProperty.set(eq(0)) + } + + func testNoReturn() { + var called = false + stub(mock) { mock in + when(mock.noReturn()).then { _ in called = true } + } + + mock.noReturn() + + XCTAssertTrue(called) + verify(mock).noReturn() + } + + func testCountCharacters() { + stub(mock) { mock in + when(mock.countCharacters("a")).thenReturn(1) + } + + XCTAssertEqual(mock.countCharacters("a"), 1) + verify(mock).countCharacters("a") + } + + func testWithThrows() { + stub(mock) { mock in + when(mock.withThrows()).thenThrow(TestError.Unknown) + } + + var catched = false + do { + try mock.withThrows() + } catch { + catched = true + } + + XCTAssertTrue(catched) + verify(mock).withThrows() + } + + func testWithNoReturnThrows() { + stub(mock) { mock in + when(mock.withNoReturnThrows()).thenThrow(TestError.Unknown) + } + + var catched = false + do { + try mock.withNoReturnThrows() + } catch { + catched = true + } + + XCTAssertTrue(catched) + verify(mock).withNoReturnThrows() + } + + func testWithClosure() { + stub(mock) { mock in + when(mock.withClosure(anyClosure())).thenReturn(0) + } + + XCTAssertEqual(mock.withClosure { _ in 1 }, 0) + verify(mock).withClosure(anyClosure()) + } + + func testWithNoescape() { + var called = false + stub(mock) { mock in + when(mock.withNoescape(anyString(), closure: anyClosure())).then { _ in called = true } + } + + mock.withNoescape("a") { _ in 1 } + + XCTAssertTrue(called) + verify(mock).withNoescape(anyString(), closure: anyClosure()) + } + + func testWithOptionalClosure() { + var called = false + stub(mock) { mock in + when(mock.withOptionalClosure(anyString(), closure: anyClosure())).then { _ in called = true } + } + + mock.withOptionalClosure("a") { _ in 1 } + + XCTAssertTrue(called) + verify(mock).withOptionalClosure(anyString(), closure: anyClosure()) + } + + private enum TestError: ErrorType { + case Unknown + } +} diff --git a/Tests/TestedClass.swift b/Tests/Source/TestedClass.swift similarity index 66% rename from Tests/TestedClass.swift rename to Tests/Source/TestedClass.swift index 1103f48..07aa452 100644 --- a/Tests/TestedClass.swift +++ b/Tests/Source/TestedClass.swift @@ -10,41 +10,33 @@ class TestedClass { let constant: Float = 0.0 var readOnlyProperty: String { - return "" + return "a" } lazy var readWriteProperty: Int = 0 lazy var optionalProperty: Int? = 0 - func noParameter() { - + func noReturn() { + } func countCharacters(test: String) -> Int { return test.characters.count } - func withReturn() -> String { - return "yello world" + func withThrows() throws -> Int { + return 0 } - func withThrows() throws { + func withNoReturnThrows() throws { } - func withClosure(closure: String -> Int) { - closure("hello") - } - - func withClosureReturningInt(closure: String -> Int) -> Int { + func withClosure(closure: String -> Int) -> Int { return closure("hello") } - func withMultipleParameters(a: String, b: Int, c: Float) { - - } - func withNoescape(a: String, @noescape closure: String -> Void) { closure(a) } diff --git a/Tests/TestedProtocol.swift b/Tests/Source/TestedProtocol.swift similarity index 66% rename from Tests/TestedProtocol.swift rename to Tests/Source/TestedProtocol.swift index 99dbec9..3381ebe 100644 --- a/Tests/TestedProtocol.swift +++ b/Tests/Source/TestedProtocol.swift @@ -13,19 +13,15 @@ protocol TestedProtocol { var optionalProperty: Int? { get set } - func noParameter() + func noReturn() func countCharacters(test: String) -> Int - func withReturn() -> String + func withThrows() throws -> Int - func withThrows() throws + func withNoReturnThrows() throws - func withClosure(closure: String -> Int) - - func withClosureReturningInt(closure: String -> Int) -> Int - - func withMultipleParameters(a: String, b: Int, c: Float) + func withClosure(closure: String -> Int) -> Int func withNoescape(a: String, @noescape closure: String -> Void) diff --git a/Tests/Stubbing/StubFunctionTest.swift b/Tests/Stubbing/StubFunctionTest.swift new file mode 100644 index 0000000..de60968 --- /dev/null +++ b/Tests/Stubbing/StubFunctionTest.swift @@ -0,0 +1,42 @@ +// +// StubFunctionTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class StubFunctionTest: XCTestCase { + + func testThen() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.countCharacters("a")).then { + return $0.characters.count * 2 + } + } + + XCTAssertEqual(mock.countCharacters("a"), 2) + } + + func testThenReturn() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.countCharacters("a")).thenReturn(2) + } + + XCTAssertEqual(mock.countCharacters("a"), 2) + } + + func testThenCallRealImplementation() { + let mock = MockTestedClass(spyOn: TestedClass()) + stub(mock) { mock in + when(mock.countCharacters("a")).thenCallRealImplementation() + } + + XCTAssertEqual(mock.countCharacters("a"), 1) + } +} \ No newline at end of file diff --git a/Tests/Stubbing/StubNoReturnFunctionTest.swift b/Tests/Stubbing/StubNoReturnFunctionTest.swift new file mode 100644 index 0000000..9642ad9 --- /dev/null +++ b/Tests/Stubbing/StubNoReturnFunctionTest.swift @@ -0,0 +1,45 @@ +// +// StubNoReturnFunctionTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class StubNoReturnFunctionTest: XCTestCase { + + func testThen() { + let mock = MockTestedClass() + var called = false + stub(mock) { mock in + when(mock.noReturn()).then { + called = true + } + } + + mock.noReturn() + + XCTAssertTrue(called) + } + + func testThenCallRealImplementation() { + let mock = MockTestedClass(spyOn: TestedClass()) + stub(mock) { mock in + when(mock.noReturn()).thenCallRealImplementation() + } + + mock.noReturn() + } + + func testThenDoNothing() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.noReturn()).thenDoNothing() + } + + mock.noReturn() + } +} \ No newline at end of file diff --git a/Tests/Stubbing/StubNoReturnThrowingFunctionTest.swift b/Tests/Stubbing/StubNoReturnThrowingFunctionTest.swift new file mode 100644 index 0000000..6192969 --- /dev/null +++ b/Tests/Stubbing/StubNoReturnThrowingFunctionTest.swift @@ -0,0 +1,65 @@ +// +// StubNoReturnThrowingFunctionTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class StubNoReturnThrowingFunctionTest: XCTestCase { + + func testThen() { + let mock = MockTestedClass() + var called = false + stub(mock) { mock in + when(mock.withNoReturnThrows()).then { + called = true + } + } + + try! mock.withNoReturnThrows() + + XCTAssertTrue(called) + } + + func testThenCallRealImplementation() { + let mock = MockTestedClass(spyOn: TestedClass()) + stub(mock) { mock in + when(mock.withNoReturnThrows()).thenCallRealImplementation() + } + + try! mock.withNoReturnThrows() + } + + func testThenDoNothing() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.withNoReturnThrows()).thenDoNothing() + } + + try! mock.withNoReturnThrows() + } + + func testThenThrow() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.withNoReturnThrows()).thenThrow(TestError.Unknown) + } + + var catched = false + do { + try mock.withNoReturnThrows() + } catch { + catched = true + } + + XCTAssertTrue(catched) + } + + private enum TestError: ErrorType { + case Unknown + } +} \ No newline at end of file diff --git a/Tests/Stubbing/StubThrowingFunctionTest.swift b/Tests/Stubbing/StubThrowingFunctionTest.swift new file mode 100644 index 0000000..08d98bd --- /dev/null +++ b/Tests/Stubbing/StubThrowingFunctionTest.swift @@ -0,0 +1,62 @@ +// +// StubThrowingFunctionTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class StubThrowingFunctionTest: XCTestCase { + + func testThen() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.withThrows()).then { + return 2 + } + } + + XCTAssertEqual(try! mock.withThrows(), 2) + } + + func testThenReturn() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.withThrows()).thenReturn(2) + } + + XCTAssertEqual(try! mock.withThrows(), 2) + } + + func testThenCallRealImplementation() { + let mock = MockTestedClass(spyOn: TestedClass()) + stub(mock) { mock in + when(mock.withThrows()).thenCallRealImplementation() + } + + XCTAssertEqual(try! mock.withThrows(), 0) + } + + func testThenThrow() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.withThrows()).thenThrow(TestError.Unknown) + } + + var catched = false + do { + try mock.withThrows() + } catch { + catched = true + } + + XCTAssertTrue(catched) + } + + private enum TestError: ErrorType { + case Unknown + } +} \ No newline at end of file diff --git a/Tests/Stubbing/StubbingTest.swift b/Tests/Stubbing/StubbingTest.swift new file mode 100644 index 0000000..bafbebb --- /dev/null +++ b/Tests/Stubbing/StubbingTest.swift @@ -0,0 +1,62 @@ +// +// StubbingTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class StubbingTest: XCTestCase { + + func testMultipleReturns() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.readOnlyProperty.get).thenReturn("a").thenReturn("b", "c") + } + + XCTAssertEqual(mock.readOnlyProperty, "a") + XCTAssertEqual(mock.readOnlyProperty, "b") + XCTAssertEqual(mock.readOnlyProperty, "c") + XCTAssertEqual(mock.readOnlyProperty, "c") + } + + func testOverrideStubWithMoreGeneralParameterMatcher() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.countCharacters("a")).thenReturn(2) + when(mock.countCharacters(anyString())).thenReturn(1) + } + + XCTAssertEqual(mock.countCharacters("a"), 1) + } + + func testOverrideStubWithMoreSpecificParameterMatcher() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.countCharacters(anyString())).thenReturn(1) + when(mock.countCharacters("a")).thenReturn(2) + } + + XCTAssertEqual(mock.countCharacters("a"), 2) + } + + func testUnstubbedSpy() { + let mock = MockTestedClass(spyOn: TestedClass()) + + XCTAssertEqual(mock.countCharacters("a"), 1) + } + + func testStubOfMultipleDifferentCalls() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.readOnlyProperty.get).thenReturn("a") + when(mock.countCharacters("a")).thenReturn(1) + } + + XCTAssertEqual(mock.readOnlyProperty, "a") + XCTAssertEqual(mock.countCharacters("a"), 1) + } +} \ No newline at end of file diff --git a/Tests/TestUtils.swift b/Tests/TestUtils.swift new file mode 100644 index 0000000..fa01993 --- /dev/null +++ b/Tests/TestUtils.swift @@ -0,0 +1,21 @@ +// +// TestUtils.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +@testable import Cuckoo + +struct TestUtils { + + static func catchCuckooFail(@noescape inClosure closure: () -> ()) -> String? { + let fail = MockManager.fail + var message: String? + MockManager.fail = { message = $0.0 } + closure() + MockManager.fail = fail + return message + } +} diff --git a/Tests/Verification/ArgumentCaptorTest.swift b/Tests/Verification/ArgumentCaptorTest.swift new file mode 100644 index 0000000..d380e24 --- /dev/null +++ b/Tests/Verification/ArgumentCaptorTest.swift @@ -0,0 +1,39 @@ +// +// ArgumentCaptorTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class ArgumentCaptorTest: XCTestCase { + + func testMultipleCalls() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.readWriteProperty.set(anyInt())).thenDoNothing() + } + mock.readWriteProperty = 10 + mock.readWriteProperty = 20 + mock.readWriteProperty = 30 + let captor = ArgumentCaptor() + + verify(mock, times(3)).readWriteProperty.set(captor.capture()) + + XCTAssertEqual(captor.value, 30) + XCTAssertEqual(captor.allValues, [10, 20, 30]) + } + + func testNoCall() { + let mock = MockTestedClass() + let captor = ArgumentCaptor() + + verify(mock, never()).readWriteProperty.set(captor.capture()) + + XCTAssertNil(captor.value) + XCTAssertTrue(captor.allValues.isEmpty) + } +} \ No newline at end of file diff --git a/Tests/Verification/VerificationTest.swift b/Tests/Verification/VerificationTest.swift new file mode 100644 index 0000000..a87f16b --- /dev/null +++ b/Tests/Verification/VerificationTest.swift @@ -0,0 +1,60 @@ +// +// VerificationTest.swift +// Cuckoo +// +// Created by Filip Dolnik on 04.07.16. +// Copyright © 2016 Brightify. All rights reserved. +// + +import XCTest +import Cuckoo + +class VerificationTest: XCTestCase { + + func testVerify() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.noReturn()).thenDoNothing() + } + + mock.noReturn() + + verify(mock).noReturn() + } + + func testVerifyWithCallMatcher() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.noReturn()).thenDoNothing() + } + + mock.noReturn() + mock.noReturn() + + verify(mock, times(2)).noReturn() + } + + func testVerifyWithMultipleDifferentCalls() { + let mock = MockTestedClass() + stub(mock) { mock in + when(mock.noReturn()).thenDoNothing() + when(mock.countCharacters(anyString())).thenReturn(1) + } + + mock.countCharacters("a") + mock.noReturn() + + verify(mock).noReturn() + verify(mock).countCharacters(anyString()) + } + + func testVerifyFail() { + let error = TestUtils.catchCuckooFail { + let mock = MockTestedClass() + + verify(mock).noReturn() + } + + XCTAssertNotNil(error) + } +} \ No newline at end of file