diff --git a/Tests/AblyChatTests/DefaultRoomPresenceTests.swift b/Tests/AblyChatTests/DefaultRoomPresenceTests.swift index 97b2f0d..1a63e39 100644 --- a/Tests/AblyChatTests/DefaultRoomPresenceTests.swift +++ b/Tests/AblyChatTests/DefaultRoomPresenceTests.swift @@ -3,47 +3,6 @@ import Ably import Testing struct DefaultRoomPresenceTests { - // MARK: - Test helpers - - let fakeNetworkDelay: UInt64 = 10 // milliseconds; without this delay (or with a very low value such as 1) most of the time attach happens before lifecycleManager has a chance to start waiting. - - private func createManager( - forTestingWhatHappensWhenCurrentlyIn status: DefaultRoomLifecycleManager.Status? = nil, - forTestingWhatHappensWhenHasPendingDiscontinuityEvents pendingDiscontinuityEvents: [MockRoomLifecycleContributor.ID: DiscontinuityEvent]? = nil, - forTestingWhatHappensWhenHasTransientDisconnectTimeoutForTheseContributorIDs idsOfContributorsWithTransientDisconnectTimeout: Set? = nil, - contributors: [MockRoomLifecycleContributor] = [], - clock: SimpleClock = MockSimpleClock() - ) async -> DefaultRoomLifecycleManager { - await .init( - testsOnly_status: status, - testsOnly_pendingDiscontinuityEvents: pendingDiscontinuityEvents, - testsOnly_idsOfContributorsWithTransientDisconnectTimeout: idsOfContributorsWithTransientDisconnectTimeout, - contributors: contributors, - logger: TestLogger(), - clock: clock - ) - } - - private func createContributor( - initialState: ARTRealtimeChannelState = .initialized, - initialErrorReason: ARTErrorInfo? = nil, - feature: RoomFeature = .messages, // Arbitrarily chosen, its value only matters in test cases where we check which error is thrown - attachBehavior: MockRoomLifecycleContributorChannel.AttachOrDetachBehavior? = nil, - detachBehavior: MockRoomLifecycleContributorChannel.AttachOrDetachBehavior? = nil, - subscribeToStateBehavior: MockRoomLifecycleContributorChannel.SubscribeToStateBehavior? = nil - ) -> MockRoomLifecycleContributor { - .init( - feature: feature, - channel: .init( - initialState: initialState, - initialErrorReason: initialErrorReason, - attachBehavior: attachBehavior, - detachBehavior: detachBehavior, - subscribeToStateBehavior: subscribeToStateBehavior - ) - ) - } - // MARK: CHA-PR1 // @spec CHA-PR1 @@ -88,8 +47,8 @@ struct DefaultRoomPresenceTests { @Test func usersMayEnterPresenceWhileAttaching() async throws { // Given: A DefaultRoomLifecycleManager, with an ATTACH operation in progress and hence in the ATTACHING status - let contributor = createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.success, newState: .attached, delayInMilliseconds: fakeNetworkDelay)) - let lifecycleManager = await createManager(contributors: [contributor]) + let contributor = RoomLifecycleHelper.createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.success, newState: .attached, delayInMilliseconds: RoomLifecycleHelper.fakeNetworkDelay)) + let lifecycleManager = await RoomLifecycleHelper.createManager(contributors: [contributor]) // Given: A DefaultPresence with DefaultFeatureChannel and MockRoomLifecycleContributor let realtimePresence = MockRealtimePresence(["client1"].map { .init(clientId: $0) }) @@ -122,8 +81,8 @@ struct DefaultRoomPresenceTests { let attachError = ARTErrorInfo(domain: "SomeDomain", code: 123) // Given: A DefaultRoomLifecycleManager, with an ATTACH operation in progress and hence in the ATTACHING status - let contributor = createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.failure(attachError), newState: .failed, delayInMilliseconds: fakeNetworkDelay)) // Without this delay most of the time attach fail happens before lifecycleManager has a chance to start waiting. I tried to use SignallableChannelOperation, but looks like `await #expect(...)` doesn't understand `let async x/try await x` syntax. - let lifecycleManager = await createManager(contributors: [contributor]) + let contributor = RoomLifecycleHelper.createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.failure(attachError), newState: .failed, delayInMilliseconds: RoomLifecycleHelper.fakeNetworkDelay)) // Without this delay most of the time attach fail happens before lifecycleManager has a chance to start waiting. I tried to use SignallableChannelOperation, but looks like `await #expect(...)` doesn't understand `let async x/try await x` syntax. + let lifecycleManager = await RoomLifecycleHelper.createManager(contributors: [contributor]) // Given: A DefaultPresence with DefaultFeatureChannel and MockRoomLifecycleContributor let realtimePresence = MockRealtimePresence(["client1"].map { .init(clientId: $0) }) @@ -208,8 +167,8 @@ struct DefaultRoomPresenceTests { @Test func usersMayUpdatePresenceWhileAttaching() async throws { // Given: A DefaultRoomLifecycleManager, with an ATTACH operation in progress and hence in the ATTACHING status - let contributor = createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.success, newState: .attached, delayInMilliseconds: fakeNetworkDelay)) - let lifecycleManager = await createManager(contributors: [contributor]) + let contributor = RoomLifecycleHelper.createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.success, newState: .attached, delayInMilliseconds: RoomLifecycleHelper.fakeNetworkDelay)) + let lifecycleManager = await RoomLifecycleHelper.createManager(contributors: [contributor]) // Given: A DefaultPresence with DefaultFeatureChannel and MockRoomLifecycleContributor let realtimePresence = MockRealtimePresence(["client1"].map { .init(clientId: $0) }) @@ -242,8 +201,8 @@ struct DefaultRoomPresenceTests { let attachError = ARTErrorInfo(domain: "SomeDomain", code: 123) // Given: A DefaultRoomLifecycleManager, with an ATTACH operation in progress and hence in the ATTACHING status - let contributor = createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.failure(attachError), newState: .failed, delayInMilliseconds: fakeNetworkDelay)) - let lifecycleManager = await createManager(contributors: [contributor]) + let contributor = RoomLifecycleHelper.createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.failure(attachError), newState: .failed, delayInMilliseconds: RoomLifecycleHelper.fakeNetworkDelay)) + let lifecycleManager = await RoomLifecycleHelper.createManager(contributors: [contributor]) // Given: A DefaultPresence with DefaultFeatureChannel and MockRoomLifecycleContributor let realtimePresence = MockRealtimePresence(["client1"].map { .init(clientId: $0) }) @@ -386,8 +345,8 @@ struct DefaultRoomPresenceTests { @Test func retrieveAllTheMembersOfThePresenceSetWhileAttaching() async throws { // Given: A DefaultRoomLifecycleManager, with an ATTACH operation in progress and hence in the ATTACHING status - let contributor = createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.success, newState: .attached, delayInMilliseconds: fakeNetworkDelay)) - let lifecycleManager = await createManager(contributors: [contributor]) + let contributor = RoomLifecycleHelper.createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.success, newState: .attached, delayInMilliseconds: RoomLifecycleHelper.fakeNetworkDelay)) + let lifecycleManager = await RoomLifecycleHelper.createManager(contributors: [contributor]) // Given: A DefaultPresence with DefaultFeatureChannel and MockRoomLifecycleContributor let realtimePresence = MockRealtimePresence(["client1"].map { .init(clientId: $0) }) @@ -420,8 +379,8 @@ struct DefaultRoomPresenceTests { let attachError = ARTErrorInfo(domain: "SomeDomain", code: 123) // Given: A DefaultRoomLifecycleManager, with an ATTACH operation in progress and hence in the ATTACHING status - let contributor = createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.failure(attachError), newState: .failed, delayInMilliseconds: fakeNetworkDelay)) - let lifecycleManager = await createManager(contributors: [contributor]) + let contributor = RoomLifecycleHelper.createContributor(feature: .presence, attachBehavior: .completeAndChangeState(.failure(attachError), newState: .failed, delayInMilliseconds: RoomLifecycleHelper.fakeNetworkDelay)) + let lifecycleManager = await RoomLifecycleHelper.createManager(contributors: [contributor]) // Given: A DefaultPresence with DefaultFeatureChannel and MockRoomLifecycleContributor let realtimePresence = MockRealtimePresence(["client1"].map { .init(clientId: $0) }) diff --git a/Tests/AblyChatTests/Helpers/Helpers.swift b/Tests/AblyChatTests/Helpers/Helpers.swift index 8db7abc..294a7be 100644 --- a/Tests/AblyChatTests/Helpers/Helpers.swift +++ b/Tests/AblyChatTests/Helpers/Helpers.swift @@ -39,3 +39,45 @@ extension Array where Element == PresenceEventType { PresenceEventType.update ] } + +struct RoomLifecycleHelper { + + static let fakeNetworkDelay: UInt64 = 10 // milliseconds; without this delay (or with a very low value such as 1) most of the time attach happens before lifecycleManager has a chance to start waiting. + + static func createManager( + forTestingWhatHappensWhenCurrentlyIn status: DefaultRoomLifecycleManager.Status? = nil, + forTestingWhatHappensWhenHasPendingDiscontinuityEvents pendingDiscontinuityEvents: [MockRoomLifecycleContributor.ID: DiscontinuityEvent]? = nil, + forTestingWhatHappensWhenHasTransientDisconnectTimeoutForTheseContributorIDs idsOfContributorsWithTransientDisconnectTimeout: Set? = nil, + contributors: [MockRoomLifecycleContributor] = [], + clock: SimpleClock = MockSimpleClock() + ) async -> DefaultRoomLifecycleManager { + await .init( + testsOnly_status: status, + testsOnly_pendingDiscontinuityEvents: pendingDiscontinuityEvents, + testsOnly_idsOfContributorsWithTransientDisconnectTimeout: idsOfContributorsWithTransientDisconnectTimeout, + contributors: contributors, + logger: TestLogger(), + clock: clock + ) + } + + static func createContributor( + initialState: ARTRealtimeChannelState = .initialized, + initialErrorReason: ARTErrorInfo? = nil, + feature: RoomFeature = .messages, // Arbitrarily chosen, its value only matters in test cases where we check which error is thrown + attachBehavior: MockRoomLifecycleContributorChannel.AttachOrDetachBehavior? = nil, + detachBehavior: MockRoomLifecycleContributorChannel.AttachOrDetachBehavior? = nil, + subscribeToStateBehavior: MockRoomLifecycleContributorChannel.SubscribeToStateBehavior? = nil + ) -> MockRoomLifecycleContributor { + .init( + feature: feature, + channel: .init( + initialState: initialState, + initialErrorReason: initialErrorReason, + attachBehavior: attachBehavior, + detachBehavior: detachBehavior, + subscribeToStateBehavior: subscribeToStateBehavior + ) + ) + } +}