blob: 2b8775b448de65dc1dbd9a36021221ded41a05c5 [file] [log] [blame]
Roman Elizarov3aed4ee2017-03-06 12:21:05 +03001/*
2 * Copyright 2016-2017 JetBrains s.r.o.
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17package kotlinx.coroutines.experimental.channels
18
Roman Elizarov9fe5f462018-02-21 19:05:52 +030019import kotlinx.coroutines.experimental.*
Roman Elizarov9fe5f462018-02-21 19:05:52 +030020import kotlin.coroutines.experimental.*
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030021import kotlin.test.*
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030022
23class ConflatedChannelTest : TestBase() {
24 @Test
25 fun testBasicConflationOfferPoll() {
26 val q = ConflatedChannel<Int>()
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030027 assertNull(q.poll())
28 assertTrue(q.offer(1))
29 assertTrue(q.offer(2))
30 assertTrue(q.offer(3))
31 assertEquals(3, q.poll())
32 assertNull(q.poll())
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030033 }
34
35 @Test
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030036 fun testConflatedSend() = runTest {
Roman Elizarove6e8ce82017-06-05 17:04:39 +030037 val q = ConflatedChannel<Int>()
38 q.send(1)
39 q.send(2) // shall conflated previously sent
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030040 assertEquals(2, q.receiveOrNull())
Roman Elizarove6e8ce82017-06-05 17:04:39 +030041 }
42
43 @Test
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030044 fun testConflatedClose() = runTest {
Roman Elizarove6e8ce82017-06-05 17:04:39 +030045 val q = ConflatedChannel<Int>()
46 q.send(1)
47 q.close() // shall conflate sent item and become closed
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030048 assertNull(q.receiveOrNull())
Roman Elizarove6e8ce82017-06-05 17:04:39 +030049 }
50
51 @Test
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030052 fun testConflationSendReceive() = runTest {
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030053 val q = ConflatedChannel<Int>()
54 expect(1)
Roman Elizarov43e3af72017-07-21 16:01:31 +030055 launch(coroutineContext) { // receiver coroutine
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030056 expect(4)
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030057 assertEquals(2, q.receive())
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030058 expect(5)
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030059 assertEquals(3, q.receive()) // this receive suspends
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030060 expect(8)
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030061 assertEquals(6, q.receive()) // last conflated value
Roman Elizarov3aed4ee2017-03-06 12:21:05 +030062 expect(9)
63 }
64 expect(2)
65 q.send(1)
66 q.send(2) // shall conflate
67 expect(3)
68 yield() // to receiver
69 expect(6)
70 q.send(3) // send to the waiting receiver
71 q.send(4) // buffer
72 q.send(5) // conflate
73 q.send(6) // conflate again
74 expect(7)
75 yield() // to receiver
76 finish(10)
77 }
Roman Elizarovb555d912017-08-17 21:01:33 +030078
79 @Test
Vsevolod Tolstopyatov96191342018-04-20 18:13:33 +030080 fun testConsumeAll() = runTest {
Roman Elizarovb555d912017-08-17 21:01:33 +030081 val q = ConflatedChannel<Int>()
82 expect(1)
83 for (i in 1..10) {
84 q.send(i) // stores as last
85 }
86 q.cancel()
87 check(q.isClosedForSend)
88 check(q.isClosedForReceive)
89 check(q.receiveOrNull() == null)
90 finish(2)
91 }
Vsevolod Tolstopyatov4b9a5592018-04-11 13:17:14 +030092
Roman Elizarovf2bdf602018-04-26 11:29:47 +030093 @Test
94 fun testCancelWithCause() = runTest({ it is TestException }) {
Vsevolod Tolstopyatov4b9a5592018-04-11 13:17:14 +030095 val channel = ConflatedChannel<Int>()
Roman Elizarovf2bdf602018-04-26 11:29:47 +030096 channel.cancel(TestException())
Vsevolod Tolstopyatov4b9a5592018-04-11 13:17:14 +030097 channel.receiveOrNull()
98 }
Roman Elizarovf2bdf602018-04-26 11:29:47 +030099
100 private class TestException : Exception()
Vsevolod Tolstopyatov4b9a5592018-04-11 13:17:14 +0300101}