Skip to content

Commit 12ecee1

Browse files
committed
[ECO-5056] Updated test helper getMockObjectsAdapter with static mocck
1. Encouraged use of global mocck for Adapter 2. Updated failing tests accordingly
1 parent c8c84e7 commit 12ecee1

5 files changed

Lines changed: 55 additions & 78 deletions

File tree

liveobjects/src/main/kotlin/io/ably/lib/objects/Helpers.kt

Lines changed: 6 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -11,12 +11,14 @@ import kotlinx.coroutines.suspendCancellableCoroutine
1111
import kotlin.coroutines.resume
1212
import kotlin.coroutines.resumeWithException
1313

14+
internal val ObjectsAdapter.connectionManager get() = connection.connectionManager
15+
1416
/**
1517
* Spec: RTO15g
1618
*/
1719
internal suspend fun ObjectsAdapter.sendAsync(message: ProtocolMessage) = suspendCancellableCoroutine { continuation ->
1820
try {
19-
connection.connectionManager.send(message, clientOptions.queueMessages, object : CompletionListener {
21+
connectionManager.send(message, clientOptions.queueMessages, object : CompletionListener {
2022
override fun onSuccess() {
2123
continuation.resume(Unit)
2224
}
@@ -47,7 +49,6 @@ internal suspend fun ObjectsAdapter.attachAsync(channelName: String) = suspendCa
4749
}
4850

4951
internal fun ObjectsAdapter.retrieveObjectsGCGracePeriod(block : (Long?) -> Unit) {
50-
val connectionManager = connection.connectionManager
5152
if (connectionManager.objectsGCGracePeriod != null) {
5253
block(connectionManager.objectsGCGracePeriod)
5354
return
@@ -88,7 +89,7 @@ internal fun ObjectsAdapter.getChannelModes(channelName: String): Array<ChannelM
8889
* Spec: RTO15d
8990
*/
9091
internal fun ObjectsAdapter.ensureMessageSizeWithinLimit(objectMessages: Array<ObjectMessage>) {
91-
val maximumAllowedSize = connection.connectionManager.maxMessageSize
92+
val maximumAllowedSize = connectionManager.maxMessageSize
9293
val objectsTotalMessageSize = objectMessages.sumOf { it.size() }
9394
if (objectsTotalMessageSize > maximumAllowedSize) {
9495
throw ablyException("ObjectMessages size $objectsTotalMessageSize exceeds maximum allowed size of $maximumAllowedSize bytes",
@@ -143,8 +144,8 @@ internal fun ObjectsAdapter.throwIfInvalidWriteApiConfiguration(channelName: Str
143144
}
144145

145146
internal fun ObjectsAdapter.throwIfUnpublishableState(channelName: String) {
146-
if (!connection.connectionManager.isActive) {
147-
throw ablyException(connection.connectionManager.stateErrorInfo)
147+
if (!connectionManager.isActive) {
148+
throw ablyException(connectionManager.stateErrorInfo)
148149
}
149150
throwIfInChannelState(channelName, arrayOf(ChannelState.failed, ChannelState.suspended))
150151
}

liveobjects/src/test/kotlin/io/ably/lib/objects/unit/HelpersTest.kt

Lines changed: 32 additions & 48 deletions
Original file line numberDiff line numberDiff line change
@@ -7,12 +7,11 @@ import io.ably.lib.realtime.ChannelStateListener
77
import io.ably.lib.realtime.CompletionListener
88
import io.ably.lib.transport.ConnectionManager
99
import io.ably.lib.types.*
10-
import io.mockk.every
11-
import io.mockk.mockk
12-
import io.mockk.slot
13-
import io.mockk.verify
10+
import io.mockk.*
1411
import kotlinx.coroutines.test.runTest
12+
import org.junit.After
1513
import org.junit.Assert.*
14+
import org.junit.Before
1615
import org.junit.Test
1716
import kotlin.test.assertFailsWith
1817

@@ -21,13 +20,10 @@ class HelpersTest {
2120
// sendAsync
2221
@Test
2322
fun testSendAsyncShouldQueueAccordingToClientOptions() = runTest {
24-
val adapter = mockk<ObjectsAdapter>(relaxed = true)
25-
val connManager = mockk<ConnectionManager>(relaxed = true)
23+
val adapter = getMockObjectsAdapter()
24+
val connManager = adapter.connectionManager
2625
val clientOptions = ClientOptions().apply { queueMessages = false }
2726

28-
every { adapter.connection } returns mockk(relaxed = true) {
29-
setPrivateField("connectionManager", connManager)
30-
}
3127
every { adapter.clientOptions } returns clientOptions
3228

3329
every { connManager.send(any(), any(), any()) } answers {
@@ -46,13 +42,10 @@ class HelpersTest {
4642

4743
@Test
4844
fun testSendAsyncErrorPropagatesAblyException() = runTest {
49-
val adapter = mockk<ObjectsAdapter>(relaxed = true)
50-
val connManager = mockk<ConnectionManager>(relaxed = true)
45+
val adapter = getMockObjectsAdapter()
46+
val connManager = adapter.connectionManager
5147
val clientOptions = ClientOptions()
5248

53-
every { adapter.connection } returns mockk(relaxed = true) {
54-
setPrivateField("connectionManager", connManager)
55-
}
5649
every { adapter.clientOptions } returns clientOptions
5750

5851
every { connManager.send(any(), any(), any()) } answers {
@@ -69,13 +62,10 @@ class HelpersTest {
6962

7063
@Test
7164
fun testSendAsyncThrowsWhenConnectionManagerThrows() = runTest {
72-
val adapter = mockk<ObjectsAdapter>(relaxed = true)
73-
val connManager = mockk<ConnectionManager>(relaxed = true)
65+
val adapter = getMockObjectsAdapter()
66+
val connManager = adapter.connectionManager
7467
val clientOptions = ClientOptions()
7568

76-
every { adapter.connection } returns mockk(relaxed = true) {
77-
setPrivateField("connectionManager", connManager)
78-
}
7969
every { adapter.clientOptions } returns clientOptions
8070

8171
every { connManager.send(any(), any(), any()) } throws RuntimeException("send failed hard")
@@ -251,25 +241,25 @@ class HelpersTest {
251241
verify(exactly = 1) { channel.once(any()) }
252242
}
253243

254-
@Test
255-
fun testEnsureAttachedAttachingButReceivesNonAttachedEmitsError() = runTest {
256-
val adapter = mockk<ObjectsAdapter>(relaxed = true)
257-
val channel = mockk<Channel>(relaxed = true)
258-
every { adapter.getChannel("ch") } returns channel
259-
channel.state = ChannelState.attaching
260-
every { channel.once(any()) } answers {
261-
val listener = firstArg<ChannelStateListener>()
262-
val stateChange = mockk<ChannelStateListener.ChannelStateChange>(relaxed = true) {
263-
setPrivateField("current", ChannelState.suspended)
264-
setPrivateField("reason", clientError("Not attached").errorInfo)
265-
}
266-
listener.onChannelStateChanged(stateChange)
267-
}
268-
val ex = assertFailsWith<AblyException> { adapter.ensureAttached("ch") }
269-
assertEquals(ErrorCode.ChannelStateError.code, ex.errorInfo.code)
270-
assertTrue(ex.errorInfo.message.contains("Not attached"))
271-
verify(exactly = 1) { channel.once(any()) }
272-
}
244+
@Test
245+
fun testEnsureAttachedAttachingButReceivesNonAttachedEmitsError() = runTest {
246+
val adapter = mockk<ObjectsAdapter>(relaxed = true)
247+
val channel = mockk<Channel>(relaxed = true)
248+
every { adapter.getChannel("ch") } returns channel
249+
channel.state = ChannelState.attaching
250+
every { channel.once(any()) } answers {
251+
val listener = firstArg<ChannelStateListener>()
252+
val stateChange = mockk<ChannelStateListener.ChannelStateChange>(relaxed = true) {
253+
setPrivateField("current", ChannelState.suspended)
254+
setPrivateField("reason", clientError("Not attached").errorInfo)
255+
}
256+
listener.onChannelStateChanged(stateChange)
257+
}
258+
val ex = assertFailsWith<AblyException> { adapter.ensureAttached("ch") }
259+
assertEquals(ErrorCode.ChannelStateError.code, ex.errorInfo.code)
260+
assertTrue(ex.errorInfo.message.contains("Not attached"))
261+
verify(exactly = 1) { channel.once(any()) }
262+
}
273263

274264
@Test
275265
fun testEnsureAttachedThrowsForInvalidState() = runTest {
@@ -350,11 +340,8 @@ class HelpersTest {
350340
// throwIfUnpublishableState
351341
@Test
352342
fun testThrowIfUnpublishableStateInactiveConnection() {
353-
val adapter = mockk<ObjectsAdapter>(relaxed = true)
354-
val connManager = mockk<ConnectionManager>(relaxed = true)
355-
every { adapter.connection } returns mockk(relaxed = true) {
356-
setPrivateField("connectionManager", connManager)
357-
}
343+
val adapter = getMockObjectsAdapter()
344+
val connManager = adapter.connectionManager
358345
every { connManager.isActive } returns false
359346
every { connManager.stateErrorInfo } returns serverError("not active").errorInfo
360347

@@ -365,11 +352,8 @@ class HelpersTest {
365352

366353
@Test
367354
fun testThrowIfUnpublishableStateChannelFailed() {
368-
val adapter = mockk<ObjectsAdapter>(relaxed = true)
369-
val connManager = mockk<ConnectionManager>(relaxed = true)
370-
every { adapter.connection } returns mockk(relaxed = true) {
371-
setPrivateField("connectionManager", connManager)
372-
}
355+
val adapter = getMockObjectsAdapter()
356+
val connManager = adapter.connectionManager
373357
every { connManager.isActive } returns true
374358
val channel = mockk<Channel>(relaxed = true)
375359
every { adapter.getChannel("ch") } returns channel

liveobjects/src/test/kotlin/io/ably/lib/objects/unit/ObjectMessageSizeTest.kt

Lines changed: 6 additions & 18 deletions
Original file line numberDiff line numberDiff line change
@@ -10,27 +10,19 @@ import io.ably.lib.objects.ObjectOperationAction
1010
import io.ably.lib.objects.ObjectValue
1111
import io.ably.lib.objects.ensureMessageSizeWithinLimit
1212
import io.ably.lib.objects.size
13-
import io.ably.lib.transport.ConnectionManager
1413
import io.ably.lib.transport.Defaults
1514
import io.ably.lib.types.AblyException
16-
import io.mockk.every
17-
import io.mockk.mockk
1815
import kotlinx.coroutines.test.runTest
1916
import org.junit.Test
2017
import kotlin.test.assertEquals
2118
import kotlin.test.assertFailsWith
2219

2320
class ObjectMessageSizeTest {
24-
2521
@Test
2622
fun testObjectMessageSizeWithinLimit() = runTest {
27-
val mockAdapter = mockk<ObjectsAdapter>(relaxed = true)
28-
val connManager = mockk<ConnectionManager>(relaxed = true)
29-
every { mockAdapter.connection } returns mockk(relaxed = true) {
30-
setPrivateField("connectionManager", connManager)
31-
}
32-
connManager.maxMessageSize = Defaults.maxMessageSize // 64 kb
33-
assertEquals(65536, connManager.maxMessageSize)
23+
val mockAdapter = getMockObjectsAdapter()
24+
mockAdapter.connectionManager.maxMessageSize = Defaults.maxMessageSize // 64 kb
25+
assertEquals(65536, mockAdapter.connectionManager.maxMessageSize)
3426

3527
// ObjectMessage with all size-contributing fields
3628
val objectMessage = ObjectMessage(
@@ -153,13 +145,9 @@ class ObjectMessageSizeTest {
153145

154146
@Test
155147
fun testObjectMessageSizeAboveLimit() = runTest {
156-
val mockAdapter = mockk<ObjectsAdapter>(relaxed = true)
157-
val connManager = mockk<ConnectionManager>(relaxed = true)
158-
every { mockAdapter.connection } returns mockk(relaxed = true) {
159-
setPrivateField("connectionManager", connManager)
160-
}
161-
connManager.maxMessageSize = Defaults.maxMessageSize // 64 kb
162-
assertEquals(65536, connManager.maxMessageSize)
148+
val mockAdapter = getMockObjectsAdapter()
149+
mockAdapter.connectionManager.maxMessageSize = Defaults.maxMessageSize // 64 kb
150+
assertEquals(65536, mockAdapter.connectionManager.maxMessageSize)
163151

164152
// Create ObjectMessage with dummy data that results in size 60kb
165153
val objectMessage1 = ObjectMessage(

liveobjects/src/test/kotlin/io/ably/lib/objects/unit/TestHelpers.kt

Lines changed: 7 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -11,11 +11,13 @@ import io.ably.lib.objects.type.livemap.LiveMapManager
1111
import io.ably.lib.realtime.AblyRealtime
1212
import io.ably.lib.realtime.Channel
1313
import io.ably.lib.realtime.ChannelState
14+
import io.ably.lib.transport.ConnectionManager
1415
import io.ably.lib.types.ChannelMode
1516
import io.ably.lib.types.ChannelOptions
1617
import io.ably.lib.types.ClientOptions
1718
import io.mockk.every
1819
import io.mockk.mockk
20+
import io.mockk.mockkStatic
1921
import io.mockk.spyk
2022

2123
internal fun getMockRealtimeChannel(
@@ -45,9 +47,11 @@ internal fun getMockRealtimeChannel(
4547
}
4648

4749
internal fun getMockObjectsAdapter(): ObjectsAdapter {
48-
val mockkAdapter = mockk<ObjectsAdapter>(relaxed = true)
49-
every { mockkAdapter.getChannel(any()) } returns getMockRealtimeChannel("testChannelName")
50-
return mockkAdapter
50+
mockkStatic("io.ably.lib.objects.HelpersKt")
51+
return mockk<ObjectsAdapter>(relaxed = true) {
52+
every { getChannel(any()) } returns getMockRealtimeChannel("testChannelName")
53+
every { connectionManager } returns mockk<ConnectionManager>(relaxed = true)
54+
}
5155
}
5256

5357
internal fun getMockObjectsPool(): ObjectsPool {

liveobjects/src/test/kotlin/io/ably/lib/objects/unit/objects/ObjectsPoolTest.kt

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -19,7 +19,7 @@ class ObjectsPoolTest {
1919

2020
@Test
2121
fun `(RTO3, RTO3a, RTO3b) An internal ObjectsPool should be used to maintain the list of objects present on a channel`() {
22-
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", mockk(relaxed = true))
22+
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", getMockObjectsAdapter())
2323
val objectsPool = defaultRealtimeObjects.objectsPool
2424
assertNotNull(objectsPool)
2525

@@ -44,7 +44,7 @@ class ObjectsPoolTest {
4444

4545
@Test
4646
fun `(RTO6) ObjectsPool should create zero-value objects if not exists`() {
47-
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", mockk(relaxed = true))
47+
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", getMockObjectsAdapter())
4848
val objectsPool = spyk(defaultRealtimeObjects.objectsPool)
4949
assertEquals(1, objectsPool.size(), "RTO3 - Should only contain the root object initially")
5050

@@ -78,7 +78,7 @@ class ObjectsPoolTest {
7878

7979
@Test
8080
fun `(RTO4b1, RTO4b2) ObjectsPool should reset to initial pool retaining original root map`() {
81-
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", mockk(relaxed = true))
81+
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", getMockObjectsAdapter())
8282
val objectsPool = defaultRealtimeObjects.objectsPool
8383
assertEquals(1, objectsPool.size())
8484
val rootMap = objectsPool.get(ROOT_OBJECT_ID) as DefaultLiveMap
@@ -107,7 +107,7 @@ class ObjectsPoolTest {
107107

108108
@Test
109109
fun `(RTO5c2, RTO5c2a) ObjectsPool should delete extra object IDs`() {
110-
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", mockk(relaxed = true))
110+
val defaultRealtimeObjects = DefaultRealtimeObjects("dummyChannel", getMockObjectsAdapter())
111111
val objectsPool = defaultRealtimeObjects.objectsPool
112112

113113
// Add some objects

0 commit comments

Comments
 (0)