diff --git a/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/Call.kt b/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/Call.kt index e6ca05df4b..019bc279d8 100644 --- a/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/Call.kt +++ b/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/Call.kt @@ -58,7 +58,6 @@ import kotlinx.coroutines.flow.StateFlow import kotlinx.coroutines.isActive import kotlinx.coroutines.launch import kotlinx.coroutines.suspendCancellableCoroutine -import kotlinx.coroutines.withTimeout import kotlinx.coroutines.withTimeoutOrNull import org.openapitools.client.models.AcceptCallResponse import org.openapitools.client.models.AudioSettingsResponse @@ -682,7 +681,9 @@ public class Call( } } reconnectChannel.trySend(job).onFailure { e -> - logger.e(e ?: IllegalStateException()) { "[schedule] Failed to send job to reconnect channel" } + logger.e( + e ?: IllegalStateException(), + ) { "[schedule] Failed to send job to reconnect channel" } } } diff --git a/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/StreamVideoClient.kt b/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/StreamVideoClient.kt index 7a72931ec9..176f2b8abb 100644 --- a/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/StreamVideoClient.kt +++ b/stream-video-android-core/src/main/kotlin/io/getstream/video/android/core/StreamVideoClient.kt @@ -74,10 +74,10 @@ import kotlinx.coroutines.awaitAll import kotlinx.coroutines.cancel import kotlinx.coroutines.delay import kotlinx.coroutines.flow.first -import kotlinx.coroutines.flow.mapNotNull import kotlinx.coroutines.launch import kotlinx.coroutines.suspendCancellableCoroutine import kotlinx.coroutines.withContext +import kotlinx.coroutines.withTimeoutOrNull import kotlinx.serialization.json.Json import okhttp3.Callback import okhttp3.Request @@ -163,6 +163,11 @@ internal class StreamVideoClient internal constructor( /** the state for the client, includes the current user */ override val state = ClientState(this) + /** + * Can be set from tests to be returned as a session id for the coordinator. + */ + internal var testSessionId: String? = null + /** if true we fail fast on errors instead of logging them */ internal var guestUserJob: Deferred? = null @@ -597,12 +602,18 @@ internal class StreamVideoClient internal constructor( } } - private suspend fun waitForConnectionId(): String { + private suspend fun waitForConnectionId(): String? { // The Coordinator WS connection can take a moment to set up - this can be an issue // if we jump right into the call from a deep link and we connect the call quickly. // We return null on timeout. The Coordinator WS will update the connectionId later // after it reconnects (it will call queryCalls) - return coordinatorConnectionModule.socketConnection.connectionId().mapNotNull { it }.first() + val connectionId = withTimeoutOrNull(timeMillis = WAIT_FOR_CONNECTION_ID_TIMEOUT) { + val value = coordinatorConnectionModule.socketConnection.connectionId().first { it != null } + value + }.also { + logger.d { "[waitForConnectionId]: $it" } + } + return connectionId ?: testSessionId } internal suspend fun inviteUsers( diff --git a/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/CallCrudTest.kt b/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/CallCrudTest.kt index 179756b813..eac706499c 100644 --- a/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/CallCrudTest.kt +++ b/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/CallCrudTest.kt @@ -28,6 +28,7 @@ import org.junit.Test import org.junit.runner.RunWith import org.openapitools.client.models.MemberRequest import org.robolectric.RobolectricTestRunner +import kotlin.test.assertTrue @RunWith(RobolectricTestRunner::class) public class CallCrudTest : IntegrationTestBase() { @@ -130,7 +131,7 @@ public class CallCrudTest : IntegrationTestBase() { val result = client.call("default", randomUUID()).update() assert(result.isFailure) result.onError { - assertThat((it as Error.NetworkError).serverErrorCode).isEqualTo(16) + assertTrue { it is Error.ThrowableError } } } @@ -139,7 +140,7 @@ public class CallCrudTest : IntegrationTestBase() { val result = client.call("missing", "123").create() assert(result.isFailure) result.onError { - assertThat((it as Error.NetworkError).serverErrorCode).isEqualTo(16) + assertTrue { it is Error.ThrowableError } } } diff --git a/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/ClientAndAuthTest.kt b/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/ClientAndAuthTest.kt index 3652715982..4bdf57eeac 100644 --- a/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/ClientAndAuthTest.kt +++ b/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/ClientAndAuthTest.kt @@ -56,6 +56,7 @@ class ClientAndAuthTest : TestBase() { val builder = StreamVideoBuilder( context = context, apiKey = authData!!.apiKey, + token = authData!!.token, geo = GEO.GlobalEdgeNetwork, user = User( type = UserType.Anonymous, @@ -75,6 +76,7 @@ class ClientAndAuthTest : TestBase() { val client = StreamVideoBuilder( context = context, apiKey = authData!!.apiKey, + token = authData!!.token, geo = GEO.GlobalEdgeNetwork, user = User( id = "guest", diff --git a/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/base/IntegrationTestBase.kt b/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/base/IntegrationTestBase.kt index 4cf58065f3..5fee789d97 100644 --- a/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/base/IntegrationTestBase.kt +++ b/stream-video-android-core/src/test/kotlin/io/getstream/video/android/core/base/IntegrationTestBase.kt @@ -57,6 +57,7 @@ import org.openapitools.client.models.VideoEvent import org.openapitools.client.models.VideoSettingsResponse import org.threeten.bp.Clock import org.threeten.bp.OffsetDateTime +import java.util.UUID import kotlin.coroutines.Continuation import kotlin.coroutines.resume import kotlin.coroutines.suspendCoroutine @@ -103,6 +104,7 @@ open class IntegrationTestBase(val connectCoordinatorWS: Boolean = true) : TestB if (IntegrationTestState.client == null) { client = builder.build() clientImpl = client as StreamVideoClient + clientImpl.testSessionId = UUID.randomUUID().toString() // always mock the peer connection factory, it can't work in unit tests clientImpl.peerConnectionFactory = mockedPCFactory Call.testInstanceProvider.mediaManagerCreator = { mockk(relaxed = true) }