Support UnsupportedMessage (#1112)

* Support UnsupportedMessage

* Fix serialize

* `UnsupportedMessage.contentToString`: use `struct.contentHashCode()`

Co-authored-by: Karlatemp <karlatemp@vip.qq.com>
This commit is contained in:
Him188 2021-03-26 23:54:17 +08:00 committed by GitHub
parent 24587503a3
commit 430c2c59ad
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
10 changed files with 194 additions and 0 deletions

View File

@ -90,6 +90,7 @@ public abstract interface class net/mamoe/mirai/IMirai : net/mamoe/mirai/LowLeve
public abstract fun constructMessageSource (JLnet/mamoe/mirai/message/data/MessageSourceKind;JJ[II[ILnet/mamoe/mirai/message/data/MessageChain;)Lnet/mamoe/mirai/message/data/OfflineMessageSource;
public abstract fun createFileMessage (Ljava/lang/String;ILjava/lang/String;J)Lnet/mamoe/mirai/message/data/FileMessage;
public abstract fun createImage (Ljava/lang/String;)Lnet/mamoe/mirai/message/data/Image;
public abstract fun createUnsupportedMessage ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public fun downloadForwardMessage (Lnet/mamoe/mirai/Bot;Ljava/lang/String;)Ljava/util/List;
public abstract fun downloadForwardMessage (Lnet/mamoe/mirai/Bot;Ljava/lang/String;Lkotlin/coroutines/Continuation;)Ljava/lang/Object;
public fun downloadLongMessage (Lnet/mamoe/mirai/Bot;Ljava/lang/String;)Lnet/mamoe/mirai/message/data/MessageChain;
@ -4727,6 +4728,7 @@ public final class net/mamoe/mirai/message/data/MessageUtils {
public static final synthetic fun At (Lnet/mamoe/mirai/contact/UserOrBot;)Lnet/mamoe/mirai/message/data/At;
public static final synthetic fun FileMessage (Ljava/lang/String;ILjava/lang/String;J)Lnet/mamoe/mirai/message/data/FileMessage;
public static final synthetic fun Image (Ljava/lang/String;)Lnet/mamoe/mirai/message/data/Image;
public static final synthetic fun UnsupportedMessage ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public static final synthetic fun at (Lnet/mamoe/mirai/contact/Member;)Lnet/mamoe/mirai/message/data/At;
public static final fun buildMessageChain (ILkotlin/jvm/functions/Function1;)Lnet/mamoe/mirai/message/data/MessageChain;
public static final fun buildMessageChain (Lkotlin/jvm/functions/Function1;)Lnet/mamoe/mirai/message/data/MessageChain;
@ -5258,6 +5260,28 @@ public final class net/mamoe/mirai/message/data/SingleMessage$Serializer : kotli
public fun serialize (Lkotlinx/serialization/encoding/Encoder;Lnet/mamoe/mirai/message/data/SingleMessage;)V
}
public abstract interface class net/mamoe/mirai/message/data/UnsupportedMessage : net/mamoe/mirai/message/data/MessageContent {
public static final field Companion Lnet/mamoe/mirai/message/data/UnsupportedMessage$Companion;
public static final field SERIAL_NAME Ljava/lang/String;
public fun contentToString ()Ljava/lang/String;
public static fun create ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public abstract fun getStruct ()[B
}
public final class net/mamoe/mirai/message/data/UnsupportedMessage$Companion {
public static final field SERIAL_NAME Ljava/lang/String;
public final fun create ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
}
public final class net/mamoe/mirai/message/data/UnsupportedMessage$Serializer : kotlinx/serialization/KSerializer {
public static final field INSTANCE Lnet/mamoe/mirai/message/data/UnsupportedMessage$Serializer;
public synthetic fun deserialize (Lkotlinx/serialization/encoding/Decoder;)Ljava/lang/Object;
public fun deserialize (Lkotlinx/serialization/encoding/Decoder;)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public fun getDescriptor ()Lkotlinx/serialization/descriptors/SerialDescriptor;
public synthetic fun serialize (Lkotlinx/serialization/encoding/Encoder;Ljava/lang/Object;)V
public fun serialize (Lkotlinx/serialization/encoding/Encoder;Lnet/mamoe/mirai/message/data/UnsupportedMessage;)V
}
public final class net/mamoe/mirai/message/data/VipFace : net/mamoe/mirai/message/code/CodableMessage, net/mamoe/mirai/message/data/HummerMessage {
public static final field AiXin Lnet/mamoe/mirai/message/data/VipFace$Kind;
public static final field BianBian Lnet/mamoe/mirai/message/data/VipFace$Kind;

View File

@ -90,6 +90,7 @@ public abstract interface class net/mamoe/mirai/IMirai : net/mamoe/mirai/LowLeve
public abstract fun constructMessageSource (JLnet/mamoe/mirai/message/data/MessageSourceKind;JJ[II[ILnet/mamoe/mirai/message/data/MessageChain;)Lnet/mamoe/mirai/message/data/OfflineMessageSource;
public abstract fun createFileMessage (Ljava/lang/String;ILjava/lang/String;J)Lnet/mamoe/mirai/message/data/FileMessage;
public abstract fun createImage (Ljava/lang/String;)Lnet/mamoe/mirai/message/data/Image;
public abstract fun createUnsupportedMessage ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public fun downloadForwardMessage (Lnet/mamoe/mirai/Bot;Ljava/lang/String;)Ljava/util/List;
public abstract fun downloadForwardMessage (Lnet/mamoe/mirai/Bot;Ljava/lang/String;Lkotlin/coroutines/Continuation;)Ljava/lang/Object;
public fun downloadLongMessage (Lnet/mamoe/mirai/Bot;Ljava/lang/String;)Lnet/mamoe/mirai/message/data/MessageChain;
@ -4727,6 +4728,7 @@ public final class net/mamoe/mirai/message/data/MessageUtils {
public static final synthetic fun At (Lnet/mamoe/mirai/contact/UserOrBot;)Lnet/mamoe/mirai/message/data/At;
public static final synthetic fun FileMessage (Ljava/lang/String;ILjava/lang/String;J)Lnet/mamoe/mirai/message/data/FileMessage;
public static final synthetic fun Image (Ljava/lang/String;)Lnet/mamoe/mirai/message/data/Image;
public static final synthetic fun UnsupportedMessage ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public static final synthetic fun at (Lnet/mamoe/mirai/contact/Member;)Lnet/mamoe/mirai/message/data/At;
public static final fun buildMessageChain (ILkotlin/jvm/functions/Function1;)Lnet/mamoe/mirai/message/data/MessageChain;
public static final fun buildMessageChain (Lkotlin/jvm/functions/Function1;)Lnet/mamoe/mirai/message/data/MessageChain;
@ -5258,6 +5260,28 @@ public final class net/mamoe/mirai/message/data/SingleMessage$Serializer : kotli
public fun serialize (Lkotlinx/serialization/encoding/Encoder;Lnet/mamoe/mirai/message/data/SingleMessage;)V
}
public abstract interface class net/mamoe/mirai/message/data/UnsupportedMessage : net/mamoe/mirai/message/data/MessageContent {
public static final field Companion Lnet/mamoe/mirai/message/data/UnsupportedMessage$Companion;
public static final field SERIAL_NAME Ljava/lang/String;
public fun contentToString ()Ljava/lang/String;
public static fun create ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public abstract fun getStruct ()[B
}
public final class net/mamoe/mirai/message/data/UnsupportedMessage$Companion {
public static final field SERIAL_NAME Ljava/lang/String;
public final fun create ([B)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
}
public final class net/mamoe/mirai/message/data/UnsupportedMessage$Serializer : kotlinx/serialization/KSerializer {
public static final field INSTANCE Lnet/mamoe/mirai/message/data/UnsupportedMessage$Serializer;
public synthetic fun deserialize (Lkotlinx/serialization/encoding/Decoder;)Ljava/lang/Object;
public fun deserialize (Lkotlinx/serialization/encoding/Decoder;)Lnet/mamoe/mirai/message/data/UnsupportedMessage;
public fun getDescriptor ()Lkotlinx/serialization/descriptors/SerialDescriptor;
public synthetic fun serialize (Lkotlinx/serialization/encoding/Encoder;Ljava/lang/Object;)V
public fun serialize (Lkotlinx/serialization/encoding/Encoder;Lnet/mamoe/mirai/message/data/UnsupportedMessage;)V
}
public final class net/mamoe/mirai/message/data/VipFace : net/mamoe/mirai/message/code/CodableMessage, net/mamoe/mirai/message/data/HummerMessage {
public static final field AiXin Lnet/mamoe/mirai/message/data/VipFace$Kind;
public static final field BianBian Lnet/mamoe/mirai/message/data/VipFace$Kind;

View File

@ -145,6 +145,12 @@ public interface IMirai : LowLevelApiAccessor {
*/
public fun createFileMessage(id: String, internalId: Int, name: String, size: Long): FileMessage
/**
* 创建 [UnsupportedMessage]
* @since 2.6
*/
public fun createUnsupportedMessage(struct: ByteArray): UnsupportedMessage
/**
* 获取图片下载链接
*

View File

@ -130,6 +130,7 @@ private val builtInSerializersModule by lazy {
subclass(MusicShare::class, MusicShare.serializer())
subclass(Dice::class, Dice.serializer())
subclass(UnsupportedMessage::class, UnsupportedMessage.Serializer)
}

View File

@ -0,0 +1,74 @@
/*
* Copyright 2019-2021 Mamoe Technologies and contributors.
*
* 此源代码的使用受 GNU AFFERO GENERAL PUBLIC LICENSE version 3 许可证的约束, 可以在以下链接找到该许可证.
* Use of this source code is governed by the GNU AGPLv3 license that can be found through the following link.
*
* https://github.com/mamoe/mirai/blob/master/LICENSE
*/
@file:Suppress("NOTHING_TO_INLINE")
@file:JvmMultifileClass
@file:JvmName("MessageUtils")
package net.mamoe.mirai.message.data
import kotlinx.serialization.KSerializer
import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable
import net.mamoe.mirai.IMirai
import net.mamoe.mirai.Mirai
import net.mamoe.mirai.internal.message.map
import net.mamoe.mirai.utils.chunkedHexToBytes
import net.mamoe.mirai.utils.copy
import net.mamoe.mirai.utils.toUHexString
/**
* mirai 尚未支持的消息类型.
*
* [UnsupportedMessage] 可以发送, 接收, 或序列化保存
* @since 2.6
*/
@SerialName(UnsupportedMessage.SERIAL_NAME)
@Serializable(UnsupportedMessage.Serializer::class)
public interface UnsupportedMessage : MessageContent {
override fun contentToString(): String = "[不支持的消息#${struct.contentHashCode()}]" // to produce 'stable' and reliable text
/**
* 原生消息数据
*/
public val struct: ByteArray
public companion object {
public const val SERIAL_NAME: String = "UnsupportedMessage"
/**
* 创建 [UnsupportedMessage]
* @see IMirai.createUnsupportedMessage
*/
@JvmStatic
public fun create(struct: ByteArray): UnsupportedMessage = Mirai.createUnsupportedMessage(struct)
}
public object Serializer : KSerializer<UnsupportedMessage> by Surrogate.serializer().map(
resultantDescriptor = Surrogate.serializer().descriptor.copy(SERIAL_NAME),
deserialize = { Mirai.createUnsupportedMessage(struct.chunkedHexToBytes()) },
serialize = { Surrogate(struct.toUHexString("")) }
) {
@Suppress("RemoveRedundantQualifierName")
@Serializable
@SerialName(UnsupportedMessage.SERIAL_NAME)
private class Surrogate(
val struct: String // hex
)
}
}
/**
* 创建 [UnsupportedMessage]
* @since 2.6
* @see UnsupportedMessage.create
*/
@JvmSynthetic
public inline fun UnsupportedMessage(struct: ByteArray): UnsupportedMessage = UnsupportedMessage.create(struct)

View File

@ -30,6 +30,7 @@ import net.mamoe.mirai.internal.contact.info.MemberInfoImpl
import net.mamoe.mirai.internal.message.*
import net.mamoe.mirai.internal.network.highway.*
import net.mamoe.mirai.internal.network.protocol.data.jce.SvcDevLoginInfo
import net.mamoe.mirai.internal.network.protocol.data.proto.ImMsgBody
import net.mamoe.mirai.internal.network.protocol.data.proto.LongMsg
import net.mamoe.mirai.internal.network.protocol.data.proto.MsgTransmit
import net.mamoe.mirai.internal.network.protocol.packet.chat.*
@ -109,6 +110,10 @@ internal open class MiraiImpl : IMirai, LowLevelApiAccessor {
OfflineMessageSourceImplData::class,
OfflineMessageSourceImplData.serializer()
)
MessageSerializers.registerSerializer(
UnsupportedMessageImpl::class,
UnsupportedMessageImpl.serializer()
)
}
}
@ -903,6 +908,9 @@ internal open class MiraiImpl : IMirai, LowLevelApiAccessor {
return FileMessageImpl(id, internalId, name, size)
}
override fun createUnsupportedMessage(struct: ByteArray): UnsupportedMessage =
UnsupportedMessageImpl(struct.loadAs(ImMsgBody.Elem.serializer()))
@Suppress("DEPRECATION", "OverridingDeprecatedMember")
override suspend fun queryImageUrl(bot: Bot, image: Image): String = when (image) {
is ConstOriginUrlAware -> image.originUrl

View File

@ -154,6 +154,7 @@ private object ReceiveMessageTransformer {
// ignore
}
else -> {
builder.add(UnsupportedMessageImpl(element))
// println(it._miraiContentToString())
}
}

View File

@ -0,0 +1,53 @@
/*
* Copyright 2019-2021 Mamoe Technologies and contributors.
*
* 此源代码的使用受 GNU AFFERO GENERAL PUBLIC LICENSE version 3 许可证的约束, 可以在以下链接找到该许可证.
* Use of this source code is governed by the GNU AGPLv3 license that can be found through the following link.
*
* https://github.com/mamoe/mirai/blob/master/LICENSE
*/
package net.mamoe.mirai.internal.message
import kotlinx.serialization.KSerializer
import kotlinx.serialization.SerialName
import kotlinx.serialization.Serializable
import kotlinx.serialization.descriptors.SerialDescriptor
import kotlinx.serialization.encoding.Decoder
import kotlinx.serialization.encoding.Encoder
import net.mamoe.mirai.internal.network.protocol.data.proto.ImMsgBody
import net.mamoe.mirai.internal.utils.io.serialization.toByteArray
import net.mamoe.mirai.message.data.UnsupportedMessage
import net.mamoe.mirai.message.data.content
import net.mamoe.mirai.utils.copy
@SerialName(UnsupportedMessage.SERIAL_NAME)
@Serializable(UnsupportedMessageImpl.Serializer::class)
internal data class UnsupportedMessageImpl(
val structElem: ImMsgBody.Elem
) : UnsupportedMessage {
override val struct: ByteArray by lazy { structElem.toByteArray(ImMsgBody.Elem.serializer()) }
override fun toString(): String = content
override fun hashCode(): Int {
return struct.contentHashCode()
}
override fun equals(other: Any?): Boolean {
if (other === this) return true
if (other !is UnsupportedMessageImpl) return false
if (other.structElem == this.structElem) return true
return other.struct.contentEquals(this.struct)
}
object Serializer : KSerializer<UnsupportedMessageImpl> {
override val descriptor: SerialDescriptor =
UnsupportedMessage.Serializer.descriptor.copy(UnsupportedMessage.SERIAL_NAME)
override fun deserialize(decoder: Decoder): UnsupportedMessageImpl =
UnsupportedMessage.Serializer.deserialize(decoder) as UnsupportedMessageImpl
override fun serialize(encoder: Encoder, value: UnsupportedMessageImpl) =
UnsupportedMessage.Serializer.serialize(encoder, value)
}
}

View File

@ -239,6 +239,7 @@ internal fun MessageChain.toRichTextElems(
is InternalFlagOnlyMessage, is ShowImageFlag -> {
// ignore
}
is UnsupportedMessageImpl -> elements.add(currentMessage.structElem)
else -> {
// unrecognized types are ignored
// error("unsupported message type: ${currentMessage::class.simpleName}")

View File

@ -19,6 +19,7 @@ import kotlinx.serialization.serializer
import net.mamoe.mirai.Mirai
import net.mamoe.mirai.internal.message.FileMessageImpl
import net.mamoe.mirai.internal.message.MarketFaceImpl
import net.mamoe.mirai.internal.message.UnsupportedMessageImpl
import net.mamoe.mirai.internal.network.protocol.data.proto.ImMsgBody
import net.mamoe.mirai.message.MessageSerializers
import net.mamoe.mirai.message.data.*
@ -75,6 +76,7 @@ internal class MessageSerializationTest {
AtAll,
image,
Face(Face.AI_NI),
UnsupportedMessageImpl(ImMsgBody.Elem())
)
private val emptySource = Mirai.constructMessageSource(