Add com.shr4pnel.ferretirc.irc package to model the live state of IRC

This commit is contained in:
2026-09-12 20:10:54 +01:00
parent 3ad2740dd2
commit d52b1085f9
4 changed files with 67 additions and 0 deletions
@@ -0,0 +1,5 @@
package com.shr4pnel.ferretirc.irc
class IRCChannel(val chanName: String, val clientCount: Int, val topic: String) {
}
@@ -0,0 +1,23 @@
package com.shr4pnel.ferretirc.irc
data class ISupportFeatures(val capabilities: List<Feature>)
sealed class Feature(key: String) {
// Indicates the maximum number of online nicknames a user may have in their accept list. First introduced in ircd-ratbox-3.0.9(r28737).
data class ACCEPT(val max: Int) : Feature("ACCEPT")
// Indicates the maximum length of an away message. If "number" is not defined, there is no limit.
data class AWAYLEN(val max: Int) : Feature("AWAYLEN")
// Indicates the character to be used as a user mode to let clients mark themselves as bots by setting it
data class BOT(val letter: Char) : Feature("BOT")
// Indicates that the "caller-id" user mode is supported, which rejects messages from unauthorized users. "letter" defines the mode character, which is used for this feature. If the value is not given, it defaults to the mode "g".
data class CALLERID(val letter: Char) : Feature("CALLERID")
// Indicates the method thats used to compare equality of case-insensitive strings (such as nick/channel names). Typical values include "ascii" and "rfc1459". "rfc3454" is a proposed value that refers to the stringprep method described in RFC3454 (typically used for UTF-8 casefolding).
data class CASEMAPPING(val method: String) : Feature("CASEMAPPING")
// Indicates the maximum length of a nickname that a client may use. Other clients on the network may have nicknames longer than this.
data class MAXNICKLEN(val max: Int) : Feature("MAXNICKLEN")
}
@@ -0,0 +1,36 @@
package com.shr4pnel.ferretirc.irc
import com.shr4pnel.ferretirc.net.messages.ClientMessage
import com.shr4pnel.ferretirc.net.messages.ServerMessage
import kotlinx.coroutines.CoroutineScope
import kotlinx.coroutines.channels.Channel
import kotlinx.coroutines.flow.SharedFlow
import kotlinx.coroutines.flow.filterIsInstance
import kotlinx.coroutines.flow.onSubscription
import kotlinx.coroutines.flow.takeWhile
class Server(private val msgBuffer: SharedFlow<ServerMessage>, private val outgoingMessages: Channel<ClientMessage>, private val scope: CoroutineScope) {
lateinit var features: ISupportFeatures
private set
var channels: Set<IRCChannel> = setOf()
private set
suspend fun fetchChannels(): Set<IRCChannel> {
val buffer = mutableSetOf<IRCChannel>()
msgBuffer
.onSubscription { outgoingMessages.send(ClientMessage.List()) }
.filterIsInstance<ServerMessage.Numeric>()
.takeWhile { it !is ServerMessage.Numeric.RPL_LISTEND }
.filterIsInstance<ServerMessage.Numeric.RPL_LIST>()
.collect { buffer.add(IRCChannel(it.chanName, it.clientCount, it.topic)) }
channels = buffer.toSortedSet(compareBy { it.chanName })
return channels
}
fun fetchFeatures() {
}
}
@@ -0,0 +1,3 @@
package com.shr4pnel.ferretirc.irc.util
class Helpers