mirror of
https://github.com/mamoe/mirai.git
synced 2025-01-07 16:40:43 +08:00
Merge remote-tracking branch 'origin/master'
This commit is contained in:
commit
c0a9db0e07
25
UpdateLog.md
25
UpdateLog.md
@ -2,6 +2,31 @@
|
||||
|
||||
开发版本. 频繁更新, 不保证高稳定性
|
||||
|
||||
## `0.12.0` *2020/1/19*
|
||||
### mirai-core
|
||||
1. 监听消息时允许使用条件式的表达式, 如:
|
||||
```kotlin
|
||||
(contains("1") and has<Image>()){
|
||||
reply("Your message has a string '1' and an image contained")
|
||||
}
|
||||
|
||||
(contains("1") or endsWith("2")){
|
||||
|
||||
}
|
||||
```
|
||||
原有单一条件语法不变:
|
||||
```kotlin
|
||||
contains("1"){
|
||||
|
||||
}
|
||||
|
||||
"Hello" reply "World"
|
||||
```
|
||||
|
||||
2. Message: 修复 `eq` 无法正确判断的问题; 性能优化.
|
||||
3. 简化 logger 结构(API 不变).
|
||||
4. 事件 `cancelled` 属性修改为 `val` (以前是 `var` with `private set`)
|
||||
|
||||
## `0.11.0` *2020/1/12*
|
||||
### mirai-core
|
||||
- 弃用 `BotAccount.id`. 将来它可能会被改名成为邮箱等账号. QQ 号码需通过 `bot.uin` 获取.
|
||||
|
@ -1,7 +1,7 @@
|
||||
# style guide
|
||||
kotlin.code.style=official
|
||||
# config
|
||||
mirai_version=0.11.0
|
||||
mirai_version=0.12.0
|
||||
kotlin.incremental.multiplatform=true
|
||||
kotlin.parallel.tasks.in.project=true
|
||||
# kotlin
|
||||
|
@ -111,6 +111,9 @@ inline fun Bot.subscribeFriendMessages(crossinline listeners: MessageSubscribers
|
||||
}.apply { listeners() }
|
||||
}
|
||||
|
||||
|
||||
typealias MessageListener<T> = @MessageDsl suspend T.(String) -> Unit
|
||||
|
||||
/**
|
||||
* 消息订阅构造器
|
||||
*
|
||||
@ -121,130 +124,312 @@ inline fun Bot.subscribeFriendMessages(crossinline listeners: MessageSubscribers
|
||||
@Suppress("unused")
|
||||
@MessageDsl
|
||||
class MessageSubscribersBuilder<T : MessagePacket<*, *>>(
|
||||
val subscriber: (@MessageDsl suspend T.(String) -> Unit) -> Listener<T>
|
||||
val subscriber: (MessageListener<T>) -> Listener<T>
|
||||
) {
|
||||
/**
|
||||
* 监听的条件
|
||||
*/
|
||||
inner class ListeningFilter(
|
||||
val filter: T.(String) -> Boolean
|
||||
) {
|
||||
/**
|
||||
* 进行逻辑 `or`.
|
||||
*/
|
||||
infix fun or(another: ListeningFilter): ListeningFilter =
|
||||
ListeningFilter { filter.invoke(this, it) || another.filter.invoke(this, it) }
|
||||
|
||||
/**
|
||||
* 进行逻辑 `and`.
|
||||
*/
|
||||
infix fun and(another: ListeningFilter): ListeningFilter =
|
||||
ListeningFilter { filter.invoke(this, it) && another.filter.invoke(this, it) }
|
||||
|
||||
/**
|
||||
* 进行逻辑 `xor`.
|
||||
*/
|
||||
infix fun xor(another: ListeningFilter): ListeningFilter =
|
||||
ListeningFilter { filter.invoke(this, it) xor another.filter.invoke(this, it) }
|
||||
|
||||
/**
|
||||
* 进行逻辑 `nand`, 即 `not and`.
|
||||
*/
|
||||
infix fun nand(another: ListeningFilter): ListeningFilter =
|
||||
ListeningFilter { !filter.invoke(this, it) || !another.filter.invoke(this, it) }
|
||||
|
||||
/**
|
||||
* 启动时间监听.
|
||||
*/
|
||||
// do not inline due to kotlin (1.3.61) bug: java.lang.IllegalAccessError
|
||||
operator fun invoke(onEvent: MessageListener<T>): Listener<T> {
|
||||
return content(filter, onEvent)
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 无任何触发条件.
|
||||
*/
|
||||
@MessageDsl
|
||||
fun always(onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> {
|
||||
return subscriber(onEvent)
|
||||
fun always(onEvent: MessageListener<T>): Listener<T> = subscriber(onEvent)
|
||||
|
||||
/**
|
||||
* 如果消息内容 `==` [equals]
|
||||
*/
|
||||
@MessageDsl
|
||||
fun case(
|
||||
equals: String,
|
||||
ignoreCase: Boolean = false,
|
||||
trim: Boolean = true
|
||||
): ListeningFilter {
|
||||
return if (trim) {
|
||||
val toCheck = equals.trim()
|
||||
content { it.trim().equals(toCheck, ignoreCase = ignoreCase) }
|
||||
} else {
|
||||
content { it.equals(equals, ignoreCase = ignoreCase) }
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息内容 `==` [equals], 就执行 [onEvent]
|
||||
* 如果消息内容 `==` [equals]
|
||||
* @param trim `true` 则删除首尾空格后比较
|
||||
* @param ignoreCase `true` 则不区分大小写
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun case(
|
||||
equals: String,
|
||||
trim: Boolean = true,
|
||||
ignoreCase: Boolean = false,
|
||||
trim: Boolean = true,
|
||||
crossinline onEvent: @MessageDsl suspend T.(String) -> Unit
|
||||
): Listener<T> {
|
||||
val toCheck = if (trim) equals.trim() else equals
|
||||
return content({ toCheck.equals(if (trim) it.trim() else it, ignoreCase = ignoreCase) }, onEvent)
|
||||
return content({ (if (trim) it.trim() else it).equals(toCheck, ignoreCase = ignoreCase) }, {
|
||||
onEvent(this, this.message.toString())
|
||||
})
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息内容包含 [sub], 就执行 [onEvent]
|
||||
* 如果消息内容包含 [sub]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun contains(sub: String, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> = content({ sub in it }, onEvent)
|
||||
fun contains(sub: String): ListeningFilter =
|
||||
content { sub in it }
|
||||
|
||||
/**
|
||||
* 如果消息的前缀是 [prefix], 就执行 [onEvent]
|
||||
* 如果消息内容包含 [sub]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun contains(
|
||||
sub: String,
|
||||
ignoreCase: Boolean = false,
|
||||
trim: Boolean = true,
|
||||
crossinline onEvent: MessageListener<T>
|
||||
): Listener<T> {
|
||||
return if (trim) {
|
||||
val toCheck = sub.trim()
|
||||
content({ it.trimStart().contains(toCheck, ignoreCase = ignoreCase) }, {
|
||||
onEvent(this, this.message.toString().trim())
|
||||
})
|
||||
} else {
|
||||
content({ it.contains(sub, ignoreCase = ignoreCase) }, {
|
||||
onEvent(this, this.message.toString())
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息的前缀是 [prefix]
|
||||
*/
|
||||
@MessageDsl
|
||||
fun startsWith(
|
||||
prefix: String,
|
||||
trim: Boolean = true
|
||||
): ListeningFilter {
|
||||
val toCheck = if (trim) prefix.trim() else prefix
|
||||
return content { (if (trim) it.trim() else it).startsWith(toCheck) }
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息的前缀是 [prefix]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun startsWith(
|
||||
prefix: String,
|
||||
removePrefix: Boolean = true,
|
||||
trim: Boolean = true,
|
||||
crossinline onEvent: @MessageDsl suspend T.(String) -> Unit
|
||||
): Listener<T> =
|
||||
content({ it.startsWith(prefix) }) {
|
||||
if (removePrefix) this.onEvent(this.message.toString().substringAfter(prefix))
|
||||
else onEvent(this, this.message.toString())
|
||||
): Listener<T> {
|
||||
return if (trim) {
|
||||
val toCheck = prefix.trim()
|
||||
content({ it.trimStart().startsWith(toCheck) }, {
|
||||
if (removePrefix) this.onEvent(this.message.toString().substringAfter(toCheck).trim())
|
||||
else onEvent(this, this.message.toString().trim())
|
||||
})
|
||||
} else {
|
||||
content({ it.startsWith(prefix) }, {
|
||||
if (removePrefix) this.onEvent(this.message.toString().removePrefix(prefix))
|
||||
else onEvent(this, this.message.toString())
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息的结尾是 [suffix], 就执行 [onEvent]
|
||||
* 如果消息的结尾是 [suffix]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun endsWith(suffix: String, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
content({ it.endsWith(suffix) }, onEvent)
|
||||
fun endsWith(suffix: String): ListeningFilter =
|
||||
content { it.endsWith(suffix) }
|
||||
|
||||
/**
|
||||
* 如果是这个人发的消息, 就执行 [onEvent]. 消息可以是好友消息也可以是群消息
|
||||
* 如果消息的结尾是 [suffix]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentBy(qqId: Long, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
content({ sender.id == qqId }, onEvent)
|
||||
inline fun endsWith(
|
||||
suffix: String,
|
||||
removeSuffix: Boolean = true,
|
||||
trim: Boolean = true,
|
||||
crossinline onEvent: @MessageDsl suspend T.(String) -> Unit
|
||||
): Listener<T> {
|
||||
return if (trim) {
|
||||
val toCheck = suffix.trim()
|
||||
content({ it.trimStart().startsWith(toCheck) }, {
|
||||
if (removeSuffix) this.onEvent(this.message.toString().substringBeforeLast(toCheck).trim())
|
||||
else onEvent(this, this.message.toString().trim())
|
||||
})
|
||||
} else {
|
||||
content({ it.startsWith(suffix) }, {
|
||||
if (removeSuffix) this.onEvent(this.message.toString().removeSuffix(suffix))
|
||||
else onEvent(this, this.message.toString())
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果是管理员或群主发的消息, 就执行 [onEvent]
|
||||
* 如果是这个人发的消息. 消息可以是好友消息也可以是群消息
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentByOperator(crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
content({ this is GroupMessage && sender.permission.isOperator() }, onEvent)
|
||||
fun sentBy(qqId: Long): ListeningFilter =
|
||||
content { sender.id == qqId }
|
||||
|
||||
/**
|
||||
* 如果是管理员发的消息, 就执行 [onEvent]
|
||||
* 如果是这个人发的消息. 消息可以是好友消息也可以是群消息
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentByAdministrator(crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
content({ this is GroupMessage && sender.permission.isAdministrator() }, onEvent)
|
||||
inline fun sentBy(qqId: Long, crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ this.sender.id == qqId }, onEvent)
|
||||
|
||||
/**
|
||||
* 如果是群主发的消息, 就执行 [onEvent]
|
||||
* 如果是管理员或群主发的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentByOwner(crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
content({ this is GroupMessage && sender.permission.isOwner() }, onEvent)
|
||||
fun sentByOperator(): ListeningFilter =
|
||||
content { this is GroupMessage && sender.permission.isOperator() }
|
||||
|
||||
/**
|
||||
* 如果是管理员或群主发的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentByOperator(crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ this is GroupMessage && this.sender.isOperator() }, onEvent)
|
||||
|
||||
/**
|
||||
* 如果是管理员发的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
fun sentByAdministrator(): ListeningFilter =
|
||||
content { this is GroupMessage && sender.permission.isAdministrator() }
|
||||
|
||||
/**
|
||||
* 如果是管理员发的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentByAdministrator(crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ this is GroupMessage && this.sender.isAdministrator() }, onEvent)
|
||||
|
||||
/**
|
||||
* 如果是群主发的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
fun sentByOwner(): ListeningFilter =
|
||||
content { this is GroupMessage && sender.isOwner() }
|
||||
|
||||
/**
|
||||
* 如果是群主发的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentByOwner(crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ this is GroupMessage && this.sender.isOwner() }, onEvent)
|
||||
|
||||
/**
|
||||
* 如果是来自这个群的消息
|
||||
*/
|
||||
@MessageDsl
|
||||
fun sentFrom(groupId: Long): ListeningFilter =
|
||||
content { this is GroupMessage && group.id == groupId }
|
||||
|
||||
/**
|
||||
* 如果是来自这个群的消息, 就执行 [onEvent]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun sentFrom(id: Long, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
content({ if (this is GroupMessage) group.id == id else false }, onEvent)
|
||||
inline fun sentFrom(groupId: Long, crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ this is GroupMessage && this.group.id == groupId }, onEvent)
|
||||
|
||||
/**
|
||||
* 如果消息内容包含 [M] 类型的 [Message]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun <reified M : Message> has(): ListeningFilter =
|
||||
content { message.any { it::class == M::class } }
|
||||
|
||||
/**
|
||||
* 如果消息内容包含 [M] 类型的 [Message], 就执行 [onEvent]
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun <reified M : Message> has(crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
subscriber { if (message.any { it::class == M::class }) onEvent(this, this.message.toString()) }
|
||||
inline fun <reified M : Message> has(crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ message.any { it::class == M::class } }, onEvent)
|
||||
|
||||
/**
|
||||
* 如果 [filter] 返回 `true`
|
||||
*/
|
||||
@MessageDsl
|
||||
fun content(filter: T.(String) -> Boolean): ListeningFilter =
|
||||
ListeningFilter(filter)
|
||||
|
||||
/**
|
||||
* 如果 [filter] 返回 `true` 就执行 `onEvent`
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun content(crossinline filter: T.(String) -> Boolean, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit): Listener<T> =
|
||||
subscriber { if (this.filter(message.toString())) onEvent(this, this.message.toString()) }
|
||||
inline fun content(crossinline filter: T.(String) -> Boolean, crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
subscriber {
|
||||
if (filter(this, it)) onEvent(this, it)
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息内容可由正则表达式匹配([Regex.matchEntire]), 就执行 `onEvent`
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun matching(regex: Regex, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit) {
|
||||
fun matching(regex: Regex): ListeningFilter =
|
||||
content { regex.matchEntire(it) != null }
|
||||
|
||||
/**
|
||||
* 如果 [filter] 返回 `true` 就执行 `onEvent`
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun matching(regex: Regex, crossinline onEvent: MessageListener<T>): Listener<T> =
|
||||
content({ regex.matchEntire(it) != null }, onEvent)
|
||||
}
|
||||
|
||||
/**
|
||||
* 如果消息内容可由正则表达式查找([Regex.find]), 就执行 `onEvent`
|
||||
*/
|
||||
@MessageDsl
|
||||
inline fun finding(regex: Regex, crossinline onEvent: @MessageDsl suspend T.(String) -> Unit) {
|
||||
content({ regex.find(it) != null }, onEvent)
|
||||
}
|
||||
fun finding(regex: Regex): ListeningFilter =
|
||||
content { regex.find(it) != null }
|
||||
|
||||
|
||||
/**
|
||||
* 若消息内容包含 [this] 则回复 [reply]
|
||||
*/
|
||||
@MessageDsl
|
||||
infix fun String.containsReply(reply: String) =
|
||||
content({ this@containsReply in it }) { this@content.reply(reply) }
|
||||
infix fun String.containsReply(reply: String): Listener<T> =
|
||||
content({ this@containsReply in it }, { reply(reply) })
|
||||
|
||||
/**
|
||||
* 若消息内容包含 [this] 则执行 [replier] 并将其返回值回复给发信对象.
|
||||
@ -254,11 +439,11 @@ class MessageSubscribersBuilder<T : MessagePacket<*, *>>(
|
||||
* @param replier 若返回 [Message] 则直接发送; 若返回 [Unit] 则不回复; 其他情况则 [Any.toString] 后回复
|
||||
*/
|
||||
@MessageDsl
|
||||
inline infix fun String.containsReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?) =
|
||||
content({ this@containsReply in it }) {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING") // false negative warning
|
||||
executeAndReply(replier)
|
||||
}
|
||||
inline infix fun String.containsReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?): Listener<T> =
|
||||
content({ this@containsReply in it }, {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING")
|
||||
this.executeAndReply(replier)
|
||||
})
|
||||
|
||||
/**
|
||||
* 若消息内容可由正则表达式匹配([Regex.matchEntire]), 则执行 [replier] 并将其返回值回复给发信对象.
|
||||
@ -268,12 +453,11 @@ class MessageSubscribersBuilder<T : MessagePacket<*, *>>(
|
||||
* @param replier 若返回 [Message] 则直接发送; 若返回 [Unit] 则不回复; 其他情况则 [Any.toString] 后回复
|
||||
*/
|
||||
@MessageDsl
|
||||
inline infix fun Regex.matchingReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?) {
|
||||
content({ this@matchingReply.matchEntire(it) != null }) {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING") // false negative warning
|
||||
executeAndReply(replier)
|
||||
}
|
||||
}
|
||||
inline infix fun Regex.matchingReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?): Listener<T> =
|
||||
content({ this@matchingReply.matchEntire(it) != null }, {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING")
|
||||
this.executeAndReply(replier)
|
||||
})
|
||||
|
||||
/**
|
||||
* 若消息内容可由正则表达式查找([Regex.find]), 则执行 [replier] 并将其返回值回复给发信对象.
|
||||
@ -283,12 +467,11 @@ class MessageSubscribersBuilder<T : MessagePacket<*, *>>(
|
||||
* @param replier 若返回 [Message] 则直接发送; 若返回 [Unit] 则不回复; 其他情况则 [Any.toString] 后回复
|
||||
*/
|
||||
@MessageDsl
|
||||
inline infix fun Regex.findingReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?) {
|
||||
content({ this@findingReply.find(it) != null }) {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING") // false negative warning
|
||||
executeAndReply(replier)
|
||||
}
|
||||
}
|
||||
inline infix fun Regex.findingReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?): Listener<T> =
|
||||
content({ this@findingReply.find(it) != null }, {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING")
|
||||
this.executeAndReply(replier)
|
||||
})
|
||||
|
||||
/**
|
||||
* 不考虑空格, 若消息内容以 [this] 开始则执行 [replier] 并将其返回值回复给发信对象.
|
||||
@ -304,14 +487,14 @@ class MessageSubscribersBuilder<T : MessagePacket<*, *>>(
|
||||
* @param replier 若返回 [Message] 则直接发送; 若返回 [Unit] 则不回复; 其他类型则 [Any.toString] 后回复
|
||||
*/
|
||||
@MessageDsl
|
||||
inline infix fun String.startsWithReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?) {
|
||||
inline infix fun String.startsWithReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?): Listener<T> {
|
||||
val toCheck = this.trimStart()
|
||||
content({ it.trimStart().startsWith(toCheck) }) {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING") // false negative warning
|
||||
executeAndReply {
|
||||
replier(it.removePrefix(toCheck).trim())
|
||||
return content({ it.trim().startsWith(toCheck) }, {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING")
|
||||
this.executeAndReply {
|
||||
replier(this, it.trim().removePrefix(toCheck))
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
/**
|
||||
@ -328,30 +511,36 @@ class MessageSubscribersBuilder<T : MessagePacket<*, *>>(
|
||||
* @param replier 若返回 [Message] 则直接发送; 若返回 [Unit] 则不回复; 其他情况则 [Any.toString] 后回复
|
||||
*/
|
||||
@MessageDsl
|
||||
inline infix fun String.endswithReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?) {
|
||||
inline infix fun String.endswithReply(crossinline replier: @MessageDsl suspend T.(String) -> Any?): Listener<T> {
|
||||
val toCheck = this.trimEnd()
|
||||
content({ it.endsWith(this@endswithReply) }) {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING") // false negative warning
|
||||
executeAndReply {
|
||||
replier(it.removeSuffix(toCheck).trim())
|
||||
return content({ it.trim().endsWith(toCheck) }, {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING")
|
||||
this.executeAndReply {
|
||||
replier(this, it.trim().removeSuffix(toCheck))
|
||||
}
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
@MessageDsl
|
||||
infix fun String.reply(reply: String) = case(this) {
|
||||
this@case.reply(reply)
|
||||
infix fun String.reply(reply: String): Listener<T> {
|
||||
val toCheck = this.trim()
|
||||
return content({ it.trim() == toCheck }, { reply(reply) })
|
||||
}
|
||||
|
||||
@MessageDsl
|
||||
inline infix fun String.reply(crossinline replier: @MessageDsl suspend T.(String) -> Any?) = case(this) {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING") // false negative warning
|
||||
executeAndReply(replier)
|
||||
inline infix fun String.reply(crossinline replier: @MessageDsl suspend T.(String) -> Any?): Listener<T> {
|
||||
val toCheck = this.trim()
|
||||
return content({ it.trim() == toCheck }, {
|
||||
@Suppress("DSL_SCOPE_VIOLATION_WARNING")
|
||||
this.executeAndReply {
|
||||
replier(this, it.trim())
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
@PublishedApi
|
||||
@Suppress("REDUNDANT_INLINE_SUSPEND_FUNCTION_TYPE") // false positive
|
||||
internal suspend inline fun T.executeAndReply(replier: @MessageDsl suspend T.(String) -> Any?) {
|
||||
internal suspend inline fun T.executeAndReply(replier: suspend T.(String) -> Any?) {
|
||||
when (val message = replier(this, this.message.toString())) {
|
||||
is Message -> this.reply(message)
|
||||
is Unit -> {
|
||||
|
@ -138,6 +138,10 @@ suspend fun main() {
|
||||
}.reply()
|
||||
}
|
||||
|
||||
(contains("1") and has<Image>()){
|
||||
reply("Your message has a string \"1\" and an image contained")
|
||||
}
|
||||
|
||||
has<Image> {
|
||||
if (this is FriendMessage || (this is GroupMessage && this.permission == MemberPermission.ADMINISTRATOR)) withContext(IO) {
|
||||
val image: Image by message
|
||||
|
Loading…
Reference in New Issue
Block a user