From de22995ef5bd234665d880f89ee223f9a4bf9436 Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 10:44:31 +0900 Subject: [PATCH 01/10] Remove unused message argument in expect --- Tests/ReactiveKitTests/Helpers.swift | 7 ++----- 1 file changed, 2 insertions(+), 5 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index c913cc5..c6b645b 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -41,19 +41,16 @@ extension Event { extension SignalProtocol { func expectNext(_ expectedElements: [Element], - _ message: @autoclosure () -> String = "", expectation: XCTestExpectation? = nil, file: StaticString = #file, line: UInt = #line) { - expect(expectedElements.map { .next($0) } + [.completed], message, expectation: expectation, file: file, line: line) + expect(expectedElements.map { .next($0) } + [.completed], expectation: expectation, file: file, line: line) } func expect(_ expectedEvents: [Event], - _ message: @autoclosure () -> String = "", expectation: XCTestExpectation? = nil, file: StaticString = #file, line: UInt = #line) { var eventsToProcess = expectedEvents var receivedEvents: [Event] = [] - let message = message() let _ = observe { event in receivedEvents.append(event) if eventsToProcess.count == 0 { @@ -61,7 +58,7 @@ extension SignalProtocol { return } let expected = eventsToProcess.removeFirst() - XCTAssert(event.isEqualTo(expected), message + "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) + XCTAssert(event.isEqualTo(expected), "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) if eventsToProcess.count == 0 { expectation?.fulfill() } From 5d6e03172449c1d122abf962fc62ae05c5bb7601 Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 10:59:46 +0900 Subject: [PATCH 02/10] Add expectAsync --- Tests/ReactiveKitTests/Helpers.swift | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index c6b645b..8709b15 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -64,6 +64,31 @@ extension SignalProtocol { } } } + + func expectNextAsync(_ expectedElements: [Element], + expectation: XCTestExpectation, + file: StaticString = #file, line: UInt = #line) { + expectAsync(expectedElements.map { .next($0) } + [.completed], expectation: expectation, file: file, line: line) + } + + func expectAsync(_ expectedEvents: [Event], + expectation: XCTestExpectation, + file: StaticString = #file, line: UInt = #line) { + var eventsToProcess = expectedEvents + var receivedEvents: [Event] = [] + let _ = observe { event in + receivedEvents.append(event) + if eventsToProcess.count == 0 { + XCTFail("Got more events than expected.") + return + } + let expected = eventsToProcess.removeFirst() + XCTAssert(event.isEqualTo(expected), "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) + if eventsToProcess.count == 0 { + expectation.fulfill() + } + } + } } class Scheduler { From 660e87d0ebd67b927b3631bf0183841855a15f16 Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 11:05:47 +0900 Subject: [PATCH 03/10] Change expectNext() to work only with syncronous test --- Tests/ReactiveKitTests/Helpers.swift | 10 ++++++---- 1 file changed, 6 insertions(+), 4 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index 8709b15..93dce58 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -41,16 +41,15 @@ extension Event { extension SignalProtocol { func expectNext(_ expectedElements: [Element], - expectation: XCTestExpectation? = nil, file: StaticString = #file, line: UInt = #line) { - expect(expectedElements.map { .next($0) } + [.completed], expectation: expectation, file: file, line: line) + expect(expectedElements.map { .next($0) } + [.completed], file: file, line: line) } func expect(_ expectedEvents: [Event], - expectation: XCTestExpectation? = nil, file: StaticString = #file, line: UInt = #line) { var eventsToProcess = expectedEvents var receivedEvents: [Event] = [] + var matchedAll = false let _ = observe { event in receivedEvents.append(event) if eventsToProcess.count == 0 { @@ -60,9 +59,12 @@ extension SignalProtocol { let expected = eventsToProcess.removeFirst() XCTAssert(event.isEqualTo(expected), "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) if eventsToProcess.count == 0 { - expectation?.fulfill() + matchedAll = true } } + if !matchedAll { + XCTFail("Got only first \(receivedEvents.count) events of expected \(expectedEvents))", file: file, line: line) + } } func expectNextAsync(_ expectedElements: [Element], From dd3ffe85a797213900f1ea1a55bbc8fe8ac66069 Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 11:24:21 +0900 Subject: [PATCH 04/10] Change expect() to expectAsync when test is asyncronous --- Tests/ReactiveKitTests/Helpers.swift | 6 +++-- Tests/ReactiveKitTests/PropertyTests.swift | 10 +++++---- Tests/ReactiveKitTests/SignalTests.swift | 26 +++++++++++----------- 3 files changed, 23 insertions(+), 19 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index 93dce58..e72d05d 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -78,7 +78,8 @@ extension SignalProtocol { file: StaticString = #file, line: UInt = #line) { var eventsToProcess = expectedEvents var receivedEvents: [Event] = [] - let _ = observe { event in + let disposeBag = DisposeBag() + observe { event in receivedEvents.append(event) if eventsToProcess.count == 0 { XCTFail("Got more events than expected.") @@ -88,8 +89,9 @@ extension SignalProtocol { XCTAssert(event.isEqualTo(expected), "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) if eventsToProcess.count == 0 { expectation.fulfill() + disposeBag.dispose() } - } + }.dispose(in: disposeBag) } } diff --git a/Tests/ReactiveKitTests/PropertyTests.swift b/Tests/ReactiveKitTests/PropertyTests.swift index c4185d8..e45e37e 100644 --- a/Tests/ReactiveKitTests/PropertyTests.swift +++ b/Tests/ReactiveKitTests/PropertyTests.swift @@ -24,7 +24,7 @@ class PropertyTests: XCTestCase { } func testEvents() { - property.expect( + property.expectAsync( [ .next(0), .next(5), @@ -52,7 +52,7 @@ class PropertyTests: XCTestCase { var readOnlyView: AnyProperty! = property.readOnlyView XCTAssert(readOnlyView.value == 0) - readOnlyView.expect( + readOnlyView.expectAsync( [ .next(0), .next(5), @@ -84,11 +84,13 @@ class PropertyTests: XCTestCase { func testBidirectionalBind() { let target = Property(100) - target.expectNext([100, 0, 50, 60]) - property.expectNext([0, 0, 50, 60]) + target.debug("target").expectAsync([.next(100), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) + property.debug("property").expectAsync([.next(0), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) property.bidirectionalBind(to: target) property.value = 50 target.value = 60 + + waitForExpectations(timeout: 2, handler: nil) } } diff --git a/Tests/ReactiveKitTests/SignalTests.swift b/Tests/ReactiveKitTests/SignalTests.swift index c099750..17a14bd 100644 --- a/Tests/ReactiveKitTests/SignalTests.swift +++ b/Tests/ReactiveKitTests/SignalTests.swift @@ -240,7 +240,7 @@ class SignalTests: XCTestCase { let combined = operationA.combineLatest(with: operationB).map { "\($0)\($1)" } let exp = expectation(description: "completed") - combined.expectNext(["1A", "1B", "2B", "3B", "3C"], expectation: exp) + combined.expectNextAsync(["1A", "1B", "2B", "3B", "3C"], expectation: exp) bob.runOne() eve.runOne() @@ -259,7 +259,7 @@ class SignalTests: XCTestCase { let merged = operationA.merge(with: operationB) let exp = expectation(description: "completed") - merged.expectNext([1, 4, 5, 2, 6, 3], expectation: exp) + merged.expectNextAsync([1, 4, 5, 2, 6, 3], expectation: exp) bob.runOne() eve.runOne() @@ -281,14 +281,14 @@ class SignalTests: XCTestCase { let operationA = Signal.sequence([1, 2, 3]) let operationB = Signal.sequence(["A", "B"]) let combined = operationA.zip(with: operationB).map { "\($0)\($1)" } - combined.expectNext(["1A", "2B"], expectation: nil) + combined.expectNext(["1A", "2B"]) } func testZipWithWhenNotComplete() { let operationA = Signal.sequence([1, 2, 3]).ignoreTerminal() let operationB = Signal.sequence(["A", "B"]) let combined = operationA.zip(with: operationB).map { "\($0)\($1)" } - combined.expectNext(["1A", "2B"], expectation: nil) + combined.expectNext(["1A", "2B"]) } func testZipWithAsyncSignal() { @@ -296,7 +296,7 @@ class SignalTests: XCTestCase { let operationB = Signal.interval(1.0).take(first: 10) // Takes 4 secs to emit 4 nexts. let combined = operationA.zip(with: operationB).map { $0 + $1 } // Completes after 4 nexts due to operationA and takes 4 secs due to operationB let exp = expectation(description: "completed") - combined.expectNext([0, 2, 4, 6], expectation: exp) + combined.expectNextAsync([0, 2, 4, 6], expectation: exp) waitForExpectations(timeout: 5.0, handler: nil) } @@ -369,7 +369,7 @@ class SignalTests: XCTestCase { let paused = operation.shareReplay().pausable(by: controller) let exp = expectation(description: "completed") - paused.expectNext([1, 3], expectation: exp) + paused.expectNextAsync([1, 3], expectation: exp) operation.next(1) controller.next(false) @@ -383,13 +383,13 @@ class SignalTests: XCTestCase { func testTimeoutNoFailure() { let exp = expectation(description: "completed") - Signal.just(1).timeout(after: 0.2, with: .Error, on: DispatchQueue.main).expectNext([1], expectation: exp) + Signal.just(1).timeout(after: 0.2, with: .Error, on: DispatchQueue.main).expectNextAsync([1], expectation: exp) waitForExpectations(timeout: 1, handler: nil) } func testTimeoutFailure() { let exp = expectation(description: "completed") - Signal.never().timeout(after: 0.5, with: .Error, on: DispatchQueue.main).expect([.failed(.Error)], expectation: exp) + Signal.never().timeout(after: 0.5, with: .Error, on: DispatchQueue.main).expectAsync([.failed(.Error)], expectation: exp) waitForExpectations(timeout: 1, handler: nil) } @@ -402,7 +402,7 @@ class SignalTests: XCTestCase { let ambdWith = operationA.amb(with: operationB) let exp = expectation(description: "completed") - ambdWith.expectNext([3, 4], expectation: exp) + ambdWith.expectNextAsync([3, 4], expectation: exp) eve.runOne() bob.runRemaining() @@ -426,7 +426,7 @@ class SignalTests: XCTestCase { let merged = operationA.concat(with: operationB) let exp = expectation(description: "completed") - merged.expectNext([1, 2, 3, 4], expectation: exp) + merged.expectNextAsync([1, 2, 3, 4], expectation: exp) bob.runOne() eve.runOne() @@ -464,7 +464,7 @@ class SignalTests: XCTestCase { } let exp = expectation(description: "completed") - merged.expectNext([5, 10, 12, 6], expectation: exp) + merged.expectNextAsync([5, 10, 12, 6], expectation: exp) bob.runOne() eves[0].runOne() @@ -485,7 +485,7 @@ class SignalTests: XCTestCase { } let exp = expectation(description: "completed") - merged.expectNext([5, 10, 12], expectation: exp) + merged.expectNextAsync([5, 10, 12], expectation: exp) bob.runOne() eves[0].runOne() @@ -506,7 +506,7 @@ class SignalTests: XCTestCase { } let exp = expectation(description: "completed") - merged.expectNext([5, 6, 10, 12], expectation: exp) + merged.expectNextAsync([5, 6, 10, 12], expectation: exp) bob.runRemaining() eves[1].runOne() From c477c90ad26821d870c8c189faf1efea4588fccc Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 13:49:27 +0900 Subject: [PATCH 05/10] Add expectNoEvent --- Tests/ReactiveKitTests/Helpers.swift | 17 +++++++++++++---- Tests/ReactiveKitTests/SignalTests.swift | 12 ++++++------ 2 files changed, 19 insertions(+), 10 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index e72d05d..ca57d2e 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -39,7 +39,8 @@ extension Event { } extension SignalProtocol { - + + // Synchronous test func expectNext(_ expectedElements: [Element], file: StaticString = #file, line: UInt = #line) { expect(expectedElements.map { .next($0) } + [.completed], file: file, line: line) @@ -67,6 +68,13 @@ extension SignalProtocol { } } + func expectNoEvent(file: StaticString = #file, line: UInt = #line) { + let _ = observe { event in + XCTFail("Got a \(event) when expected empty", file: file, line: line) + } + } + + // Asynchronous test func expectNextAsync(_ expectedElements: [Element], expectation: XCTestExpectation, file: StaticString = #file, line: UInt = #line) { @@ -76,9 +84,10 @@ extension SignalProtocol { func expectAsync(_ expectedEvents: [Event], expectation: XCTestExpectation, file: StaticString = #file, line: UInt = #line) { + XCTAssert(!expectedEvents.isEmpty, "Use expectEmptyAsync for waiting empty signal") var eventsToProcess = expectedEvents var receivedEvents: [Event] = [] - let disposeBag = DisposeBag() + let disposeOnSuccess = DisposeBag() observe { event in receivedEvents.append(event) if eventsToProcess.count == 0 { @@ -89,9 +98,9 @@ extension SignalProtocol { XCTAssert(event.isEqualTo(expected), "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) if eventsToProcess.count == 0 { expectation.fulfill() - disposeBag.dispose() + disposeOnSuccess.dispose() } - }.dispose(in: disposeBag) + }.dispose(in: disposeOnSuccess) } } diff --git a/Tests/ReactiveKitTests/SignalTests.swift b/Tests/ReactiveKitTests/SignalTests.swift index 17a14bd..2e8199e 100644 --- a/Tests/ReactiveKitTests/SignalTests.swift +++ b/Tests/ReactiveKitTests/SignalTests.swift @@ -67,7 +67,7 @@ class SignalTests: XCTestCase { func testNever() { let operation = Signal.never() - operation.expectNext([]) + operation.expectNoEvent() } func testFailed() { @@ -523,10 +523,10 @@ class SignalTests: XCTestCase { let operation = Signal.sequence([1, 2, 3]).executeIn(bob.context) let replayed = operation.replay(2) - replayed.expectNext([1, 2, 3]) + operation.expectNext([1, 2, 3]) let _ = replayed.connect() replayed.expectNext([2, 3]) - XCTAssertEqual(bob.numberOfRuns, 1) + XCTAssertEqual(bob.numberOfRuns, 2) } func testPublish() { @@ -536,10 +536,10 @@ class SignalTests: XCTestCase { let operation = Signal.sequence([1, 2, 3]).executeIn(bob.context) let published = operation.publish() - published.expectNext([1, 2, 3]) + operation.expectNext([1, 2, 3]) let _ = published.connect() - published.expectNext([]) + published.expectNoEvent() - XCTAssertEqual(bob.numberOfRuns, 1) + XCTAssertEqual(bob.numberOfRuns, 2) } } From f1d3e040b5db4ec11fa62a89003835cb9881ef45 Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 13:55:06 +0900 Subject: [PATCH 06/10] Change expectNextAsync() to continue testing even after all expected events arrives --- Tests/ReactiveKitTests/Helpers.swift | 6 ++---- Tests/ReactiveKitTests/PropertyTests.swift | 4 ++-- 2 files changed, 4 insertions(+), 6 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index ca57d2e..47c56ef 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -87,8 +87,7 @@ extension SignalProtocol { XCTAssert(!expectedEvents.isEmpty, "Use expectEmptyAsync for waiting empty signal") var eventsToProcess = expectedEvents var receivedEvents: [Event] = [] - let disposeOnSuccess = DisposeBag() - observe { event in + let _ = observe { event in receivedEvents.append(event) if eventsToProcess.count == 0 { XCTFail("Got more events than expected.") @@ -98,9 +97,8 @@ extension SignalProtocol { XCTAssert(event.isEqualTo(expected), "(Got \(receivedEvents) instead of \(expectedEvents))", file: file, line: line) if eventsToProcess.count == 0 { expectation.fulfill() - disposeOnSuccess.dispose() } - }.dispose(in: disposeOnSuccess) + } } } diff --git a/Tests/ReactiveKitTests/PropertyTests.swift b/Tests/ReactiveKitTests/PropertyTests.swift index e45e37e..adb73ea 100644 --- a/Tests/ReactiveKitTests/PropertyTests.swift +++ b/Tests/ReactiveKitTests/PropertyTests.swift @@ -84,8 +84,8 @@ class PropertyTests: XCTestCase { func testBidirectionalBind() { let target = Property(100) - target.debug("target").expectAsync([.next(100), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) - property.debug("property").expectAsync([.next(0), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) + target.ignoreTerminal().expectAsync([.next(100), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) + property.ignoreTerminal().expectAsync([.next(0), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) property.bidirectionalBind(to: target) property.value = 50 From ffd2c77fcdee92f7e124658a533358304b1a4194 Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 10:17:41 +0900 Subject: [PATCH 07/10] Add test for zip --- Tests/ReactiveKitTests/SignalTests.swift | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/Tests/ReactiveKitTests/SignalTests.swift b/Tests/ReactiveKitTests/SignalTests.swift index 2e8199e..487d679 100644 --- a/Tests/ReactiveKitTests/SignalTests.swift +++ b/Tests/ReactiveKitTests/SignalTests.swift @@ -291,6 +291,13 @@ class SignalTests: XCTestCase { combined.expectNext(["1A", "2B"]) } + func testZipWithWhenNotComplete2() { + let operationA = Signal.sequence([1, 2, 3]) + let operationB = Signal.sequence(["A", "B"]).ignoreTerminal() + let combined = operationA.zip(with: operationB).map { "\($0)\($1)" } + combined.expect([.next("1A"), .next("2B")]) + } + func testZipWithAsyncSignal() { let operationA = Signal.interval(0.5).take(first: 4) // Takes just 2 secs to emit 4 nexts. let operationB = Signal.interval(1.0).take(first: 10) // Takes 4 secs to emit 4 nexts. From 8d915d7ba563ad3a5942b5a9c64e2d14063acb3a Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 14:02:00 +0900 Subject: [PATCH 08/10] Rename expectNext() to expectComplete(after:) --- Tests/ReactiveKitTests/Helpers.swift | 4 +- Tests/ReactiveKitTests/SignalTests.swift | 82 ++++++++++++------------ 2 files changed, 43 insertions(+), 43 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index 47c56ef..4f02802 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -41,8 +41,8 @@ extension Event { extension SignalProtocol { // Synchronous test - func expectNext(_ expectedElements: [Element], - file: StaticString = #file, line: UInt = #line) { + func expectComplete(after expectedElements: [Element], + file: StaticString = #file, line: UInt = #line) { expect(expectedElements.map { .next($0) } + [.completed], file: file, line: line) } diff --git a/Tests/ReactiveKitTests/SignalTests.swift b/Tests/ReactiveKitTests/SignalTests.swift index 487d679..ac88842 100644 --- a/Tests/ReactiveKitTests/SignalTests.swift +++ b/Tests/ReactiveKitTests/SignalTests.swift @@ -34,8 +34,8 @@ class SignalTests: XCTestCase { let operation = Signal.sequence([1, 2, 3]).executeIn(bob.context) - operation.expectNext([1, 2, 3]) - operation.expectNext([1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) XCTAssertEqual(bob.numberOfRuns, 2) } @@ -52,17 +52,17 @@ class SignalTests: XCTestCase { func testJust() { let operation = Signal.just(1) - operation.expectNext([1]) + operation.expectComplete(after: [1]) } func testSequence() { let operation = Signal.sequence([1, 2, 3]) - operation.expectNext([1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) } func testCompleted() { let operation = Signal.completed() - operation.expectNext([]) + operation.expectComplete(after: []) } func testNever() { @@ -96,99 +96,99 @@ class SignalTests: XCTestCase { func testBuffer() { let operation = Signal.sequence([1,2,3,4,5]) let buffered = operation.buffer(size: 2) - buffered.expectNext([[1, 2], [3, 4]]) + buffered.expectComplete(after: [[1, 2], [3, 4]]) } func testMap() { let operation = Signal.sequence([1, 2, 3]) let mapped = operation.map { $0 * 2 } - mapped.expectNext([2, 4, 6]) + mapped.expectComplete(after: [2, 4, 6]) } func testScan() { let operation = Signal.sequence([1, 2, 3]) let scanned = operation.scan(0, +) - scanned.expectNext([0, 1, 3, 6]) + scanned.expectComplete(after: [0, 1, 3, 6]) } func testToSignal() { let operation = Signal.sequence([1, 2, 3]) let operation2 = operation.toSignal() - operation2.expectNext([1, 2, 3]) + operation2.expectComplete(after: [1, 2, 3]) } func testSuppressError() { let operation = Signal.sequence([1, 2, 3]) let signal = operation.suppressError(logging: false) - signal.expectNext([1, 2, 3]) + signal.expectComplete(after: [1, 2, 3]) } func testSuppressError2() { let operation = Signal.failed(.Error) let signal = operation.suppressError(logging: false) - signal.expectNext([]) + signal.expectComplete(after: []) } func testRecover() { let operation = Signal.failed(.Error) let signal = operation.recover(with: 1) - signal.expectNext([1]) + signal.expectComplete(after: [1]) } func testWindow() { let operation = Signal.sequence([1, 2, 3]) let window = operation.window(size: 2) - window.merge().expectNext([1, 2]) + window.merge().expectComplete(after: [1, 2]) } // func testDebounce() { // let operation = Signal.interval(0.1, queue: Queue.global).take(first: 3) // let distinct = operation.debounce(interval: 0.3, on: Queue.global) // let exp = expectation(withDescription: "completed") - // distinct.expectNext([2], expectation: exp) + // distinct.expectComplete(after: [2], expectation: exp) // waitForExpectations(withTimeout: 1, handler: nil) // } func testDistinct() { let operation = Signal.sequence([1, 2, 2, 3]) let distinct = operation.distinct { a, b in a != b } - distinct.expectNext([1, 2, 3]) + distinct.expectComplete(after: [1, 2, 3]) } func testDistinct2() { let operation = Signal.sequence([1, 2, 2, 3]) let distinct = operation.distinct() - distinct.expectNext([1, 2, 3]) + distinct.expectComplete(after: [1, 2, 3]) } func testElementAt() { let operation = Signal.sequence([1, 2, 3]) let elementAt1 = operation.element(at: 1) - elementAt1.expectNext([2]) + elementAt1.expectComplete(after: [2]) } func testFilter() { let operation = Signal.sequence([1, 2, 3]) let filtered = operation.filter { $0 % 2 != 0 } - filtered.expectNext([1, 3]) + filtered.expectComplete(after: [1, 3]) } func testFirst() { let operation = Signal.sequence([1, 2, 3]) let first = operation.first() - first.expectNext([1]) + first.expectComplete(after: [1]) } func testIgnoreElement() { let operation = Signal.sequence([1, 2, 3]) let ignoreElements = operation.ignoreElements() - ignoreElements.expectNext([]) + ignoreElements.expectComplete(after: []) } func testLast() { let operation = Signal.sequence([1, 2, 3]) let first = operation.last() - first.expectNext([3]) + first.expectComplete(after: [3]) } // TODO: sample @@ -196,39 +196,39 @@ class SignalTests: XCTestCase { func testSkip() { let operation = Signal.sequence([1, 2, 3]) let skipped1 = operation.skip(first: 1) - skipped1.expectNext([2, 3]) + skipped1.expectComplete(after: [2, 3]) } func testSkipLast() { let operation = Signal.sequence([1, 2, 3]) let skippedLast1 = operation.skip(last: 1) - skippedLast1.expectNext([1, 2]) + skippedLast1.expectComplete(after: [1, 2]) } func testTake() { let operation = Signal.sequence([1, 2, 3]) let taken2 = operation.take(first: 2) - taken2.expectNext([1, 2]) + taken2.expectComplete(after: [1, 2]) } func testTakeLast() { let operation = Signal.sequence([1, 2, 3]) let takenLast2 = operation.take(last: 2) - takenLast2.expectNext([2, 3]) + takenLast2.expectComplete(after: [2, 3]) } // func testThrottle() { // let operation = Signal.interval(0.4, queue: Queue.global).take(5) // let distinct = operation.throttle(1) // let exp = expectation(withDescription: "completed") -// distinct.expectNext([0, 3], expectation: exp) +// distinct.expectComplete(after: [0, 3], expectation: exp) // waitForExpectationsWithTimeout(3, handler: nil) // } func testIgnoreNil() { let operation = Signal.sequence(Array([1, nil, 3])) let unwrapped = operation.ignoreNil() - unwrapped.expectNext([1, 3]) + unwrapped.expectComplete(after: [1, 3]) } func testCombineLatestWith() { @@ -274,21 +274,21 @@ class SignalTests: XCTestCase { func testStartWith() { let operation = Signal.sequence([1, 2, 3]) let startWith4 = operation.start(with: 4) - startWith4.expectNext([4, 1, 2, 3]) + startWith4.expectComplete(after: [4, 1, 2, 3]) } func testZipWith() { let operationA = Signal.sequence([1, 2, 3]) let operationB = Signal.sequence(["A", "B"]) let combined = operationA.zip(with: operationB).map { "\($0)\($1)" } - combined.expectNext(["1A", "2B"]) + combined.expectComplete(after: ["1A", "2B"]) } func testZipWithWhenNotComplete() { let operationA = Signal.sequence([1, 2, 3]).ignoreTerminal() let operationB = Signal.sequence(["A", "B"]) let combined = operationA.zip(with: operationB).map { "\($0)\($1)" } - combined.expectNext(["1A", "2B"]) + combined.expectComplete(after: ["1A", "2B"]) } func testZipWithWhenNotComplete2() { @@ -310,13 +310,13 @@ class SignalTests: XCTestCase { func testFlatMapError() { let operation = Signal.failed(.Error) let recovered = operation.flatMapError { error in Signal.just(1) } - recovered.expectNext([1]) + recovered.expectComplete(after: [1]) } func testFlatMapError2() { let operation = Signal.failed(.Error) let recovered = operation.flatMapError { error in Signal.just(1) } - recovered.expectNext([1]) + recovered.expectComplete(after: [1]) } func testRetry() { @@ -335,7 +335,7 @@ class SignalTests: XCTestCase { bob.runRemaining() let operation = Signal.sequence([1, 2, 3]).executeIn(bob.context) - operation.expectNext([1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) XCTAssertEqual(bob.numberOfRuns, 1) } @@ -365,7 +365,7 @@ class SignalTests: XCTestCase { bob.runRemaining() let operation = Signal.sequence([1, 2, 3]).observeIn(bob.context) - operation.expectNext([1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) XCTAssertEqual(bob.numberOfRuns, 4) // 3 elements + completion } @@ -421,7 +421,7 @@ class SignalTests: XCTestCase { func testCollect() { let operation = Signal.sequence([1, 2, 3]) let collected = operation.collect() - collected.expectNext([[1, 2, 3]]) + collected.expectComplete(after: [[1, 2, 3]]) } func testConcatWith() { @@ -446,19 +446,19 @@ class SignalTests: XCTestCase { func testDefaultIfEmpty() { let operation = Signal.sequence([]) let defaulted = operation.defaultIfEmpty(1) - defaulted.expectNext([1]) + defaulted.expectComplete(after: [1]) } func testReduce() { let operation = Signal.sequence([1, 2, 3]) let reduced = operation.reduce(0, +) - reduced.expectNext([6]) + reduced.expectComplete(after: [6]) } func testZipPrevious() { let operation = Signal.sequence([1, 2, 3]) let zipped = operation.zipPrevious() - zipped.expectNext([(nil, 1), (1, 2), (2, 3)]) + zipped.expectComplete(after: [(nil, 1), (1, 2), (2, 3)]) } func testFlatMapMerge() { @@ -530,9 +530,9 @@ class SignalTests: XCTestCase { let operation = Signal.sequence([1, 2, 3]).executeIn(bob.context) let replayed = operation.replay(2) - operation.expectNext([1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) let _ = replayed.connect() - replayed.expectNext([2, 3]) + replayed.expectComplete(after: [2, 3]) XCTAssertEqual(bob.numberOfRuns, 2) } @@ -543,7 +543,7 @@ class SignalTests: XCTestCase { let operation = Signal.sequence([1, 2, 3]).executeIn(bob.context) let published = operation.publish() - operation.expectNext([1, 2, 3]) + operation.expectComplete(after: [1, 2, 3]) let _ = published.connect() published.expectNoEvent() From 7788cbc744e40c835195438bbc7a400fc558b12d Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 14:04:38 +0900 Subject: [PATCH 09/10] Rename expectNextAsync() to expectAsyncComplete(after:) --- Tests/ReactiveKitTests/Helpers.swift | 6 +++--- Tests/ReactiveKitTests/SignalTests.swift | 20 ++++++++++---------- 2 files changed, 13 insertions(+), 13 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index 4f02802..eca6342 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -75,9 +75,9 @@ extension SignalProtocol { } // Asynchronous test - func expectNextAsync(_ expectedElements: [Element], - expectation: XCTestExpectation, - file: StaticString = #file, line: UInt = #line) { + func expectAsyncComplete(after expectedElements: [Element], + expectation: XCTestExpectation, + file: StaticString = #file, line: UInt = #line) { expectAsync(expectedElements.map { .next($0) } + [.completed], expectation: expectation, file: file, line: line) } diff --git a/Tests/ReactiveKitTests/SignalTests.swift b/Tests/ReactiveKitTests/SignalTests.swift index ac88842..21c7804 100644 --- a/Tests/ReactiveKitTests/SignalTests.swift +++ b/Tests/ReactiveKitTests/SignalTests.swift @@ -240,7 +240,7 @@ class SignalTests: XCTestCase { let combined = operationA.combineLatest(with: operationB).map { "\($0)\($1)" } let exp = expectation(description: "completed") - combined.expectNextAsync(["1A", "1B", "2B", "3B", "3C"], expectation: exp) + combined.expectAsyncComplete(after: ["1A", "1B", "2B", "3B", "3C"], expectation: exp) bob.runOne() eve.runOne() @@ -259,7 +259,7 @@ class SignalTests: XCTestCase { let merged = operationA.merge(with: operationB) let exp = expectation(description: "completed") - merged.expectNextAsync([1, 4, 5, 2, 6, 3], expectation: exp) + merged.expectAsyncComplete(after: [1, 4, 5, 2, 6, 3], expectation: exp) bob.runOne() eve.runOne() @@ -303,7 +303,7 @@ class SignalTests: XCTestCase { let operationB = Signal.interval(1.0).take(first: 10) // Takes 4 secs to emit 4 nexts. let combined = operationA.zip(with: operationB).map { $0 + $1 } // Completes after 4 nexts due to operationA and takes 4 secs due to operationB let exp = expectation(description: "completed") - combined.expectNextAsync([0, 2, 4, 6], expectation: exp) + combined.expectAsyncComplete(after: [0, 2, 4, 6], expectation: exp) waitForExpectations(timeout: 5.0, handler: nil) } @@ -376,7 +376,7 @@ class SignalTests: XCTestCase { let paused = operation.shareReplay().pausable(by: controller) let exp = expectation(description: "completed") - paused.expectNextAsync([1, 3], expectation: exp) + paused.expectAsyncComplete(after: [1, 3], expectation: exp) operation.next(1) controller.next(false) @@ -390,7 +390,7 @@ class SignalTests: XCTestCase { func testTimeoutNoFailure() { let exp = expectation(description: "completed") - Signal.just(1).timeout(after: 0.2, with: .Error, on: DispatchQueue.main).expectNextAsync([1], expectation: exp) + Signal.just(1).timeout(after: 0.2, with: .Error, on: DispatchQueue.main).expectAsyncComplete(after: [1], expectation: exp) waitForExpectations(timeout: 1, handler: nil) } @@ -409,7 +409,7 @@ class SignalTests: XCTestCase { let ambdWith = operationA.amb(with: operationB) let exp = expectation(description: "completed") - ambdWith.expectNextAsync([3, 4], expectation: exp) + ambdWith.expectAsyncComplete(after: [3, 4], expectation: exp) eve.runOne() bob.runRemaining() @@ -433,7 +433,7 @@ class SignalTests: XCTestCase { let merged = operationA.concat(with: operationB) let exp = expectation(description: "completed") - merged.expectNextAsync([1, 2, 3, 4], expectation: exp) + merged.expectAsyncComplete(after: [1, 2, 3, 4], expectation: exp) bob.runOne() eve.runOne() @@ -471,7 +471,7 @@ class SignalTests: XCTestCase { } let exp = expectation(description: "completed") - merged.expectNextAsync([5, 10, 12, 6], expectation: exp) + merged.expectAsyncComplete(after: [5, 10, 12, 6], expectation: exp) bob.runOne() eves[0].runOne() @@ -492,7 +492,7 @@ class SignalTests: XCTestCase { } let exp = expectation(description: "completed") - merged.expectNextAsync([5, 10, 12], expectation: exp) + merged.expectAsyncComplete(after: [5, 10, 12], expectation: exp) bob.runOne() eves[0].runOne() @@ -513,7 +513,7 @@ class SignalTests: XCTestCase { } let exp = expectation(description: "completed") - merged.expectNextAsync([5, 6, 10, 12], expectation: exp) + merged.expectAsyncComplete(after: [5, 6, 10, 12], expectation: exp) bob.runRemaining() eves[1].runOne() From b6daf344509a216aed3956714cb52f24047596be Mon Sep 17 00:00:00 2001 From: jechol Date: Tue, 17 Jan 2017 14:09:35 +0900 Subject: [PATCH 10/10] Rename expect() to expect(events:) and expectAsync() to expectAsync(events:) --- Tests/ReactiveKitTests/Helpers.swift | 8 ++++---- Tests/ReactiveKitTests/PropertyTests.swift | 8 ++++---- Tests/ReactiveKitTests/SignalTests.swift | 8 ++++---- 3 files changed, 12 insertions(+), 12 deletions(-) diff --git a/Tests/ReactiveKitTests/Helpers.swift b/Tests/ReactiveKitTests/Helpers.swift index eca6342..12f86bc 100644 --- a/Tests/ReactiveKitTests/Helpers.swift +++ b/Tests/ReactiveKitTests/Helpers.swift @@ -43,10 +43,10 @@ extension SignalProtocol { // Synchronous test func expectComplete(after expectedElements: [Element], file: StaticString = #file, line: UInt = #line) { - expect(expectedElements.map { .next($0) } + [.completed], file: file, line: line) + expect(events: expectedElements.map { .next($0) } + [.completed], file: file, line: line) } - func expect(_ expectedEvents: [Event], + func expect(events expectedEvents: [Event], file: StaticString = #file, line: UInt = #line) { var eventsToProcess = expectedEvents var receivedEvents: [Event] = [] @@ -78,10 +78,10 @@ extension SignalProtocol { func expectAsyncComplete(after expectedElements: [Element], expectation: XCTestExpectation, file: StaticString = #file, line: UInt = #line) { - expectAsync(expectedElements.map { .next($0) } + [.completed], expectation: expectation, file: file, line: line) + expectAsync(events: expectedElements.map { .next($0) } + [.completed], expectation: expectation, file: file, line: line) } - func expectAsync(_ expectedEvents: [Event], + func expectAsync(events expectedEvents: [Event], expectation: XCTestExpectation, file: StaticString = #file, line: UInt = #line) { XCTAssert(!expectedEvents.isEmpty, "Use expectEmptyAsync for waiting empty signal") diff --git a/Tests/ReactiveKitTests/PropertyTests.swift b/Tests/ReactiveKitTests/PropertyTests.swift index adb73ea..e88b70e 100644 --- a/Tests/ReactiveKitTests/PropertyTests.swift +++ b/Tests/ReactiveKitTests/PropertyTests.swift @@ -24,7 +24,7 @@ class PropertyTests: XCTestCase { } func testEvents() { - property.expectAsync( + property.expectAsync(events: [ .next(0), .next(5), @@ -52,7 +52,7 @@ class PropertyTests: XCTestCase { var readOnlyView: AnyProperty! = property.readOnlyView XCTAssert(readOnlyView.value == 0) - readOnlyView.expectAsync( + readOnlyView.expectAsync(events: [ .next(0), .next(5), @@ -84,8 +84,8 @@ class PropertyTests: XCTestCase { func testBidirectionalBind() { let target = Property(100) - target.ignoreTerminal().expectAsync([.next(100), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) - property.ignoreTerminal().expectAsync([.next(0), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) + target.ignoreTerminal().expectAsync(events: [.next(100), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) + property.ignoreTerminal().expectAsync(events: [.next(0), .next(0), .next(50), .next(60)], expectation: expectation(description: "nexts")) property.bidirectionalBind(to: target) property.value = 50 diff --git a/Tests/ReactiveKitTests/SignalTests.swift b/Tests/ReactiveKitTests/SignalTests.swift index 21c7804..81d5054 100644 --- a/Tests/ReactiveKitTests/SignalTests.swift +++ b/Tests/ReactiveKitTests/SignalTests.swift @@ -72,7 +72,7 @@ class SignalTests: XCTestCase { func testFailed() { let operation = Signal.failed(.Error) - operation.expect([.failed(.Error)]) + operation.expect(events: [.failed(.Error)]) } func testObserveFailed() { @@ -295,7 +295,7 @@ class SignalTests: XCTestCase { let operationA = Signal.sequence([1, 2, 3]) let operationB = Signal.sequence(["A", "B"]).ignoreTerminal() let combined = operationA.zip(with: operationB).map { "\($0)\($1)" } - combined.expect([.next("1A"), .next("2B")]) + combined.expect(events: [.next("1A"), .next("2B")]) } func testZipWithAsyncSignal() { @@ -325,7 +325,7 @@ class SignalTests: XCTestCase { let operation = Signal.failed(.Error).executeIn(bob.context) let retry = operation.retry(times: 3) - retry.expect([.failed(.Error)]) + retry.expect(events: [.failed(.Error)]) XCTAssertEqual(bob.numberOfRuns, 4) } @@ -396,7 +396,7 @@ class SignalTests: XCTestCase { func testTimeoutFailure() { let exp = expectation(description: "completed") - Signal.never().timeout(after: 0.5, with: .Error, on: DispatchQueue.main).expectAsync([.failed(.Error)], expectation: exp) + Signal.never().timeout(after: 0.5, with: .Error, on: DispatchQueue.main).expectAsync(events: [.failed(.Error)], expectation: exp) waitForExpectations(timeout: 1, handler: nil) }