Skip to content

Commit 9a31748

Browse files
committed
ChannelEventBusOptionWhenSendingToBusDoesNotExist
1 parent b76fb81 commit 9a31748

File tree

5 files changed

+112
-25
lines changed

5 files changed

+112
-25
lines changed

.editorconfig

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -14,5 +14,7 @@ ktlint_standard_property-naming=disabled
1414
ktlint_standard_function-naming=disabled
1515
filename=disabled
1616
ktlint_experimental=enabled
17+
ij_kotlin_name_count_to_use_star_import=999
18+
ij_kotlin_name_count_to_use_star_import_for_members=999
1719
[*.xml]
1820
indent_size=4

channel-event-bus/api/channel-event-bus.api

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -13,11 +13,12 @@ public abstract interface class com/hoc081098/channeleventbus/ChannelEventBus {
1313
public abstract fun close ()V
1414
public abstract fun closeKey (Lcom/hoc081098/channeleventbus/ChannelEvent$Key;Ljava/util/Set;)V
1515
public abstract fun receiveAsFlow (Lcom/hoc081098/channeleventbus/ChannelEvent$Key;)Lkotlinx/coroutines/flow/Flow;
16-
public abstract fun send (Lcom/hoc081098/channeleventbus/ChannelEvent;)V
16+
public abstract fun send (Lcom/hoc081098/channeleventbus/ChannelEvent;Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;)V
1717
}
1818

1919
public final class com/hoc081098/channeleventbus/ChannelEventBus$DefaultImpls {
2020
public static synthetic fun closeKey$default (Lcom/hoc081098/channeleventbus/ChannelEventBus;Lcom/hoc081098/channeleventbus/ChannelEvent$Key;Ljava/util/Set;ILjava/lang/Object;)V
21+
public static synthetic fun send$default (Lcom/hoc081098/channeleventbus/ChannelEventBus;Lcom/hoc081098/channeleventbus/ChannelEvent;Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;ILjava/lang/Object;)V
2122
}
2223

2324
public abstract class com/hoc081098/channeleventbus/ChannelEventBusException : java/lang/RuntimeException {
@@ -44,17 +45,26 @@ public final class com/hoc081098/channeleventbus/ChannelEventBusException$CloseE
4445
public fun getKey ()Lcom/hoc081098/channeleventbus/ChannelEvent$Key;
4546
}
4647

47-
public final class com/hoc081098/channeleventbus/ChannelEventBusException$FailedToSendEvent : com/hoc081098/channeleventbus/ChannelEventBusException {
48-
public fun <init> (Lcom/hoc081098/channeleventbus/ChannelEvent;Ljava/lang/Throwable;)V
49-
public final fun getEvent ()Lcom/hoc081098/channeleventbus/ChannelEvent;
48+
public final class com/hoc081098/channeleventbus/ChannelEventBusException$FlowAlreadyCollected : com/hoc081098/channeleventbus/ChannelEventBusException {
49+
public fun <init> (Lcom/hoc081098/channeleventbus/ChannelEvent$Key;)V
5050
public fun getKey ()Lcom/hoc081098/channeleventbus/ChannelEvent$Key;
5151
}
5252

53-
public final class com/hoc081098/channeleventbus/ChannelEventBusException$FlowAlreadyCollected : com/hoc081098/channeleventbus/ChannelEventBusException {
53+
public abstract class com/hoc081098/channeleventbus/ChannelEventBusException$SendException : com/hoc081098/channeleventbus/ChannelEventBusException {
54+
public synthetic fun <init> (Ljava/lang/String;Ljava/lang/Throwable;Lkotlin/jvm/internal/DefaultConstructorMarker;)V
55+
}
56+
57+
public final class com/hoc081098/channeleventbus/ChannelEventBusException$SendException$BusDoesNotExist : com/hoc081098/channeleventbus/ChannelEventBusException$CloseException {
5458
public fun <init> (Lcom/hoc081098/channeleventbus/ChannelEvent$Key;)V
5559
public fun getKey ()Lcom/hoc081098/channeleventbus/ChannelEvent$Key;
5660
}
5761

62+
public final class com/hoc081098/channeleventbus/ChannelEventBusException$SendException$FailedToSendEvent : com/hoc081098/channeleventbus/ChannelEventBusException$SendException {
63+
public fun <init> (Lcom/hoc081098/channeleventbus/ChannelEvent;Ljava/lang/Throwable;)V
64+
public final fun getEvent ()Lcom/hoc081098/channeleventbus/ChannelEvent;
65+
public fun getKey ()Lcom/hoc081098/channeleventbus/ChannelEvent$Key;
66+
}
67+
5868
public final class com/hoc081098/channeleventbus/ChannelEventBusKt {
5969
public static final fun ChannelEventBus (Lcom/hoc081098/channeleventbus/ChannelEventBusLogger;)Lcom/hoc081098/channeleventbus/ChannelEventBus;
6070
public static synthetic fun ChannelEventBus$default (Lcom/hoc081098/channeleventbus/ChannelEventBusLogger;ILjava/lang/Object;)Lcom/hoc081098/channeleventbus/ChannelEventBus;
@@ -75,6 +85,15 @@ public final class com/hoc081098/channeleventbus/ChannelEventBusLogger$Companion
7585
public final fun stdout ()Lcom/hoc081098/channeleventbus/ChannelEventBusLogger;
7686
}
7787

88+
public final class com/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist : java/lang/Enum {
89+
public static final field CREATE_NEW_BUS Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;
90+
public static final field DO_NOTHING Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;
91+
public static final field THROW_EXCEPTION Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;
92+
public static fun getEntries ()Lkotlin/enums/EnumEntries;
93+
public static fun valueOf (Ljava/lang/String;)Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;
94+
public static fun values ()[Lcom/hoc081098/channeleventbus/ChannelEventBusOptionWhenSendingToBusDoesNotExist;
95+
}
96+
7897
public final class com/hoc081098/channeleventbus/ChannelEventBusValidationBeforeClosing : java/lang/Enum {
7998
public static final field ALL Ljava/util/Set;
8099
public static final field Companion Lcom/hoc081098/channeleventbus/ChannelEventBusValidationBeforeClosing$Companion;

channel-event-bus/src/commonMain/kotlin/com/hoc081098/channeleventbus/ChannelEventBus.kt

Lines changed: 36 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,8 @@
11
package com.hoc081098.channeleventbus
22

3+
import com.hoc081098.channeleventbus.ChannelEventBusOptionWhenSendingToBusDoesNotExist.CREATE_NEW_BUS
4+
import com.hoc081098.channeleventbus.ChannelEventBusOptionWhenSendingToBusDoesNotExist.DO_NOTHING
5+
import com.hoc081098.channeleventbus.ChannelEventBusOptionWhenSendingToBusDoesNotExist.THROW_EXCEPTION
36
import com.hoc081098.channeleventbus.ChannelEventBusValidationBeforeClosing.REQUIRE_BUS_IS_EMPTY
47
import com.hoc081098.channeleventbus.ChannelEventBusValidationBeforeClosing.REQUIRE_BUS_IS_EXISTING
58
import com.hoc081098.channeleventbus.ChannelEventBusValidationBeforeClosing.REQUIRE_FLOW_IS_NOT_COLLECTING
@@ -54,11 +57,18 @@ import kotlinx.coroutines.internal.synchronized as coroutinesSynchronized
5457
public sealed interface ChannelEventBus {
5558
/**
5659
* Send [event] to the bus identified by [ChannelEvent.key].
57-
* If the bus associated with `event.key` does not exist, a new bus will be created.
5860
*
59-
* @throws ChannelEventBusException.FailedToSendEvent if failed to send the event.
61+
* When the bus associated with `event.key` does not exist, the behavior is determined by [option].
62+
* See [ChannelEventBusOptionWhenSendingToBusDoesNotExist] for more details.
63+
*
64+
* @throws ChannelEventBusException.SendException if failed to send the event.
65+
* @see ChannelEventBusOptionWhenSendingToBusDoesNotExist
6066
*/
61-
public fun <E : ChannelEvent<E>> send(event: E)
67+
@Throws(ChannelEventBusException.SendException::class)
68+
public fun <E : ChannelEvent<E>> send(
69+
event: E,
70+
option: ChannelEventBusOptionWhenSendingToBusDoesNotExist = CREATE_NEW_BUS,
71+
)
6272

6373
/**
6474
* Receive events from the bus identified by [ChannelEvent.key].
@@ -72,6 +82,7 @@ public sealed interface ChannelEventBus {
7282
* @throws ChannelEventBusException.FlowAlreadyCollected if collecting the flow is already collected
7383
* by another collector.
7484
*/
85+
@Throws(ChannelEventBusException.FlowAlreadyCollected::class)
7586
public fun <T : ChannelEvent<T>> receiveAsFlow(key: ChannelEventKey<T>): Flow<T>
7687

7788
/**
@@ -87,6 +98,7 @@ public sealed interface ChannelEventBus {
8798
* @throws ChannelEventBusException.CloseException if failed to close the bus.
8899
* @see ChannelEventBusValidationBeforeClosing
89100
*/
101+
@Throws(ChannelEventBusException.CloseException::class)
90102
public fun closeKey(
91103
key: ChannelEventKey<*>,
92104
validations: Set<ChannelEventBusValidationBeforeClosing> = ChannelEventBusValidationBeforeClosing.ALL,
@@ -133,6 +145,13 @@ private class ChannelEventBusImpl(
133145
*/
134146
private val _busMap = SynchronizedHashMap<ChannelEventKey<*>, Bus>()
135147

148+
private fun getOrNull(key: ChannelEventKey<*>): Bus? = _busMap.synchronized { _busMap[key] }
149+
150+
private fun getOrThrow(key: ChannelEventKey<*>): Bus = _busMap.synchronized {
151+
_busMap[key]
152+
?: throw ChannelEventBusException.SendException.BusDoesNotExist(key)
153+
}
154+
136155
private fun getOrCreateBus(key: ChannelEventKey<*>): Bus =
137156
_busMap.synchronized {
138157
_busMap.getOrPut(key) {
@@ -196,11 +215,20 @@ private class ChannelEventBusImpl(
196215

197216
// ---------------------------------------------------------------------------------------------
198217

199-
override fun <E : ChannelEvent<E>> send(event: E) = getOrCreateBus(event.key)
200-
.channel
201-
.trySend(event)
202-
.getOrElse { throw ChannelEventBusException.FailedToSendEvent(event, it) }
203-
.also { logger?.onSent(event, this) }
218+
override fun <E : ChannelEvent<E>> send(
219+
event: E,
220+
option: ChannelEventBusOptionWhenSendingToBusDoesNotExist,
221+
) {
222+
when (option) {
223+
CREATE_NEW_BUS -> getOrCreateBus(event.key)
224+
THROW_EXCEPTION -> getOrThrow(event.key)
225+
DO_NOTHING -> getOrNull(event.key) ?: return
226+
}
227+
.channel
228+
.trySend(event)
229+
.getOrElse { throw ChannelEventBusException.SendException.FailedToSendEvent(event, it) }
230+
.also { logger?.onSent(event, this) }
231+
}
204232

205233
override fun <T : ChannelEvent<T>> receiveAsFlow(key: ChannelEventKey<T>): Flow<T> = flow {
206234
try {

channel-event-bus/src/commonMain/kotlin/com/hoc081098/channeleventbus/ChannelEventBusException.kt

Lines changed: 24 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -6,18 +6,6 @@ package com.hoc081098.channeleventbus
66
public sealed class ChannelEventBusException(message: String?, cause: Throwable?) : RuntimeException(message, cause) {
77
public abstract val key: ChannelEventKey<*>
88

9-
/**
10-
* Represents an exception thrown when failed to send an event to a bus.
11-
*
12-
* @param event the event that failed to send.
13-
*/
14-
public class FailedToSendEvent(
15-
public val event: ChannelEvent<*>,
16-
cause: Throwable?,
17-
) : ChannelEventBusException("Failed to send event: $event", cause) {
18-
override val key: ChannelEventKey<*> get() = event.key
19-
}
20-
219
/**
2210
* Represents an exception thrown when trying to collect a flow that is already collected by another collector.
2311
*/
@@ -51,4 +39,28 @@ public sealed class ChannelEventBusException(message: String?, cause: Throwable?
5139
override val key: ChannelEventKey<*>,
5240
) : CloseException("Bus by key=$key is not empty, try to consume all elements before closing", null)
5341
}
42+
43+
/**
44+
*
45+
*/
46+
public sealed class SendException(message: String?, cause: Throwable?) : ChannelEventBusException(message, cause) {
47+
/**
48+
* Represents an exception thrown when trying to send an event to a bus that does not exist.
49+
*/
50+
public class BusDoesNotExist(
51+
override val key: ChannelEventKey<*>,
52+
) : CloseException("Bus by key=$key does not exist", null)
53+
54+
/**
55+
* Represents an exception thrown when failed to send an event to a bus.
56+
*
57+
* @param event the event that failed to send.
58+
*/
59+
public class FailedToSendEvent(
60+
public val event: ChannelEvent<*>,
61+
cause: Throwable?,
62+
) : SendException("Failed to send event: $event", cause) {
63+
override val key: ChannelEventKey<*> get() = event.key
64+
}
65+
}
5466
}
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,26 @@
1+
package com.hoc081098.channeleventbus
2+
3+
/**
4+
* Option when sending an event to a bus that does not exist.
5+
* - Create a new bus if the bus associated with [ChannelEvent.key] does not exist.
6+
* - Throw [ChannelEventBusException.SendException.BusDoesNotExist] if the bus associated with [ChannelEvent.key] does not exist.
7+
* - Do nothing if the bus associated with [ChannelEvent.key] does not exist.
8+
*/
9+
public enum class ChannelEventBusOptionWhenSendingToBusDoesNotExist {
10+
/**
11+
* Create a new bus if the bus associated with [ChannelEvent.key] does not exist.
12+
* This is the default option.
13+
*/
14+
CREATE_NEW_BUS,
15+
16+
/**
17+
* Throw [ChannelEventBusException.SendException.BusDoesNotExist] if the bus associated with [ChannelEvent.key] does not exist.
18+
*/
19+
THROW_EXCEPTION,
20+
21+
/**
22+
* Do nothing if the bus associated with [ChannelEvent.key] does not exist.
23+
* Basically, the event will be ignored (not sent) if the bus does not exist.
24+
*/
25+
DO_NOTHING,
26+
}

0 commit comments

Comments
 (0)