mirror of
https://github.com/mamoe/mirai.git
synced 2025-01-27 17:00:14 +08:00
Update to Kotlin 1.3.70
This commit is contained in:
parent
e6cb229b18
commit
2e57e358c3
@ -71,7 +71,7 @@ If you meet any problem or have any questions, be free to open a issue. Our goal
|
|||||||
|
|
||||||
## Requirements
|
## Requirements
|
||||||
|
|
||||||
Kotlin 1.3.61
|
Kotlin 1.3.70
|
||||||
|
|
||||||
On JVM: Java 6
|
On JVM: Java 6
|
||||||
|
|
||||||
|
@ -11,7 +11,7 @@
|
|||||||
|
|
||||||
## 构建需求
|
## 构建需求
|
||||||
|
|
||||||
- Kotlin 1.3.61 (必须)
|
- Kotlin 1.3.70 (必须)
|
||||||
- JDK 6 或更高 (必须)
|
- JDK 6 或更高 (必须)
|
||||||
- Android SDK 29 (可选, 用于编译安卓目标)
|
- Android SDK 29 (可选, 用于编译安卓目标)
|
||||||
|
|
||||||
|
@ -5,7 +5,7 @@ miraiVersion=0.24.1
|
|||||||
kotlin.incremental.multiplatform=true
|
kotlin.incremental.multiplatform=true
|
||||||
kotlin.parallel.tasks.in.project=true
|
kotlin.parallel.tasks.in.project=true
|
||||||
# kotlin
|
# kotlin
|
||||||
kotlinVersion=1.3.61
|
kotlinVersion=1.3.70
|
||||||
# kotlin libraries
|
# kotlin libraries
|
||||||
serializationVersion=0.14.0
|
serializationVersion=0.14.0
|
||||||
coroutinesVersion=1.3.3
|
coroutinesVersion=1.3.3
|
||||||
|
@ -21,7 +21,7 @@ import net.mamoe.mirai.utils.MiraiInternalAPI
|
|||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
actual object QQAndroid : BotFactory {
|
actual object QQAndroid : BotFactory {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@JvmName("newBot")
|
@JvmName("newBot")
|
||||||
actual override fun Bot(context: Context, qq: Long, password: String, configuration: BotConfiguration): Bot {
|
actual override fun Bot(context: Context, qq: Long, password: String, configuration: BotConfiguration): Bot {
|
||||||
return QQAndroidBot(context, BotAccount(qq, password), configuration)
|
return QQAndroidBot(context, BotAccount(qq, password), configuration)
|
||||||
@ -30,7 +30,7 @@ actual object QQAndroid : BotFactory {
|
|||||||
/**
|
/**
|
||||||
* 使用指定的 [配置][configuration] 构造 [Bot] 实例
|
* 使用指定的 [配置][configuration] 构造 [Bot] 实例
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@JvmName("newBot")
|
@JvmName("newBot")
|
||||||
actual override fun Bot(
|
actual override fun Bot(
|
||||||
context: Context,
|
context: Context,
|
||||||
|
@ -14,7 +14,7 @@ import net.mamoe.mirai.utils.BotConfiguration
|
|||||||
import net.mamoe.mirai.utils.Context
|
import net.mamoe.mirai.utils.Context
|
||||||
import net.mamoe.mirai.utils.MiraiInternalAPI
|
import net.mamoe.mirai.utils.MiraiInternalAPI
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal actual class QQAndroidBot
|
internal actual class QQAndroidBot
|
||||||
actual constructor(
|
actual constructor(
|
||||||
context: Context,
|
context: Context,
|
||||||
|
@ -361,7 +361,7 @@ internal class MemberInfoImpl(
|
|||||||
* 中name/announcement的更改会直接向服务器异步汇报
|
* 中name/announcement的更改会直接向服务器异步汇报
|
||||||
*/
|
*/
|
||||||
@Suppress("PropertyName")
|
@Suppress("PropertyName")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal class GroupImpl(
|
internal class GroupImpl(
|
||||||
bot: QQAndroidBot, override val coroutineContext: CoroutineContext,
|
bot: QQAndroidBot, override val coroutineContext: CoroutineContext,
|
||||||
override val id: Long,
|
override val id: Long,
|
||||||
@ -373,7 +373,7 @@ internal class GroupImpl(
|
|||||||
|
|
||||||
override lateinit var owner: Member
|
override lateinit var owner: Member
|
||||||
|
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
override val botAsMember: Member by lazy {
|
override val botAsMember: Member by lazy {
|
||||||
Member(object : MemberInfo {
|
Member(object : MemberInfo {
|
||||||
override val nameCard: String
|
override val nameCard: String
|
||||||
@ -391,7 +391,7 @@ internal class GroupImpl(
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
override lateinit var botPermission: MemberPermission
|
override lateinit var botPermission: MemberPermission
|
||||||
|
|
||||||
var _botMuteTimestamp: Int = groupInfo.botMuteRemaining
|
var _botMuteTimestamp: Int = groupInfo.botMuteRemaining
|
||||||
@ -547,10 +547,10 @@ internal class GroupImpl(
|
|||||||
TODO("not implemented")
|
TODO("not implemented")
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
override fun Member(memberInfo: MemberInfo): Member {
|
override fun Member(memberInfo: MemberInfo): Member {
|
||||||
return MemberImpl(
|
return MemberImpl(
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
bot._lowLevelNewQQ(memberInfo) as QQImpl,
|
bot._lowLevelNewQQ(memberInfo) as QQImpl,
|
||||||
this,
|
this,
|
||||||
this.coroutineContext,
|
this.coroutineContext,
|
||||||
|
@ -36,14 +36,14 @@ import net.mamoe.mirai.utils.*
|
|||||||
import kotlin.collections.asSequence
|
import kotlin.collections.asSequence
|
||||||
import kotlin.coroutines.CoroutineContext
|
import kotlin.coroutines.CoroutineContext
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal expect class QQAndroidBot constructor(
|
internal expect class QQAndroidBot constructor(
|
||||||
context: Context,
|
context: Context,
|
||||||
account: BotAccount,
|
account: BotAccount,
|
||||||
configuration: BotConfiguration
|
configuration: BotConfiguration
|
||||||
) : QQAndroidBotBase
|
) : QQAndroidBotBase
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class, MiraiExperimentalAPI::class)
|
@OptIn(MiraiInternalAPI::class, MiraiExperimentalAPI::class)
|
||||||
internal abstract class QQAndroidBotBase constructor(
|
internal abstract class QQAndroidBotBase constructor(
|
||||||
context: Context,
|
context: Context,
|
||||||
account: BotAccount,
|
account: BotAccount,
|
||||||
@ -69,7 +69,7 @@ internal abstract class QQAndroidBotBase constructor(
|
|||||||
override val friends: ContactList<QQ> = ContactList(LockFreeLinkedList())
|
override val friends: ContactList<QQ> = ContactList(LockFreeLinkedList())
|
||||||
|
|
||||||
override val selfQQ: QQ by lazy {
|
override val selfQQ: QQ by lazy {
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
_lowLevelNewQQ(object : FriendInfo {
|
_lowLevelNewQQ(object : FriendInfo {
|
||||||
override val uin: Long get() = this@QQAndroidBotBase.uin
|
override val uin: Long get() = this@QQAndroidBotBase.uin
|
||||||
override val nick: String get() = this@QQAndroidBotBase.nick
|
override val nick: String get() = this@QQAndroidBotBase.nick
|
||||||
@ -101,7 +101,7 @@ internal abstract class QQAndroidBotBase constructor(
|
|||||||
return groups.delegate.getOrNull(uin)
|
return groups.delegate.getOrNull(uin)
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
override suspend fun _lowLevelQueryGroupList(): Sequence<Long> {
|
override suspend fun _lowLevelQueryGroupList(): Sequence<Long> {
|
||||||
return network.run {
|
return network.run {
|
||||||
FriendList.GetTroopListSimplify(bot.client)
|
FriendList.GetTroopListSimplify(bot.client)
|
||||||
@ -109,7 +109,7 @@ internal abstract class QQAndroidBotBase constructor(
|
|||||||
}.groups.asSequence().map { it.groupUin.shl(32) and it.groupCode }
|
}.groups.asSequence().map { it.groupUin.shl(32) and it.groupCode }
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
override suspend fun _lowLevelQueryGroupInfo(groupCode: Long): GroupInfo = network.run {
|
override suspend fun _lowLevelQueryGroupInfo(groupCode: Long): GroupInfo = network.run {
|
||||||
TroopManagement.GetGroupInfo(
|
TroopManagement.GetGroupInfo(
|
||||||
client = bot.client,
|
client = bot.client,
|
||||||
@ -117,7 +117,7 @@ internal abstract class QQAndroidBotBase constructor(
|
|||||||
).sendAndExpect<GroupInfoImpl>(retry = 2)
|
).sendAndExpect<GroupInfoImpl>(retry = 2)
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
override suspend fun _lowLevelQueryGroupMemberList(
|
override suspend fun _lowLevelQueryGroupMemberList(
|
||||||
groupUin: Long,
|
groupUin: Long,
|
||||||
groupCode: Long,
|
groupCode: Long,
|
||||||
@ -187,7 +187,7 @@ internal abstract class QQAndroidBotBase constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
override suspend fun _lowLevelRecallFriendMessage(friendId: Long, messageId: Long, time: Long) {
|
override suspend fun _lowLevelRecallFriendMessage(friendId: Long, messageId: Long, time: Long) {
|
||||||
network.run {
|
network.run {
|
||||||
val response: PbMessageSvc.PbMsgWithDraw.Response =
|
val response: PbMessageSvc.PbMsgWithDraw.Response =
|
||||||
@ -198,7 +198,7 @@ internal abstract class QQAndroidBotBase constructor(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
override suspend fun _lowLevelRecallGroupMessage(groupId: Long, messageId: Long) {
|
override suspend fun _lowLevelRecallGroupMessage(groupId: Long, messageId: Long) {
|
||||||
network.run {
|
network.run {
|
||||||
val response: PbMessageSvc.PbMsgWithDraw.Response =
|
val response: PbMessageSvc.PbMsgWithDraw.Response =
|
||||||
|
@ -81,7 +81,7 @@ class Jce private constructor(private val charset: JceCharset, context: SerialMo
|
|||||||
* From: com.qq.taf.jce.JceOutputStream
|
* From: com.qq.taf.jce.JceOutputStream
|
||||||
*/
|
*/
|
||||||
@Suppress("unused", "MemberVisibilityCanBePrivate")
|
@Suppress("unused", "MemberVisibilityCanBePrivate")
|
||||||
@UseExperimental(ExperimentalIoApi::class)
|
@OptIn(ExperimentalIoApi::class)
|
||||||
private open inner class JceEncoder(
|
private open inner class JceEncoder(
|
||||||
internal val output: BytePacketBuilder
|
internal val output: BytePacketBuilder
|
||||||
) : TaggedEncoder<Int>() {
|
) : TaggedEncoder<Int>() {
|
||||||
@ -102,7 +102,7 @@ class Jce private constructor(private val charset: JceCharset, context: SerialMo
|
|||||||
else -> throw SerializationException("Primitives are not supported at top-level")
|
else -> throw SerializationException("Primitives are not supported at top-level")
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ImplicitReflectionSerializer::class)
|
@OptIn(ImplicitReflectionSerializer::class)
|
||||||
@Suppress("UNCHECKED_CAST", "NAME_SHADOWING")
|
@Suppress("UNCHECKED_CAST", "NAME_SHADOWING")
|
||||||
override fun <T> encodeSerializableValue(serializer: SerializationStrategy<T>, value: T) = when (serializer.descriptor) {
|
override fun <T> encodeSerializableValue(serializer: SerializationStrategy<T>, value: T) = when (serializer.descriptor) {
|
||||||
is MapLikeDescriptor -> {
|
is MapLikeDescriptor -> {
|
||||||
@ -515,7 +515,7 @@ class Jce private constructor(private val charset: JceCharset, context: SerialMo
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
internal inner class JceInput(
|
internal inner class JceInput(
|
||||||
@PublishedApi
|
@PublishedApi
|
||||||
internal val input: ByteReadPacket,
|
internal val input: ByteReadPacket,
|
||||||
@ -667,7 +667,7 @@ class Jce private constructor(private val charset: JceCharset, context: SerialMo
|
|||||||
} while (head.type.toInt() != 11)
|
} while (head.type.toInt() != 11)
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
@PublishedApi
|
@PublishedApi
|
||||||
internal fun skipField(type: Byte) = when (type.toInt()) {
|
internal fun skipField(type: Byte) = when (type.toInt()) {
|
||||||
0 -> this.input.discardExact(1)
|
0 -> this.input.discardExact(1)
|
||||||
@ -794,7 +794,7 @@ internal inline fun <R> Jce.JceInput.skipToTagOrNull(tag: Int, block: (JceHead)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
inline class JceHead(private val value: Long) {
|
inline class JceHead(private val value: Long) {
|
||||||
constructor(tag: Int, type: Byte) : this(tag.toLong().shl(32) or type.toLong())
|
constructor(tag: Int, type: Byte) : this(tag.toLong().shl(32) or type.toLong())
|
||||||
|
|
||||||
|
@ -253,7 +253,7 @@ internal class MessageSourceFromSendFriend(
|
|||||||
val sequenceId: Int,
|
val sequenceId: Int,
|
||||||
override val originalMessage: MessageChain
|
override val originalMessage: MessageChain
|
||||||
) : MessageSourceFromSend() {
|
) : MessageSourceFromSend() {
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
override val id: Long
|
override val id: Long
|
||||||
get() = sequenceId.toLong().shl(32) or
|
get() = sequenceId.toLong().shl(32) or
|
||||||
messageRandom.toLong().and(0xFFFFFFFF)
|
messageRandom.toLong().and(0xFFFFFFFF)
|
||||||
@ -277,12 +277,12 @@ internal class MessageSourceFromSendGroup(
|
|||||||
) : MessageSourceFromSend() {
|
) : MessageSourceFromSend() {
|
||||||
private lateinit var sequenceIdDeferred: Deferred<Int>
|
private lateinit var sequenceIdDeferred: Deferred<Int>
|
||||||
|
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
override val id: Long
|
override val id: Long
|
||||||
get() = sequenceIdDeferred.getCompleted().toLong().shl(32) or
|
get() = sequenceIdDeferred.getCompleted().toLong().shl(32) or
|
||||||
messageRandom.toLong().and(0xFFFFFFFF)
|
messageRandom.toLong().and(0xFFFFFFFF)
|
||||||
|
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
internal fun startWaitingSequenceId(coroutineScope: CoroutineScope) {
|
internal fun startWaitingSequenceId(coroutineScope: CoroutineScope) {
|
||||||
sequenceIdDeferred =
|
sequenceIdDeferred =
|
||||||
coroutineScope.subscribingGetAsync<OnlinePush.PbPushGroupMsg.SendGroupMessageReceipt, Int>(
|
coroutineScope.subscribingGetAsync<OnlinePush.PbPushGroupMsg.SendGroupMessageReceipt, Int>(
|
||||||
|
@ -219,7 +219,7 @@ private val atAllData = ImMsgBody.Elem(
|
|||||||
)
|
)
|
||||||
)
|
)
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal fun MessageChain.toRichTextElems(forGroup: Boolean): MutableList<ImMsgBody.Elem> {
|
internal fun MessageChain.toRichTextElems(forGroup: Boolean): MutableList<ImMsgBody.Elem> {
|
||||||
val elements = mutableListOf<ImMsgBody.Elem>()
|
val elements = mutableListOf<ImMsgBody.Elem>()
|
||||||
|
|
||||||
@ -332,7 +332,7 @@ internal class OnlineFriendImageImpl(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
@OptIn(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
||||||
internal fun MsgComm.Msg.toMessageChain(): MessageChain {
|
internal fun MsgComm.Msg.toMessageChain(): MessageChain {
|
||||||
val elements = this.msgBody.richText.elems
|
val elements = this.msgBody.richText.elems
|
||||||
|
|
||||||
@ -343,7 +343,7 @@ internal fun MsgComm.Msg.toMessageChain(): MessageChain {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// These two functions are not identical, dont combine.
|
// These two functions are not identical, dont combine.
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
@OptIn(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
||||||
internal fun ImMsgBody.SourceMsg.toMessageChain(): MessageChain {
|
internal fun ImMsgBody.SourceMsg.toMessageChain(): MessageChain {
|
||||||
val elements = this.elems!!
|
val elements = this.elems!!
|
||||||
|
|
||||||
@ -368,7 +368,9 @@ private fun MessageChain.removeAtIfHasQuoteReply(): MessageChain =
|
|||||||
}.asMessageChain()
|
}.asMessageChain()
|
||||||
} else this*/
|
} else this*/
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class, ExperimentalUnsignedTypes::class, MiraiDebugAPI::class, LowLevelAPI::class)
|
@OptIn(
|
||||||
|
MiraiInternalAPI::class, ExperimentalUnsignedTypes::class, MiraiDebugAPI::class, LowLevelAPI::class
|
||||||
|
)
|
||||||
internal fun List<ImMsgBody.Elem>.joinToMessageChain(message: MessageChainBuilder) {
|
internal fun List<ImMsgBody.Elem>.joinToMessageChain(message: MessageChainBuilder) {
|
||||||
this.forEach {
|
this.forEach {
|
||||||
when {
|
when {
|
||||||
|
@ -45,7 +45,7 @@ import kotlin.jvm.Volatile
|
|||||||
import kotlin.time.ExperimentalTime
|
import kotlin.time.ExperimentalTime
|
||||||
|
|
||||||
@Suppress("MemberVisibilityCanBePrivate")
|
@Suppress("MemberVisibilityCanBePrivate")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal class QQAndroidBotNetworkHandler(bot: QQAndroidBot) : BotNetworkHandler() {
|
internal class QQAndroidBotNetworkHandler(bot: QQAndroidBot) : BotNetworkHandler() {
|
||||||
override val bot: QQAndroidBot by bot.unsafeWeakRef()
|
override val bot: QQAndroidBot by bot.unsafeWeakRef()
|
||||||
override val supervisor: CompletableJob = SupervisorJob(bot.coroutineContext[Job])
|
override val supervisor: CompletableJob = SupervisorJob(bot.coroutineContext[Job])
|
||||||
@ -183,7 +183,7 @@ internal class QQAndroidBotNetworkHandler(bot: QQAndroidBot) : BotNetworkHandler
|
|||||||
internal var pendingIncomingPackets: LockFreeLinkedList<KnownPacketFactories.IncomingPacket<*>>? =
|
internal var pendingIncomingPackets: LockFreeLinkedList<KnownPacketFactories.IncomingPacket<*>>? =
|
||||||
LockFreeLinkedList()
|
LockFreeLinkedList()
|
||||||
|
|
||||||
@UseExperimental(MiraiExperimentalAPI::class, ExperimentalTime::class)
|
@OptIn(MiraiExperimentalAPI::class, ExperimentalTime::class)
|
||||||
override suspend fun init(): Unit = coroutineScope {
|
override suspend fun init(): Unit = coroutineScope {
|
||||||
check(bot.isActive) { "bot is dead therefore network can't init" }
|
check(bot.isActive) { "bot is dead therefore network can't init" }
|
||||||
check(this@QQAndroidBotNetworkHandler.isActive) { "network is dead therefore can't init" }
|
check(this@QQAndroidBotNetworkHandler.isActive) { "network is dead therefore can't init" }
|
||||||
@ -372,7 +372,7 @@ internal class QQAndroidBotNetworkHandler(bot: QQAndroidBot) : BotNetworkHandler
|
|||||||
*
|
*
|
||||||
* @param input 一个完整的包的内容, 去掉开头的 int 包长度
|
* @param input 一个完整的包的内容, 去掉开头的 int 包长度
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
fun parsePacketAsync(input: Input): Job {
|
fun parsePacketAsync(input: Input): Job {
|
||||||
return this.launch(start = CoroutineStart.ATOMIC) {
|
return this.launch(start = CoroutineStart.ATOMIC) {
|
||||||
input.use { parsePacket(it) }
|
input.use { parsePacket(it) }
|
||||||
|
@ -40,7 +40,7 @@ import net.mamoe.mirai.utils.io.*
|
|||||||
DOMAINS
|
DOMAINS
|
||||||
Pskey: "openmobile.qq.com"
|
Pskey: "openmobile.qq.com"
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiExperimentalAPI::class, MiraiInternalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class, MiraiInternalAPI::class)
|
||||||
@PublishedApi
|
@PublishedApi
|
||||||
internal open class QQAndroidClient(
|
internal open class QQAndroidClient(
|
||||||
context: Context,
|
context: Context,
|
||||||
@ -158,7 +158,7 @@ internal open class QQAndroidClient(
|
|||||||
*/
|
*/
|
||||||
val uin: Long get() = _uin
|
val uin: Long get() = _uin
|
||||||
|
|
||||||
@UseExperimental(RawAccountIdUse::class)
|
@OptIn(RawAccountIdUse::class)
|
||||||
@Suppress("PropertyName")
|
@Suppress("PropertyName")
|
||||||
internal var _uin: Long = bot.account.id
|
internal var _uin: Long = bot.account.id
|
||||||
|
|
||||||
|
@ -34,7 +34,7 @@ import net.mamoe.mirai.utils.io.ByteArrayPool
|
|||||||
import net.mamoe.mirai.utils.io.PlatformSocket
|
import net.mamoe.mirai.utils.io.PlatformSocket
|
||||||
import net.mamoe.mirai.utils.io.withUse
|
import net.mamoe.mirai.utils.io.withUse
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@Suppress("SpellCheckingInspection")
|
@Suppress("SpellCheckingInspection")
|
||||||
internal suspend fun HttpClient.postImage(
|
internal suspend fun HttpClient.postImage(
|
||||||
htcmd: String,
|
htcmd: String,
|
||||||
@ -92,9 +92,9 @@ internal suspend fun HttpClient.postImage(
|
|||||||
}
|
}
|
||||||
} == HttpStatusCode.OK
|
} == HttpStatusCode.OK
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal object HighwayHelper {
|
internal object HighwayHelper {
|
||||||
@UseExperimental(InternalCoroutinesApi::class)
|
@OptIn(InternalCoroutinesApi::class)
|
||||||
suspend fun uploadImage(
|
suspend fun uploadImage(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
serverIp: String,
|
serverIp: String,
|
||||||
|
@ -23,7 +23,7 @@ import net.mamoe.mirai.qqandroid.network.protocol.packet.EMPTY_BYTE_ARRAY
|
|||||||
import net.mamoe.mirai.utils.MiraiInternalAPI
|
import net.mamoe.mirai.utils.MiraiInternalAPI
|
||||||
import net.mamoe.mirai.utils.io.*
|
import net.mamoe.mirai.utils.io.*
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal fun createImageDataPacketSequence( // RequestDataTrans
|
internal fun createImageDataPacketSequence( // RequestDataTrans
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
command: String,
|
command: String,
|
||||||
|
@ -16,7 +16,7 @@ import net.mamoe.mirai.utils.cryptor.ECDHKeyPair
|
|||||||
import net.mamoe.mirai.utils.io.encryptAndWrite
|
import net.mamoe.mirai.utils.io.encryptAndWrite
|
||||||
import net.mamoe.mirai.utils.io.writeShortLVByteArray
|
import net.mamoe.mirai.utils.io.writeShortLVByteArray
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
internal interface EncryptMethod {
|
internal interface EncryptMethod {
|
||||||
val id: Int
|
val id: Int
|
||||||
|
|
||||||
|
@ -35,7 +35,7 @@ internal val EMPTY_BYTE_ARRAY = ByteArray(0)
|
|||||||
* com.tencent.qphone.base.util.CodecWarpper#encodeRequest(int, java.lang.String, java.lang.String, java.lang.String, java.lang.String, java.lang.String, byte[], int, int, java.lang.String, byte, byte, byte, byte[], byte[], boolean)
|
* com.tencent.qphone.base.util.CodecWarpper#encodeRequest(int, java.lang.String, java.lang.String, java.lang.String, java.lang.String, java.lang.String, byte[], int, int, java.lang.String, byte, byte, byte, byte[], byte[], boolean)
|
||||||
*/
|
*/
|
||||||
@Deprecated("危险", level = DeprecationLevel.ERROR)
|
@Deprecated("危险", level = DeprecationLevel.ERROR)
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal inline fun OutgoingPacketFactory<*>.buildOutgoingPacket(
|
internal inline fun OutgoingPacketFactory<*>.buildOutgoingPacket(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
bodyType: Byte = 1, // 1: PB?
|
bodyType: Byte = 1, // 1: PB?
|
||||||
@ -63,7 +63,7 @@ internal inline fun OutgoingPacketFactory<*>.buildOutgoingPacket(
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal inline fun OutgoingPacketFactory<*>.buildOutgoingUniPacket(
|
internal inline fun OutgoingPacketFactory<*>.buildOutgoingUniPacket(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
bodyType: Byte = 1, // 1: PB?
|
bodyType: Byte = 1, // 1: PB?
|
||||||
@ -96,7 +96,7 @@ internal inline fun OutgoingPacketFactory<*>.buildOutgoingUniPacket(
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal inline fun IncomingPacketFactory<*>.buildResponseUniPacket(
|
internal inline fun IncomingPacketFactory<*>.buildResponseUniPacket(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
bodyType: Byte = 1, // 1: PB?
|
bodyType: Byte = 1, // 1: PB?
|
||||||
@ -127,7 +127,7 @@ internal inline fun IncomingPacketFactory<*>.buildResponseUniPacket(
|
|||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal inline fun BytePacketBuilder.writeUniPacket(
|
internal inline fun BytePacketBuilder.writeUniPacket(
|
||||||
commandName: String,
|
commandName: String,
|
||||||
unknownData: ByteArray,
|
unknownData: ByteArray,
|
||||||
@ -160,7 +160,7 @@ internal val NO_ENCRYPT: ByteArray = ByteArray(0)
|
|||||||
/**
|
/**
|
||||||
* com.tencent.qphone.base.util.CodecWarpper#encodeRequest(int, java.lang.String, java.lang.String, java.lang.String, java.lang.String, java.lang.String, byte[], int, int, java.lang.String, byte, byte, byte, byte[], byte[], boolean)
|
* com.tencent.qphone.base.util.CodecWarpper#encodeRequest(int, java.lang.String, java.lang.String, java.lang.String, java.lang.String, java.lang.String, byte[], int, int, java.lang.String, byte, byte, byte, byte[], byte[], boolean)
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal inline fun OutgoingPacketFactory<*>.buildLoginOutgoingPacket(
|
internal inline fun OutgoingPacketFactory<*>.buildLoginOutgoingPacket(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
bodyType: Byte,
|
bodyType: Byte,
|
||||||
@ -198,7 +198,7 @@ internal inline fun OutgoingPacketFactory<*>.buildLoginOutgoingPacket(
|
|||||||
|
|
||||||
private inline val BRP_STUB get() = ByteReadPacket.Empty
|
private inline val BRP_STUB get() = ByteReadPacket.Empty
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal inline fun BytePacketBuilder.writeSsoPacket(
|
internal inline fun BytePacketBuilder.writeSsoPacket(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
subAppId: Long,
|
subAppId: Long,
|
||||||
@ -264,7 +264,7 @@ internal inline fun BytePacketBuilder.writeSsoPacket(
|
|||||||
writeIntLVPacket(lengthOffset = { it + 4 }, builder = body)
|
writeIntLVPacket(lengthOffset = { it + 4 }, builder = body)
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
@OptIn(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
||||||
internal fun BytePacketBuilder.writeOicqRequestPacket(
|
internal fun BytePacketBuilder.writeOicqRequestPacket(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
encryptMethod: EncryptMethod,
|
encryptMethod: EncryptMethod,
|
||||||
|
@ -48,7 +48,7 @@ internal sealed class PacketFactory<TPacket : Packet?> {
|
|||||||
*
|
*
|
||||||
* @param TPacket 服务器回复包解析结果
|
* @param TPacket 服务器回复包解析结果
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
internal abstract class OutgoingPacketFactory<TPacket : Packet?>(
|
internal abstract class OutgoingPacketFactory<TPacket : Packet?>(
|
||||||
/**
|
/**
|
||||||
* 命令名. 如 `wtlogin.login`, `ConfigPushSvc.PushDomain`
|
* 命令名. 如 `wtlogin.login`, `ConfigPushSvc.PushDomain`
|
||||||
@ -117,7 +117,7 @@ internal val PacketLogger: MiraiLoggerWithSwitch = DefaultLogger("Packet").withS
|
|||||||
/**
|
/**
|
||||||
* 已知的数据包工厂列表.
|
* 已知的数据包工厂列表.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
internal object KnownPacketFactories {
|
internal object KnownPacketFactories {
|
||||||
object OutgoingFactories : List<OutgoingPacketFactory<*>> by mutableListOf(
|
object OutgoingFactories : List<OutgoingPacketFactory<*>> by mutableListOf(
|
||||||
WtLogin.Login,
|
WtLogin.Login,
|
||||||
@ -164,7 +164,7 @@ internal object KnownPacketFactories {
|
|||||||
* full packet without length
|
* full packet without length
|
||||||
*/
|
*/
|
||||||
// do not inline. Exceptions thrown will not be reported correctly
|
// do not inline. Exceptions thrown will not be reported correctly
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@Suppress("UNCHECKED_CAST")
|
@Suppress("UNCHECKED_CAST")
|
||||||
suspend fun <T : Packet?> parseIncomingPacket(bot: QQAndroidBot, rawInput: Input, consumer: PacketConsumer<T>) = with(rawInput) {
|
suspend fun <T : Packet?> parseIncomingPacket(bot: QQAndroidBot, rawInput: Input, consumer: PacketConsumer<T>) = with(rawInput) {
|
||||||
// login
|
// login
|
||||||
@ -226,7 +226,7 @@ internal object KnownPacketFactories {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal suspend fun <T : Packet?> handleIncomingPacket(it: IncomingPacket<T>, bot: QQAndroidBot, flag2: Int, consumer: PacketConsumer<T>) {
|
internal suspend fun <T : Packet?> handleIncomingPacket(it: IncomingPacket<T>, bot: QQAndroidBot, flag2: Int, consumer: PacketConsumer<T>) {
|
||||||
if (it.packetFactory == null) {
|
if (it.packetFactory == null) {
|
||||||
bot.network.logger.debug("Received commandName: ${it.commandName}")
|
bot.network.logger.debug("Received commandName: ${it.commandName}")
|
||||||
@ -275,7 +275,7 @@ internal object KnownPacketFactories {
|
|||||||
/**
|
/**
|
||||||
* 解析 SSO 层包装
|
* 解析 SSO 层包装
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
@OptIn(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
||||||
private fun parseSsoFrame(bot: QQAndroidBot, input: ByteReadPacket): IncomingPacket<*> {
|
private fun parseSsoFrame(bot: QQAndroidBot, input: ByteReadPacket): IncomingPacket<*> {
|
||||||
val commandName: String
|
val commandName: String
|
||||||
val ssoSequenceId: Int
|
val ssoSequenceId: Int
|
||||||
@ -336,7 +336,7 @@ internal object KnownPacketFactories {
|
|||||||
return IncomingPacket(packetFactory, ssoSequenceId, packet, commandName)
|
return IncomingPacket(packetFactory, ssoSequenceId, packet, commandName)
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
private suspend fun <T : Packet?> ByteReadPacket.parseOicqResponse(
|
private suspend fun <T : Packet?> ByteReadPacket.parseOicqResponse(
|
||||||
bot: QQAndroidBot,
|
bot: QQAndroidBot,
|
||||||
packetFactory: OutgoingPacketFactory<T>,
|
packetFactory: OutgoingPacketFactory<T>,
|
||||||
|
@ -71,7 +71,7 @@ internal class MessageSvc {
|
|||||||
/**
|
/**
|
||||||
* 获取好友消息和消息记录
|
* 获取好友消息和消息记录
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal object PbGetMsg : OutgoingPacketFactory<PbGetMsg.Response>("MessageSvc.PbGetMsg") {
|
internal object PbGetMsg : OutgoingPacketFactory<PbGetMsg.Response>("MessageSvc.PbGetMsg") {
|
||||||
operator fun invoke(
|
operator fun invoke(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
@ -102,7 +102,7 @@ internal class MessageSvc {
|
|||||||
)
|
)
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
open class GetMsgSuccess(delegate: List<Packet>) : Response(MsgSvc.SyncFlag.STOP, delegate) {
|
open class GetMsgSuccess(delegate: List<Packet>) : Response(MsgSvc.SyncFlag.STOP, delegate) {
|
||||||
override fun toString(): String = "MessageSvc.PbGetMsg.GetMsgSuccess(messages=<Iterable>))"
|
override fun toString(): String = "MessageSvc.PbGetMsg.GetMsgSuccess(messages=<Iterable>))"
|
||||||
}
|
}
|
||||||
@ -119,7 +119,7 @@ internal class MessageSvc {
|
|||||||
|
|
||||||
object EmptyResponse : GetMsgSuccess(emptyList())
|
object EmptyResponse : GetMsgSuccess(emptyList())
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class, MiraiExperimentalAPI::class)
|
@OptIn(MiraiInternalAPI::class, MiraiExperimentalAPI::class)
|
||||||
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot): Response {
|
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot): Response {
|
||||||
// 00 00 01 0F 08 00 12 00 1A 34 08 FF C1 C4 F1 05 10 FF C1 C4 F1 05 18 E6 ED B9 C3 02 20 89 FE BE A4 06 28 8A CA 91 D1 0C 48 9B A5 BD 9B 0A 58 DE 9D 99 F8 08 60 1D 68 FF C1 C4 F1 05 70 00 20 02 2A 9D 01 08 F3 C1 C4 F1 05 10 A2 FF 8C F0 03 18 01 22 8A 01 0A 2A 08 A2 FF 8C F0 03 10 DD F1 92 B7 07 18 A6 01 20 0B 28 AE F9 01 30 F4 C1 C4 F1 05 38 A7 E3 D8 D4 84 80 80 80 01 B8 01 CD B5 01 12 08 08 01 10 00 18 00 20 00 1A 52 0A 50 0A 27 08 00 10 F4 C1 C4 F1 05 18 A7 E3 D8 D4 04 20 00 28 0C 30 00 38 86 01 40 22 4A 0C E5 BE AE E8 BD AF E9 9B 85 E9 BB 91 12 08 0A 06 0A 04 4E 4D 53 4C 12 15 AA 02 12 9A 01 0F 80 01 01 C8 01 00 F0 01 00 F8 01 00 90 02 00 12 04 4A 02 08 00 30 01 2A 15 08 97 A2 C1 F1 05 10 95 A6 F5 E5 0C 18 01 30 01 40 01 48 81 01 2A 10 08 D3 F7 B5 F1 05 10 DD F1 92 B7 07 18 01 30 01 38 00 42 00 48 00
|
// 00 00 01 0F 08 00 12 00 1A 34 08 FF C1 C4 F1 05 10 FF C1 C4 F1 05 18 E6 ED B9 C3 02 20 89 FE BE A4 06 28 8A CA 91 D1 0C 48 9B A5 BD 9B 0A 58 DE 9D 99 F8 08 60 1D 68 FF C1 C4 F1 05 70 00 20 02 2A 9D 01 08 F3 C1 C4 F1 05 10 A2 FF 8C F0 03 18 01 22 8A 01 0A 2A 08 A2 FF 8C F0 03 10 DD F1 92 B7 07 18 A6 01 20 0B 28 AE F9 01 30 F4 C1 C4 F1 05 38 A7 E3 D8 D4 84 80 80 80 01 B8 01 CD B5 01 12 08 08 01 10 00 18 00 20 00 1A 52 0A 50 0A 27 08 00 10 F4 C1 C4 F1 05 18 A7 E3 D8 D4 04 20 00 28 0C 30 00 38 86 01 40 22 4A 0C E5 BE AE E8 BD AF E9 9B 85 E9 BB 91 12 08 0A 06 0A 04 4E 4D 53 4C 12 15 AA 02 12 9A 01 0F 80 01 01 C8 01 00 F0 01 00 F8 01 00 90 02 00 12 04 4A 02 08 00 30 01 2A 15 08 97 A2 C1 F1 05 10 95 A6 F5 E5 0C 18 01 30 01 40 01 48 81 01 2A 10 08 D3 F7 B5 F1 05 10 DD F1 92 B7 07 18 01 30 01 38 00 42 00 48 00
|
||||||
val resp = readProtoBuf(MsgSvc.PbGetMsgResp.serializer())
|
val resp = readProtoBuf(MsgSvc.PbGetMsgResp.serializer())
|
||||||
@ -275,6 +275,7 @@ internal class MessageSvc {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Suppress("FunctionName")
|
||||||
inline fun ToFriend(
|
inline fun ToFriend(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
toUin: Long,
|
toUin: Long,
|
||||||
@ -325,6 +326,7 @@ internal class MessageSvc {
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@Suppress("FunctionName")
|
||||||
inline fun ToGroup(
|
inline fun ToGroup(
|
||||||
client: QQAndroidClient,
|
client: QQAndroidClient,
|
||||||
groupCode: Long,
|
groupCode: Long,
|
||||||
|
@ -54,7 +54,7 @@ internal class OnlinePush {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalStdlibApi::class)
|
@OptIn(ExperimentalStdlibApi::class)
|
||||||
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot, sequenceId: Int): Packet? {
|
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot, sequenceId: Int): Packet? {
|
||||||
// 00 00 02 E4 0A D5 05 0A 4F 08 A2 FF 8C F0 03 10 DD F1 92 B7 07 18 52 20 00 28 BC 3D 30 8C 82 AB F1 05 38 D2 80 E0 8C 80 80 80 80 02 4A 21 08 E7 C1 AD B8 02 10 01 18 BA 05 22 09 48 69 6D 31 38 38 6D 6F 65 30 06 38 02 42 05 4D 69 72 61 69 50 01 58 01 60 00 88 01 08 12 06 08 01 10 00 18 00 1A F9 04 0A F6 04 0A 26 08 00 10 87 82 AB F1 05 18 B7 B4 BF 30 20 00 28 0C 30 00 38 86 01 40 22 4A 0C E5 BE AE E8 BD AF E9 9B 85 E9 BB 91 12 E6 03 42 E3 03 12 2A 7B 34 45 31 38 35 38 32 32 2D 30 45 37 42 2D 46 38 30 46 2D 43 35 42 31 2D 33 34 34 38 38 33 37 34 44 33 39 43 7D 2E 6A 70 67 22 00 2A 04 03 00 00 00 32 60 15 36 20 39 36 6B 45 31 41 38 35 32 32 39 64 63 36 39 38 34 37 39 37 37 62 20 20 20 20 20 20 35 30 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 7B 34 45 31 38 35 38 32 32 2D 30 45 37 42 2D 46 38 30 46 2D 43 35 42 31 2D 33 34 34 38 38 33 37 34 44 33 39 43 7D 2E 6A 70 67 31 32 31 32 41 38 C6 BB 8A A9 08 40 FB AE 9E C2 09 48 50 50 41 5A 00 60 01 6A 10 4E 18 58 22 0E 7B F8 0F C5 B1 34 48 83 74 D3 9C 72 59 2F 67 63 68 61 74 70 69 63 5F 6E 65 77 2F 31 30 34 30 34 30 30 32 39 30 2F 36 35 35 30 35 37 31 32 37 2D 32 32 33 33 36 33 38 33 34 32 2D 34 45 31 38 35 38 32 32 30 45 37 42 46 38 30 46 43 35 42 31 33 34 34 38 38 33 37 34 44 33 39 43 2F 31 39 38 3F 74 65 72 6D 3D 32 82 01 57 2F 67 63 68 61 74 70 69 63 5F 6E 65 77 2F 31 30 34 30 34 30 30 32 39 30 2F 36 35 35 30 35 37 31 32 37 2D 32 32 33 33 36 33 38 33 34 32 2D 34 45 31 38 35 38 32 32 30 45 37 42 46 38 30 46 43 35 42 31 33 34 34 38 38 33 37 34 44 33 39 43 2F 30 3F 74 65 72 6D 3D 32 B0 01 4D B8 01 2E C8 01 FF 05 D8 01 4D E0 01 2E FA 01 59 2F 67 63 68 61 74 70 69 63 5F 6E 65 77 2F 31 30 34 30 34 30 30 32 39 30 2F 36 35 35 30 35 37 31 32 37 2D 32 32 33 33 36 33 38 33 34 32 2D 34 45 31 38 35 38 32 32 30 45 37 42 46 38 30 46 43 35 42 31 33 34 34 38 38 33 37 34 44 33 39 43 2F 34 30 30 3F 74 65 72 6D 3D 32 80 02 4D 88 02 2E 12 45 AA 02 42 50 03 60 00 68 00 9A 01 39 08 09 20 BF 50 80 01 01 C8 01 00 F0 01 00 F8 01 00 90 02 00 98 03 00 A0 03 20 B0 03 00 C0 03 00 D0 03 00 E8 03 00 8A 04 04 08 02 08 01 90 04 80 80 80 10 B8 04 00 C0 04 00 12 06 4A 04 08 00 40 01 12 14 82 01 11 0A 09 48 69 6D 31 38 38 6D 6F 65 18 06 20 08 28 03 10 8A CA 9D A1 07 1A 00
|
// 00 00 02 E4 0A D5 05 0A 4F 08 A2 FF 8C F0 03 10 DD F1 92 B7 07 18 52 20 00 28 BC 3D 30 8C 82 AB F1 05 38 D2 80 E0 8C 80 80 80 80 02 4A 21 08 E7 C1 AD B8 02 10 01 18 BA 05 22 09 48 69 6D 31 38 38 6D 6F 65 30 06 38 02 42 05 4D 69 72 61 69 50 01 58 01 60 00 88 01 08 12 06 08 01 10 00 18 00 1A F9 04 0A F6 04 0A 26 08 00 10 87 82 AB F1 05 18 B7 B4 BF 30 20 00 28 0C 30 00 38 86 01 40 22 4A 0C E5 BE AE E8 BD AF E9 9B 85 E9 BB 91 12 E6 03 42 E3 03 12 2A 7B 34 45 31 38 35 38 32 32 2D 30 45 37 42 2D 46 38 30 46 2D 43 35 42 31 2D 33 34 34 38 38 33 37 34 44 33 39 43 7D 2E 6A 70 67 22 00 2A 04 03 00 00 00 32 60 15 36 20 39 36 6B 45 31 41 38 35 32 32 39 64 63 36 39 38 34 37 39 37 37 62 20 20 20 20 20 20 35 30 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 20 7B 34 45 31 38 35 38 32 32 2D 30 45 37 42 2D 46 38 30 46 2D 43 35 42 31 2D 33 34 34 38 38 33 37 34 44 33 39 43 7D 2E 6A 70 67 31 32 31 32 41 38 C6 BB 8A A9 08 40 FB AE 9E C2 09 48 50 50 41 5A 00 60 01 6A 10 4E 18 58 22 0E 7B F8 0F C5 B1 34 48 83 74 D3 9C 72 59 2F 67 63 68 61 74 70 69 63 5F 6E 65 77 2F 31 30 34 30 34 30 30 32 39 30 2F 36 35 35 30 35 37 31 32 37 2D 32 32 33 33 36 33 38 33 34 32 2D 34 45 31 38 35 38 32 32 30 45 37 42 46 38 30 46 43 35 42 31 33 34 34 38 38 33 37 34 44 33 39 43 2F 31 39 38 3F 74 65 72 6D 3D 32 82 01 57 2F 67 63 68 61 74 70 69 63 5F 6E 65 77 2F 31 30 34 30 34 30 30 32 39 30 2F 36 35 35 30 35 37 31 32 37 2D 32 32 33 33 36 33 38 33 34 32 2D 34 45 31 38 35 38 32 32 30 45 37 42 46 38 30 46 43 35 42 31 33 34 34 38 38 33 37 34 44 33 39 43 2F 30 3F 74 65 72 6D 3D 32 B0 01 4D B8 01 2E C8 01 FF 05 D8 01 4D E0 01 2E FA 01 59 2F 67 63 68 61 74 70 69 63 5F 6E 65 77 2F 31 30 34 30 34 30 30 32 39 30 2F 36 35 35 30 35 37 31 32 37 2D 32 32 33 33 36 33 38 33 34 32 2D 34 45 31 38 35 38 32 32 30 45 37 42 46 38 30 46 43 35 42 31 33 34 34 38 38 33 37 34 44 33 39 43 2F 34 30 30 3F 74 65 72 6D 3D 32 80 02 4D 88 02 2E 12 45 AA 02 42 50 03 60 00 68 00 9A 01 39 08 09 20 BF 50 80 01 01 C8 01 00 F0 01 00 F8 01 00 90 02 00 98 03 00 A0 03 20 B0 03 00 C0 03 00 D0 03 00 E8 03 00 8A 04 04 08 02 08 01 90 04 80 80 80 10 B8 04 00 C0 04 00 12 06 4A 04 08 00 40 01 12 14 82 01 11 0A 09 48 69 6D 31 38 38 6D 6F 65 18 06 20 08 28 03 10 8A CA 9D A1 07 1A 00
|
||||||
if (!bot.firstLoginSucceed) return null
|
if (!bot.firstLoginSucceed) return null
|
||||||
@ -93,7 +93,7 @@ internal class OnlinePush {
|
|||||||
|
|
||||||
internal object PbPushTransMsg : IncomingPacketFactory<Packet>("OnlinePush.PbPushTransMsg", "OnlinePush.RespPush") {
|
internal object PbPushTransMsg : IncomingPacketFactory<Packet>("OnlinePush.PbPushTransMsg", "OnlinePush.RespPush") {
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@ExperimentalUnsignedTypes
|
@ExperimentalUnsignedTypes
|
||||||
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot, sequenceId: Int): Packet {
|
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot, sequenceId: Int): Packet {
|
||||||
val content = this.readProtoBuf(OnlinePushTrans.PbMsgInfo.serializer())
|
val content = this.readProtoBuf(OnlinePushTrans.PbMsgInfo.serializer())
|
||||||
@ -184,7 +184,7 @@ internal class OnlinePush {
|
|||||||
//0C 01 B1 89 BE 09 5E 3D 72 A6 00 01 73 68 FC 06 00 00 00 3C
|
//0C 01 B1 89 BE 09 5E 3D 72 A6 00 01 73 68 FC 06 00 00 00 3C
|
||||||
internal object ReqPush : IncomingPacketFactory<Packet>("OnlinePush.ReqPush", "OnlinePush.RespPush") {
|
internal object ReqPush : IncomingPacketFactory<Packet>("OnlinePush.ReqPush", "OnlinePush.RespPush") {
|
||||||
@ExperimentalUnsignedTypes
|
@ExperimentalUnsignedTypes
|
||||||
@UseExperimental(ExperimentalStdlibApi::class)
|
@OptIn(ExperimentalStdlibApi::class)
|
||||||
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot, sequenceId: Int): Packet {
|
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot, sequenceId: Int): Packet {
|
||||||
val reqPushMsg = decodeUniPacket(OnlinePushPack.SvcReqPushMsg.serializer(), "req")
|
val reqPushMsg = decodeUniPacket(OnlinePushPack.SvcReqPushMsg.serializer(), "req")
|
||||||
|
|
||||||
|
@ -29,7 +29,7 @@ internal class WtLogin {
|
|||||||
* OicqRequest
|
* OicqRequest
|
||||||
*/
|
*/
|
||||||
@Suppress("FunctionName")
|
@Suppress("FunctionName")
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
@OptIn(ExperimentalUnsignedTypes::class, MiraiInternalAPI::class)
|
||||||
internal object Login : OutgoingPacketFactory<Login.LoginPacketResponse>("wtlogin.login") {
|
internal object Login : OutgoingPacketFactory<Login.LoginPacketResponse>("wtlogin.login") {
|
||||||
private const val subAppId = 537062845L
|
private const val subAppId = 537062845L
|
||||||
|
|
||||||
@ -121,7 +121,7 @@ internal class WtLogin {
|
|||||||
private const val appId = 16L
|
private const val appId = 16L
|
||||||
private const val subAppId = 537062845L
|
private const val subAppId = 537062845L
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
operator fun invoke(
|
operator fun invoke(
|
||||||
client: QQAndroidClient
|
client: QQAndroidClient
|
||||||
): OutgoingPacket = buildLoginOutgoingPacket(client, bodyType = 2) { sequenceId ->
|
): OutgoingPacket = buildLoginOutgoingPacket(client, bodyType = 2) { sequenceId ->
|
||||||
@ -303,7 +303,7 @@ internal class WtLogin {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@InternalAPI
|
@InternalAPI
|
||||||
@UseExperimental(MiraiDebugAPI::class)
|
@OptIn(MiraiDebugAPI::class)
|
||||||
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot): LoginPacketResponse {
|
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot): LoginPacketResponse {
|
||||||
|
|
||||||
discardExact(2) // subCommand
|
discardExact(2) // subCommand
|
||||||
@ -352,7 +352,7 @@ internal class WtLogin {
|
|||||||
}
|
}
|
||||||
|
|
||||||
@InternalAPI
|
@InternalAPI
|
||||||
@UseExperimental(MiraiDebugAPI::class)
|
@OptIn(MiraiDebugAPI::class)
|
||||||
private fun onSolveLoginCaptcha(tlvMap: TlvMap, bot: QQAndroidBot): LoginPacketResponse.Captcha {
|
private fun onSolveLoginCaptcha(tlvMap: TlvMap, bot: QQAndroidBot): LoginPacketResponse.Captcha {
|
||||||
/*
|
/*
|
||||||
java.lang.IllegalStateException: UNKNOWN CAPTCHA QUESTION:
|
java.lang.IllegalStateException: UNKNOWN CAPTCHA QUESTION:
|
||||||
@ -388,7 +388,7 @@ internal class WtLogin {
|
|||||||
error("UNKNOWN CAPTCHA, tlvMap=" + tlvMap._miraiContentToString())
|
error("UNKNOWN CAPTCHA, tlvMap=" + tlvMap._miraiContentToString())
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiDebugAPI::class)
|
@OptIn(MiraiDebugAPI::class)
|
||||||
private fun onLoginSuccess(tlvMap: TlvMap, bot: QQAndroidBot): LoginPacketResponse.Success {
|
private fun onLoginSuccess(tlvMap: TlvMap, bot: QQAndroidBot): LoginPacketResponse.Success {
|
||||||
val client = bot.client
|
val client = bot.client
|
||||||
//println("TLV KEYS: " + tlvMap.keys.joinToString { it.contentToString() })
|
//println("TLV KEYS: " + tlvMap.keys.joinToString { it.contentToString() })
|
||||||
|
@ -21,7 +21,7 @@ import kotlin.jvm.JvmName
|
|||||||
/**
|
/**
|
||||||
* Inline the block
|
* Inline the block
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
@PublishedApi
|
@PublishedApi
|
||||||
internal inline fun <R> inline(block: () -> R): R {
|
internal inline fun <R> inline(block: () -> R): R {
|
||||||
contract {
|
contract {
|
||||||
|
@ -35,7 +35,7 @@ inline fun ByteArray.debugPrintThis(name: String): ByteArray {
|
|||||||
return this
|
return this
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalContracts::class, MiraiInternalAPI::class)
|
@OptIn(ExperimentalContracts::class, MiraiInternalAPI::class)
|
||||||
inline fun <R> Input.debugIfFail(name: String = "", onFail: (ByteArray) -> ByteReadPacket = { it.toReadPacket() }, block: ByteReadPacket.() -> R): R {
|
inline fun <R> Input.debugIfFail(name: String = "", onFail: (ByteArray) -> ByteReadPacket = { it.toReadPacket() }, block: ByteReadPacket.() -> R): R {
|
||||||
|
|
||||||
contract {
|
contract {
|
||||||
|
@ -23,7 +23,7 @@ import net.mamoe.mirai.utils.MiraiInternalAPI
|
|||||||
* QQ for Android
|
* QQ for Android
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual object QQAndroid : BotFactory {
|
actual object QQAndroid : BotFactory {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -15,11 +15,11 @@ import net.mamoe.mirai.utils.Context
|
|||||||
import net.mamoe.mirai.utils.ContextImpl
|
import net.mamoe.mirai.utils.ContextImpl
|
||||||
import net.mamoe.mirai.utils.MiraiInternalAPI
|
import net.mamoe.mirai.utils.MiraiInternalAPI
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@Suppress("FunctionName")
|
@Suppress("FunctionName")
|
||||||
internal fun QQAndroidBot(account: BotAccount, configuration: BotConfiguration): QQAndroidBot = QQAndroidBot(ContextImpl(), account, configuration)
|
internal fun QQAndroidBot(account: BotAccount, configuration: BotConfiguration): QQAndroidBot = QQAndroidBot(ContextImpl(), account, configuration)
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
internal actual class QQAndroidBot actual constructor(
|
internal actual class QQAndroidBot actual constructor(
|
||||||
context: Context,
|
context: Context,
|
||||||
account: BotAccount,
|
account: BotAccount,
|
||||||
|
@ -161,7 +161,7 @@ data class PBFieldInfo(
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
fun String.generateProtoBufDataClass(): GeneratedClass {
|
fun String.generateProtoBufDataClass(): GeneratedClass {
|
||||||
if (this.indexOf("extends") == -1) {
|
if (this.indexOf("extends") == -1) {
|
||||||
val javaClassname = substringBetween("class", "{")
|
val javaClassname = substringBetween("class", "{")
|
||||||
@ -367,7 +367,7 @@ fun String.getNumericalValue(): Int? {
|
|||||||
return this.filter { it in '0'..'9' }.toDoubleOrNull()?.toInt()
|
return this.filter { it in '0'..'9' }.toDoubleOrNull()?.toInt()
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiDebugAPI::class)
|
@OptIn(MiraiDebugAPI::class)
|
||||||
fun ProtoType.mapToKotlinType(): String {
|
fun ProtoType.mapToKotlinType(): String {
|
||||||
return when (this) {
|
return when (this) {
|
||||||
ProtoType.VAR_INT -> "Int"
|
ProtoType.VAR_INT -> "Int"
|
||||||
|
@ -24,7 +24,9 @@ import net.mamoe.mirai.utils.*
|
|||||||
* @see kotlinx.coroutines.isActive 判断 [Bot] 是否正常运行中. (在线, 且没有被 [close])
|
* @see kotlinx.coroutines.isActive 判断 [Bot] 是否正常运行中. (在线, 且没有被 [close])
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, LowLevelAPI::class, MiraiExperimentalAPI::class, JavaHappyAPI::class)
|
@OptIn(
|
||||||
|
MiraiInternalAPI::class, LowLevelAPI::class, MiraiExperimentalAPI::class, JavaHappyAPI::class
|
||||||
|
)
|
||||||
actual abstract class Bot actual constructor() : CoroutineScope, LowLevelBotAPIAccessor, BotJavaHappyAPI() {
|
actual abstract class Bot actual constructor() : CoroutineScope, LowLevelBotAPIAccessor, BotJavaHappyAPI() {
|
||||||
actual companion object {
|
actual companion object {
|
||||||
/**
|
/**
|
||||||
@ -234,6 +236,6 @@ actual abstract class Bot actual constructor() : CoroutineScope, LowLevelBotAPIA
|
|||||||
*/
|
*/
|
||||||
actual abstract fun close(cause: Throwable?)
|
actual abstract fun close(cause: Throwable?)
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class, MiraiExperimentalAPI::class)
|
@OptIn(LowLevelAPI::class, MiraiExperimentalAPI::class)
|
||||||
actual final override fun toString(): String = "Bot(${uin})"
|
actual final override fun toString(): String = "Bot(${uin})"
|
||||||
}
|
}
|
@ -132,7 +132,7 @@ actual abstract class BotJavaHappyAPI actual constructor() {
|
|||||||
message: String? = null,
|
message: String? = null,
|
||||||
remark: String? = null
|
remark: String? = null
|
||||||
): AddFriendResult {
|
): AddFriendResult {
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
return runBlocking { addFriend(id, message, remark) }
|
return runBlocking { addFriend(id, message, remark) }
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -170,7 +170,7 @@ actual abstract class BotJavaHappyAPI actual constructor() {
|
|||||||
}
|
}
|
||||||
|
|
||||||
// !! 不要 crossinline, 会编译失败
|
// !! 不要 crossinline, 会编译失败
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
internal fun <R, C : CoroutineScope> C.future(block: suspend C.() -> R): Future<R> {
|
internal fun <R, C : CoroutineScope> C.future(block: suspend C.() -> R): Future<R> {
|
||||||
val future = object : Future<R> {
|
val future = object : Future<R> {
|
||||||
val value: CompletableDeferred<R> = CompletableDeferred()
|
val value: CompletableDeferred<R> = CompletableDeferred()
|
||||||
@ -215,7 +215,7 @@ internal fun <R, C : CoroutineScope> C.future(block: suspend C.() -> R): Future<
|
|||||||
}
|
}
|
||||||
|
|
||||||
launch {
|
launch {
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
future.value.completeWith(kotlin.runCatching { block() })
|
future.value.completeWith(kotlin.runCatching { block() })
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -33,7 +33,7 @@ import net.mamoe.mirai.utils.WeakRefProperty
|
|||||||
* @author Him188moe
|
* @author Him188moe
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, JavaHappyAPI::class)
|
@OptIn(MiraiInternalAPI::class, JavaHappyAPI::class)
|
||||||
actual abstract class Contact : CoroutineScope, ContactJavaHappyAPI() {
|
actual abstract class Contact : CoroutineScope, ContactJavaHappyAPI() {
|
||||||
/**
|
/**
|
||||||
* 这个联系人所属 [Bot].
|
* 这个联系人所属 [Bot].
|
||||||
|
@ -21,7 +21,7 @@ import net.mamoe.mirai.utils.WeakRefProperty
|
|||||||
* 群成员.
|
* 群成员.
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, JavaHappyAPI::class)
|
@OptIn(MiraiInternalAPI::class, JavaHappyAPI::class)
|
||||||
actual abstract class Member : MemberJavaHappyAPI() {
|
actual abstract class Member : MemberJavaHappyAPI() {
|
||||||
/**
|
/**
|
||||||
* 所在的群.
|
* 所在的群.
|
||||||
|
@ -16,7 +16,7 @@ import net.mamoe.mirai.utils.MiraiInternalAPI
|
|||||||
/**
|
/**
|
||||||
* 平台相关扩展
|
* 平台相关扩展
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual abstract class MessagePacket<TSender : QQ, TSubject : Contact> actual constructor() : MessagePacketBase<TSender, TSubject>() {
|
actual abstract class MessagePacket<TSender : QQ, TSubject : Contact> actual constructor() : MessagePacketBase<TSender, TSubject>() {
|
||||||
// suspend inline fun uploadImage(image: Bitmap): Image = subject.uploadImage(image)
|
// suspend inline fun uploadImage(image: Bitmap): Image = subject.uploadImage(image)
|
||||||
//suspend inline fun uploadImage(image: URL): Image = subject.uploadImage(image)
|
//suspend inline fun uploadImage(image: URL): Image = subject.uploadImage(image)
|
||||||
|
@ -28,7 +28,7 @@ import net.mamoe.mirai.utils.unsafeWeakRef
|
|||||||
* @see MessageReceipt.sourceTime 源时间
|
* @see MessageReceipt.sourceTime 源时间
|
||||||
*/
|
*/
|
||||||
@Suppress("FunctionName")
|
@Suppress("FunctionName")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual open class MessageReceipt<C : Contact> actual constructor(
|
actual open class MessageReceipt<C : Contact> actual constructor(
|
||||||
actual val source: MessageSource,
|
actual val source: MessageSource,
|
||||||
target: C,
|
target: C,
|
||||||
@ -94,7 +94,7 @@ actual open class MessageReceipt<C : Contact> actual constructor(
|
|||||||
*/
|
*/
|
||||||
actual open suspend fun quote(): QuoteReplyToSend {
|
actual open suspend fun quote(): QuoteReplyToSend {
|
||||||
this.source.ensureSequenceIdAvailable()
|
this.source.ensureSequenceIdAvailable()
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
return _unsafeQuote()
|
return _unsafeQuote()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -23,7 +23,7 @@ import java.io.File
|
|||||||
/**
|
/**
|
||||||
* 加载一个设备信息. 若文件不存在或为空则随机并创建一个设备信息保存.
|
* 加载一个设备信息. 若文件不存在或为空则随机并创建一个设备信息保存.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(UnstableDefault::class)
|
@OptIn(UnstableDefault::class)
|
||||||
fun File.loadAsDeviceInfo(context: Context): DeviceInfo {
|
fun File.loadAsDeviceInfo(context: Context): DeviceInfo {
|
||||||
if (!this.exists() || this.length() == 0L) {
|
if (!this.exists() || this.length() == 0L) {
|
||||||
return SystemDeviceInfo(context).also {
|
return SystemDeviceInfo(context).also {
|
||||||
|
@ -80,7 +80,7 @@ actual class PlatformSocket : Closeable {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalIoApi::class)
|
@OptIn(ExperimentalIoApi::class)
|
||||||
actual suspend fun connect(serverHost: String, serverPort: Int) {
|
actual suspend fun connect(serverHost: String, serverPort: Int) {
|
||||||
withContext(Dispatchers.IO) {
|
withContext(Dispatchers.IO) {
|
||||||
socket = Socket(serverHost, serverPort)
|
socket = Socket(serverHost, serverPort)
|
||||||
|
@ -26,7 +26,7 @@ import java.util.zip.Inflater
|
|||||||
/**
|
/**
|
||||||
* Ktor HttpClient. 不同平台使用不同引擎.
|
* Ktor HttpClient. 不同平台使用不同引擎.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(KtorExperimentalAPI::class)
|
@OptIn(KtorExperimentalAPI::class)
|
||||||
actual val Http: HttpClient
|
actual val Http: HttpClient
|
||||||
get() = HttpClient(CIO)
|
get() = HttpClient(CIO)
|
||||||
|
|
||||||
@ -76,7 +76,7 @@ private inline fun InputStream.readInSequence(block: (Int) -> Unit) {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual fun ByteArray.unzip(offset: Int, length: Int): ByteArray {
|
actual fun ByteArray.unzip(offset: Int, length: Int): ByteArray {
|
||||||
this.checkOffsetAndLength(offset, length)
|
this.checkOffsetAndLength(offset, length)
|
||||||
if (length == 0) return ByteArray(0)
|
if (length == 0) return ByteArray(0)
|
||||||
|
@ -41,7 +41,7 @@ import kotlin.jvm.JvmSynthetic
|
|||||||
* @see kotlinx.coroutines.isActive 判断 [Bot] 是否正常运行中. (在线, 且没有被 [close])
|
* @see kotlinx.coroutines.isActive 判断 [Bot] 是否正常运行中. (在线, 且没有被 [close])
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, LowLevelAPI::class)
|
@OptIn(MiraiInternalAPI::class, LowLevelAPI::class)
|
||||||
expect abstract class Bot() : CoroutineScope, LowLevelBotAPIAccessor {
|
expect abstract class Bot() : CoroutineScope, LowLevelBotAPIAccessor {
|
||||||
companion object {
|
companion object {
|
||||||
/**
|
/**
|
||||||
@ -241,7 +241,7 @@ expect abstract class Bot() : CoroutineScope, LowLevelBotAPIAccessor {
|
|||||||
*/
|
*/
|
||||||
abstract fun close(cause: Throwable? = null)
|
abstract fun close(cause: Throwable? = null)
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class, MiraiExperimentalAPI::class)
|
@OptIn(LowLevelAPI::class, MiraiExperimentalAPI::class)
|
||||||
final override fun toString(): String
|
final override fun toString(): String
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -52,5 +52,5 @@ data class BotAccount(
|
|||||||
@MiraiInternalAPI
|
@MiraiInternalAPI
|
||||||
@Retention(AnnotationRetention.SOURCE)
|
@Retention(AnnotationRetention.SOURCE)
|
||||||
@Target(CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR)
|
@Target(CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR)
|
||||||
@Experimental(level = Experimental.Level.WARNING)
|
@RequiresOptIn(level = RequiresOptIn.Level.WARNING)
|
||||||
annotation class RawAccountIdUse
|
annotation class RawAccountIdUse
|
@ -27,7 +27,7 @@ import kotlin.coroutines.CoroutineContext
|
|||||||
/*
|
/*
|
||||||
* 泛型 N 不需要向外(接口)暴露.
|
* 泛型 N 不需要向外(接口)暴露.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
@MiraiInternalAPI
|
@MiraiInternalAPI
|
||||||
abstract class BotImpl<N : BotNetworkHandler> constructor(
|
abstract class BotImpl<N : BotNetworkHandler> constructor(
|
||||||
context: Context,
|
context: Context,
|
||||||
@ -42,7 +42,8 @@ abstract class BotImpl<N : BotNetworkHandler> constructor(
|
|||||||
|
|
||||||
@Suppress("CanBePrimaryConstructorProperty") // for logger
|
@Suppress("CanBePrimaryConstructorProperty") // for logger
|
||||||
final override val account: BotAccount = account
|
final override val account: BotAccount = account
|
||||||
@UseExperimental(RawAccountIdUse::class)
|
|
||||||
|
@OptIn(RawAccountIdUse::class)
|
||||||
override val uin: Long
|
override val uin: Long
|
||||||
get() = account.id
|
get() = account.id
|
||||||
final override val logger: MiraiLogger by lazy { configuration.botLoggerSupplier(this) }
|
final override val logger: MiraiLogger by lazy { configuration.botLoggerSupplier(this) }
|
||||||
@ -171,7 +172,7 @@ abstract class BotImpl<N : BotNetworkHandler> constructor(
|
|||||||
|
|
||||||
// endregion
|
// endregion
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
override fun close(cause: Throwable?) {
|
override fun close(cause: Throwable?) {
|
||||||
if (!this.botJob.isActive) {
|
if (!this.botJob.isActive) {
|
||||||
// already cancelled
|
// already cancelled
|
||||||
|
@ -36,7 +36,7 @@ import kotlin.jvm.JvmSynthetic
|
|||||||
*
|
*
|
||||||
* @author Him188moe
|
* @author Him188moe
|
||||||
*/ // 不要删除多平台结构 !!! kotlin bug
|
*/ // 不要删除多平台结构 !!! kotlin bug
|
||||||
@UseExperimental(MiraiInternalAPI::class, JavaHappyAPI::class)
|
@OptIn(MiraiInternalAPI::class, JavaHappyAPI::class)
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
expect abstract class Contact() : CoroutineScope, ContactJavaHappyAPI {
|
expect abstract class Contact() : CoroutineScope, ContactJavaHappyAPI {
|
||||||
/**
|
/**
|
||||||
|
@ -19,7 +19,7 @@ import net.mamoe.mirai.utils.*
|
|||||||
*
|
*
|
||||||
* @see ContactList.asSequence
|
* @see ContactList.asSequence
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
@Suppress("unused")
|
@Suppress("unused")
|
||||||
class ContactList<C : Contact>(@MiraiInternalAPI val delegate: LockFreeLinkedList<C>) {
|
class ContactList<C : Contact>(@MiraiInternalAPI val delegate: LockFreeLinkedList<C>) {
|
||||||
/**
|
/**
|
||||||
@ -79,7 +79,7 @@ fun <E : Contact> ContactList<E>.toList(): List<E> = toMutableList()
|
|||||||
/**
|
/**
|
||||||
* Collect all the elements into a [MutableList].
|
* Collect all the elements into a [MutableList].
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun <E : Contact> ContactList<E>.toMutableList(): MutableList<E> = this.delegate.toMutableList()
|
fun <E : Contact> ContactList<E>.toMutableList(): MutableList<E> = this.delegate.toMutableList()
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -90,7 +90,7 @@ fun <E : Contact> ContactList<E>.toSet(): Set<E> = toMutableSet()
|
|||||||
/**
|
/**
|
||||||
* Collect all the elements into a [MutableSet].
|
* Collect all the elements into a [MutableSet].
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun <E : Contact> ContactList<E>.toMutableSet(): MutableSet<E> = this.delegate.toMutableSet()
|
fun <E : Contact> ContactList<E>.toMutableSet(): MutableSet<E> = this.delegate.toMutableSet()
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@ -98,7 +98,7 @@ fun <E : Contact> ContactList<E>.toMutableSet(): MutableSet<E> = this.delegate.t
|
|||||||
*
|
*
|
||||||
* Note that the sequence is dynamic, that is, elements are yielded atomically only when it is required
|
* Note that the sequence is dynamic, that is, elements are yielded atomically only when it is required
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun <E : Contact> ContactList<E>.asSequence(): Sequence<E> {
|
fun <E : Contact> ContactList<E>.asSequence(): Sequence<E> {
|
||||||
return this.delegate.asSequence()
|
return this.delegate.asSequence()
|
||||||
}
|
}
|
@ -25,7 +25,7 @@ import kotlin.time.ExperimentalTime
|
|||||||
* 群成员.
|
* 群成员.
|
||||||
*/ // 不要删除多平台结构, kotlin bug
|
*/ // 不要删除多平台结构, kotlin bug
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, JavaHappyAPI::class)
|
@OptIn(MiraiInternalAPI::class, JavaHappyAPI::class)
|
||||||
expect abstract class Member() : MemberJavaHappyAPI {
|
expect abstract class Member() : MemberJavaHappyAPI {
|
||||||
/**
|
/**
|
||||||
* 所在的群.
|
* 所在的群.
|
||||||
|
@ -82,7 +82,7 @@ expect class PermissionDeniedException : IllegalStateException {
|
|||||||
*
|
*
|
||||||
* @throws PermissionDeniedException
|
* @throws PermissionDeniedException
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
inline fun Group.checkBotPermission(
|
inline fun Group.checkBotPermission(
|
||||||
required: MemberPermission,
|
required: MemberPermission,
|
||||||
lazyMessage: () -> String = {
|
lazyMessage: () -> String = {
|
||||||
@ -99,7 +99,7 @@ inline fun Group.checkBotPermission(
|
|||||||
*
|
*
|
||||||
* @throws PermissionDeniedException
|
* @throws PermissionDeniedException
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
inline fun Group.checkBotPermissionOperator(
|
inline fun Group.checkBotPermissionOperator(
|
||||||
lazyMessage: () -> String = {
|
lazyMessage: () -> String = {
|
||||||
"Permission denied: required ${MemberPermission.ADMINISTRATOR} or ${MemberPermission.OWNER}, got actual $botPermission for $bot in group $id"
|
"Permission denied: required ${MemberPermission.ADMINISTRATOR} or ${MemberPermission.OWNER}, got actual $botPermission for $bot in group $id"
|
||||||
|
@ -66,7 +66,7 @@ abstract class AbstractCancellableEvent : Event, CancellableEvent {
|
|||||||
/**
|
/**
|
||||||
* 广播一个事件的唯一途径.
|
* 广播一个事件的唯一途径.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
suspend fun <E : Event> E.broadcast(): E = apply {
|
suspend fun <E : Event> E.broadcast(): E = apply {
|
||||||
if (this is BroadcastControllable && !this.shouldBroadcast) {
|
if (this is BroadcastControllable && !this.shouldBroadcast) {
|
||||||
return@apply
|
return@apply
|
||||||
|
@ -143,7 +143,7 @@ sealed class MessageRecallEvent : BotEvent {
|
|||||||
) : MessageRecallEvent(), GroupOperableEvent, Packet
|
) : MessageRecallEvent(), GroupOperableEvent, Packet
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
val MessageRecallEvent.GroupRecall.author: Member
|
val MessageRecallEvent.GroupRecall.author: Member
|
||||||
get() = if (authorId == bot.uin) group.botAsMember else group[authorId]
|
get() = if (authorId == bot.uin) group.botAsMember else group[authorId]
|
||||||
|
|
||||||
|
@ -73,7 +73,7 @@ val GroupOperableEvent.isByBot: Boolean get() = operator == null
|
|||||||
* 当操作人为 [Member] 时获取这个 [Member],
|
* 当操作人为 [Member] 时获取这个 [Member],
|
||||||
* 当操作人为 [Bot] 时获取 [Group.botAsMember]
|
* 当操作人为 [Bot] 时获取 [Group.botAsMember]
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
val GroupOperableEvent.operatorOrBot: Member
|
val GroupOperableEvent.operatorOrBot: Member
|
||||||
get() = this.operator ?: this.group.botAsMember
|
get() = this.operator ?: this.group.botAsMember
|
||||||
|
|
||||||
|
@ -36,7 +36,7 @@ internal fun <E : Event> CoroutineScope.Handler(
|
|||||||
coroutineContext: CoroutineContext,
|
coroutineContext: CoroutineContext,
|
||||||
handler: suspend (E) -> ListeningStatus
|
handler: suspend (E) -> ListeningStatus
|
||||||
): Handler<E> {
|
): Handler<E> {
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class) // don't remove
|
@OptIn(ExperimentalCoroutinesApi::class) // don't remove
|
||||||
val context = this.newCoroutineContext(coroutineContext)
|
val context = this.newCoroutineContext(coroutineContext)
|
||||||
return Handler(context[Job], context, handler)
|
return Handler(context[Job], context, handler)
|
||||||
}
|
}
|
||||||
@ -50,7 +50,7 @@ internal class Handler<in E : Event>
|
|||||||
@PublishedApi internal constructor(parentJob: Job?, private val subscriberContext: CoroutineContext, @JvmField val handler: suspend (E) -> ListeningStatus) :
|
@PublishedApi internal constructor(parentJob: Job?, private val subscriberContext: CoroutineContext, @JvmField val handler: suspend (E) -> ListeningStatus) :
|
||||||
Listener<E>, CompletableJob by Job(parentJob) {
|
Listener<E>, CompletableJob by Job(parentJob) {
|
||||||
|
|
||||||
@UseExperimental(MiraiDebugAPI::class)
|
@OptIn(MiraiDebugAPI::class)
|
||||||
override suspend fun onEvent(event: E): ListeningStatus {
|
override suspend fun onEvent(event: E): ListeningStatus {
|
||||||
if (isCompleted || isCancelled) return ListeningStatus.STOPPED
|
if (isCompleted || isCancelled) return ListeningStatus.STOPPED
|
||||||
if (!isActive) return ListeningStatus.LISTENING
|
if (!isActive) return ListeningStatus.LISTENING
|
||||||
@ -155,7 +155,7 @@ internal suspend inline fun Event.broadcastInternal() = coroutineScope {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
private fun <E : Event> CoroutineScope.callAndRemoveIfRequired(event: E, listeners: EventListeners<E>) {
|
private fun <E : Event> CoroutineScope.callAndRemoveIfRequired(event: E, listeners: EventListeners<E>) {
|
||||||
// atomic foreach
|
// atomic foreach
|
||||||
listeners.forEachNode { node ->
|
listeners.forEachNode { node ->
|
||||||
|
@ -33,7 +33,7 @@ import kotlin.coroutines.EmptyCoroutineContext
|
|||||||
*
|
*
|
||||||
* @see CoroutineScope.incoming
|
* @see CoroutineScope.incoming
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> CoroutineScope.subscribeMessages(
|
inline fun <R> CoroutineScope.subscribeMessages(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
crossinline listeners: MessageSubscribersBuilder<MessagePacket<*, *>>.() -> R
|
crossinline listeners: MessageSubscribersBuilder<MessagePacket<*, *>>.() -> R
|
||||||
@ -58,7 +58,7 @@ inline fun <R> CoroutineScope.subscribeMessages(
|
|||||||
*
|
*
|
||||||
* @see CoroutineScope.incoming
|
* @see CoroutineScope.incoming
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> CoroutineScope.subscribeGroupMessages(
|
inline fun <R> CoroutineScope.subscribeGroupMessages(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
crossinline listeners: MessageSubscribersBuilder<GroupMessage>.() -> R
|
crossinline listeners: MessageSubscribersBuilder<GroupMessage>.() -> R
|
||||||
@ -78,7 +78,7 @@ inline fun <R> CoroutineScope.subscribeGroupMessages(
|
|||||||
*
|
*
|
||||||
* @see CoroutineScope.incoming
|
* @see CoroutineScope.incoming
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> CoroutineScope.subscribeFriendMessages(
|
inline fun <R> CoroutineScope.subscribeFriendMessages(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
crossinline listeners: MessageSubscribersBuilder<FriendMessage>.() -> R
|
crossinline listeners: MessageSubscribersBuilder<FriendMessage>.() -> R
|
||||||
@ -98,7 +98,7 @@ inline fun <R> CoroutineScope.subscribeFriendMessages(
|
|||||||
*
|
*
|
||||||
* @see CoroutineScope.incoming
|
* @see CoroutineScope.incoming
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> Bot.subscribeMessages(
|
inline fun <R> Bot.subscribeMessages(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
crossinline listeners: MessageSubscribersBuilder<MessagePacket<*, *>>.() -> R
|
crossinline listeners: MessageSubscribersBuilder<MessagePacket<*, *>>.() -> R
|
||||||
@ -120,7 +120,7 @@ inline fun <R> Bot.subscribeMessages(
|
|||||||
*
|
*
|
||||||
* @see CoroutineScope.incoming
|
* @see CoroutineScope.incoming
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> Bot.subscribeGroupMessages(
|
inline fun <R> Bot.subscribeGroupMessages(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
crossinline listeners: MessageSubscribersBuilder<GroupMessage>.() -> R
|
crossinline listeners: MessageSubscribersBuilder<GroupMessage>.() -> R
|
||||||
@ -140,7 +140,7 @@ inline fun <R> Bot.subscribeGroupMessages(
|
|||||||
*
|
*
|
||||||
* @see CoroutineScope.incoming
|
* @see CoroutineScope.incoming
|
||||||
*/
|
*/
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> Bot.subscribeFriendMessages(
|
inline fun <R> Bot.subscribeFriendMessages(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
crossinline listeners: MessageSubscribersBuilder<FriendMessage>.() -> R
|
crossinline listeners: MessageSubscribersBuilder<FriendMessage>.() -> R
|
||||||
|
@ -118,7 +118,7 @@ interface Listener<in E : Event> : CompletableJob {
|
|||||||
* @see subscribeGroupMessages 监听群消息 DSL
|
* @see subscribeGroupMessages 监听群消息 DSL
|
||||||
* @see subscribeFriendMessages 监听好友消息 DSL
|
* @see subscribeFriendMessages 监听好友消息 DSL
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
inline fun <reified E : Event> CoroutineScope.subscribe(
|
inline fun <reified E : Event> CoroutineScope.subscribe(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
noinline handler: suspend E.(E) -> ListeningStatus
|
noinline handler: suspend E.(E) -> ListeningStatus
|
||||||
@ -136,7 +136,7 @@ inline fun <reified E : Event> CoroutineScope.subscribe(
|
|||||||
*
|
*
|
||||||
* @see subscribe 获取更多说明
|
* @see subscribe 获取更多说明
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class, ExperimentalContracts::class)
|
@OptIn(MiraiInternalAPI::class, ExperimentalContracts::class)
|
||||||
inline fun <reified E : Event> CoroutineScope.subscribeAlways(
|
inline fun <reified E : Event> CoroutineScope.subscribeAlways(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
noinline listener: suspend E.(E) -> Unit
|
noinline listener: suspend E.(E) -> Unit
|
||||||
@ -158,7 +158,7 @@ inline fun <reified E : Event> CoroutineScope.subscribeAlways(
|
|||||||
*
|
*
|
||||||
* @see subscribe 获取更多说明
|
* @see subscribe 获取更多说明
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
inline fun <reified E : Event> CoroutineScope.subscribeOnce(
|
inline fun <reified E : Event> CoroutineScope.subscribeOnce(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
noinline listener: suspend E.(E) -> Unit
|
noinline listener: suspend E.(E) -> Unit
|
||||||
@ -184,7 +184,7 @@ inline fun <reified E : Event> CoroutineScope.subscribeOnce(
|
|||||||
* @see subscribe 获取更多说明
|
* @see subscribe 获取更多说明
|
||||||
*/
|
*/
|
||||||
@JvmName("subscribeAlwaysForBot")
|
@JvmName("subscribeAlwaysForBot")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
inline fun <reified E : BotEvent> Bot.subscribe(
|
inline fun <reified E : BotEvent> Bot.subscribe(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
noinline handler: suspend E.(E) -> ListeningStatus
|
noinline handler: suspend E.(E) -> ListeningStatus
|
||||||
@ -204,7 +204,7 @@ inline fun <reified E : BotEvent> Bot.subscribe(
|
|||||||
* @see subscribe 获取更多说明
|
* @see subscribe 获取更多说明
|
||||||
*/
|
*/
|
||||||
@JvmName("subscribeAlwaysForBot1")
|
@JvmName("subscribeAlwaysForBot1")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
inline fun <reified E : BotEvent> Bot.subscribeAlways(
|
inline fun <reified E : BotEvent> Bot.subscribeAlways(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
noinline listener: suspend E.(E) -> Unit
|
noinline listener: suspend E.(E) -> Unit
|
||||||
@ -224,7 +224,7 @@ inline fun <reified E : BotEvent> Bot.subscribeAlways(
|
|||||||
* @see subscribe 获取更多说明
|
* @see subscribe 获取更多说明
|
||||||
*/
|
*/
|
||||||
@JvmName("subscribeOnceForBot2")
|
@JvmName("subscribeOnceForBot2")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
inline fun <reified E : BotEvent> Bot.subscribeOnce(
|
inline fun <reified E : BotEvent> Bot.subscribeOnce(
|
||||||
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
coroutineContext: CoroutineContext = EmptyCoroutineContext,
|
||||||
noinline listener: suspend E.(E) -> Unit
|
noinline listener: suspend E.(E) -> Unit
|
||||||
|
@ -15,7 +15,7 @@ import net.mamoe.mirai.utils.MiraiInternalAPI
|
|||||||
* 表明这个 API 是为了让 Java 使用者调用更方便.
|
* 表明这个 API 是为了让 Java 使用者调用更方便.
|
||||||
*/
|
*/
|
||||||
@MiraiInternalAPI
|
@MiraiInternalAPI
|
||||||
@Experimental(level = Experimental.Level.ERROR)
|
@RequiresOptIn(level = RequiresOptIn.Level.ERROR)
|
||||||
@Target(AnnotationTarget.PROPERTY, AnnotationTarget.FUNCTION, AnnotationTarget.TYPE, AnnotationTarget.CLASS)
|
@Target(AnnotationTarget.PROPERTY, AnnotationTarget.FUNCTION, AnnotationTarget.TYPE, AnnotationTarget.CLASS)
|
||||||
annotation class JavaHappyAPI
|
annotation class JavaHappyAPI
|
||||||
|
|
||||||
|
@ -25,7 +25,7 @@ import net.mamoe.mirai.utils.WeakRef
|
|||||||
* 使用低级的 API 无法带来任何安全和便捷保障.
|
* 使用低级的 API 无法带来任何安全和便捷保障.
|
||||||
* 仅在某些使用结构化 API 可能影响性能的情况下使用这些低级 API.
|
* 仅在某些使用结构化 API 可能影响性能的情况下使用这些低级 API.
|
||||||
*/
|
*/
|
||||||
@Experimental
|
@RequiresOptIn
|
||||||
@Retention(AnnotationRetention.BINARY)
|
@Retention(AnnotationRetention.BINARY)
|
||||||
@Target(AnnotationTarget.CLASS, AnnotationTarget.TYPE, AnnotationTarget.FUNCTION, AnnotationTarget.PROPERTY)
|
@Target(AnnotationTarget.CLASS, AnnotationTarget.TYPE, AnnotationTarget.FUNCTION, AnnotationTarget.PROPERTY)
|
||||||
annotation class LowLevelAPI
|
annotation class LowLevelAPI
|
||||||
|
@ -33,7 +33,7 @@ import kotlin.jvm.JvmName
|
|||||||
* 一条从服务器接收到的消息事件.
|
* 一条从服务器接收到的消息事件.
|
||||||
* 请查看各平台的 `actual` 实现的说明.
|
* 请查看各平台的 `actual` 实现的说明.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
expect abstract class MessagePacket<TSender : QQ, TSubject : Contact>() : MessagePacketBase<TSender, TSubject>
|
expect abstract class MessagePacket<TSender : QQ, TSubject : Contact>() : MessagePacketBase<TSender, TSubject>
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -28,6 +28,7 @@ import kotlin.jvm.JvmStatic
|
|||||||
* @see AtAll 全体成员
|
* @see AtAll 全体成员
|
||||||
*/
|
*/
|
||||||
class At
|
class At
|
||||||
|
@Suppress("MemberVisibilityCanBePrivate")
|
||||||
private constructor(val target: Long, val display: String) : Message, MessageContent {
|
private constructor(val target: Long, val display: String) : Message, MessageContent {
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -76,7 +76,7 @@ interface OnlineImage : Image {
|
|||||||
* 查询原图下载链接.
|
* 查询原图下载链接.
|
||||||
*/
|
*/
|
||||||
suspend fun Image.queryUrl(): String {
|
suspend fun Image.queryUrl(): String {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
return when (this) {
|
return when (this) {
|
||||||
is OnlineImage -> this.originUrl
|
is OnlineImage -> this.originUrl
|
||||||
else -> BotImpl.instances.peekFirst().get()?.queryImageUrl(this)
|
else -> BotImpl.instances.peekFirst().get()?.queryImageUrl(this)
|
||||||
@ -102,7 +102,7 @@ interface OfflineImage : Image
|
|||||||
* 原图下载链接. 包含域名
|
* 原图下载链接. 包含域名
|
||||||
*/
|
*/
|
||||||
suspend fun OfflineImage.queryOriginUrl(): String {
|
suspend fun OfflineImage.queryOriginUrl(): String {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
return BotImpl.instances.peekFirst().get()?.queryImageUrl(this) ?: error("No Bot available to query image url")
|
return BotImpl.instances.peekFirst().get()?.queryImageUrl(this) ?: error("No Bot available to query image url")
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -115,7 +115,7 @@ suspend fun OfflineImage.queryOriginUrl(): String {
|
|||||||
* 群图片
|
* 群图片
|
||||||
*/
|
*/
|
||||||
// CustomFace
|
// CustomFace
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
sealed class GroupImage : AbstractImage() {
|
sealed class GroupImage : AbstractImage() {
|
||||||
abstract val filepath: String
|
abstract val filepath: String
|
||||||
abstract val fileId: Int
|
abstract val fileId: Int
|
||||||
@ -184,7 +184,7 @@ abstract class OnlineGroupImage : GroupImage(), OnlineImage
|
|||||||
/**
|
/**
|
||||||
* 好友图片
|
* 好友图片
|
||||||
*/ // NotOnlineImage
|
*/ // NotOnlineImage
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
sealed class FriendImage : AbstractImage() {
|
sealed class FriendImage : AbstractImage() {
|
||||||
abstract val resourceId: String
|
abstract val resourceId: String
|
||||||
abstract val md5: ByteArray
|
abstract val md5: ByteArray
|
||||||
|
@ -39,7 +39,7 @@ open class QuoteReply
|
|||||||
* 用于发送的引用回复.
|
* 用于发送的引用回复.
|
||||||
* 总是使用 [quote] 来构造实例.
|
* 总是使用 [quote] 来构造实例.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
sealed class QuoteReplyToSend
|
sealed class QuoteReplyToSend
|
||||||
@MiraiInternalAPI constructor(source: MessageSource) : QuoteReply(source) {
|
@MiraiInternalAPI constructor(source: MessageSource) : QuoteReply(source) {
|
||||||
class ToGroup(source: MessageSource, val sender: QQ) : QuoteReplyToSend(source) {
|
class ToGroup(source: MessageSource, val sender: QQ) : QuoteReplyToSend(source) {
|
||||||
@ -53,7 +53,7 @@ sealed class QuoteReplyToSend
|
|||||||
* 引用这条消息.
|
* 引用这条消息.
|
||||||
* @see sender 消息发送人.
|
* @see sender 消息发送人.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun MessageChain.quote(sender: QQ?): QuoteReplyToSend {
|
fun MessageChain.quote(sender: QQ?): QuoteReplyToSend {
|
||||||
this.firstOrNull<MessageSource>()?.let {
|
this.firstOrNull<MessageSource>()?.let {
|
||||||
return it.quote(sender)
|
return it.quote(sender)
|
||||||
@ -65,7 +65,7 @@ fun MessageChain.quote(sender: QQ?): QuoteReplyToSend {
|
|||||||
* 引用这条消息.
|
* 引用这条消息.
|
||||||
* @see from 消息来源. 若是好友发送
|
* @see from 消息来源. 若是好友发送
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun MessageSource.quote(from: QQ?): QuoteReplyToSend {
|
fun MessageSource.quote(from: QQ?): QuoteReplyToSend {
|
||||||
return if (this.groupId != 0L) {
|
return if (this.groupId != 0L) {
|
||||||
check(from is Member) { "sender must be Member to quote a GroupMessage" }
|
check(from is Member) { "sender must be Member to quote a GroupMessage" }
|
||||||
|
@ -101,7 +101,7 @@ abstract class BotNetworkHandler : CoroutineScope {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
suspend fun BotNetworkHandler.closeAndJoin(cause: Throwable? = null) {
|
suspend fun BotNetworkHandler.closeAndJoin(cause: Throwable? = null) {
|
||||||
this.close(cause)
|
this.close(cause)
|
||||||
this.supervisor.join()
|
this.supervisor.join()
|
||||||
|
@ -120,7 +120,7 @@ class DeviceInfoData(
|
|||||||
@Transient
|
@Transient
|
||||||
override lateinit var context: Context
|
override lateinit var context: Context
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
override val ipAddress: ByteArray
|
override val ipAddress: ByteArray
|
||||||
get() = localIpAddress().split(".").map { it.toUByte().toByte() }.takeIf { it.size == 4 }?.toByteArray() ?: byteArrayOf()
|
get() = localIpAddress().split(".").map { it.toUByte().toByte() }.takeIf { it.size == 4 }?.toByteArray() ?: byteArrayOf()
|
||||||
override val androidId: ByteArray get() = display
|
override val androidId: ByteArray get() = display
|
||||||
|
@ -18,7 +18,7 @@ import kotlin.annotation.AnnotationTarget.*
|
|||||||
* 非常不建议在发行版本中使用这些 API.
|
* 非常不建议在发行版本中使用这些 API.
|
||||||
*/
|
*/
|
||||||
@Retention(AnnotationRetention.BINARY)
|
@Retention(AnnotationRetention.BINARY)
|
||||||
@Experimental(level = Experimental.Level.ERROR)
|
@RequiresOptIn(level = RequiresOptIn.Level.ERROR)
|
||||||
@Target(
|
@Target(
|
||||||
CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR,
|
CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR,
|
||||||
CLASS,
|
CLASS,
|
||||||
@ -36,7 +36,7 @@ annotation class MiraiInternalAPI(
|
|||||||
* 不建议在发行版本中使用这些 API.
|
* 不建议在发行版本中使用这些 API.
|
||||||
*/
|
*/
|
||||||
@Retention(AnnotationRetention.BINARY)
|
@Retention(AnnotationRetention.BINARY)
|
||||||
@Experimental(level = Experimental.Level.WARNING)
|
@RequiresOptIn(level = RequiresOptIn.Level.WARNING)
|
||||||
@Target(CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR)
|
@Target(CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR)
|
||||||
annotation class MiraiExperimentalAPI(
|
annotation class MiraiExperimentalAPI(
|
||||||
val message: String = ""
|
val message: String = ""
|
||||||
@ -49,7 +49,7 @@ annotation class MiraiExperimentalAPI(
|
|||||||
* 非常不建议在发行版本中使用这些 API.
|
* 非常不建议在发行版本中使用这些 API.
|
||||||
*/
|
*/
|
||||||
@Retention(AnnotationRetention.BINARY)
|
@Retention(AnnotationRetention.BINARY)
|
||||||
@Experimental(level = Experimental.Level.WARNING)
|
@RequiresOptIn(level = RequiresOptIn.Level.WARNING)
|
||||||
@Target(CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR)
|
@Target(CLASS, TYPEALIAS, FUNCTION, PROPERTY, FIELD, CONSTRUCTOR)
|
||||||
annotation class MiraiDebugAPI(
|
annotation class MiraiDebugAPI(
|
||||||
val message: String = ""
|
val message: String = ""
|
||||||
|
@ -30,7 +30,7 @@ import kotlin.jvm.JvmName
|
|||||||
* 从接收者管道读取所有数据并写入 [dst]. 不会关闭 [dst]
|
* 从接收者管道读取所有数据并写入 [dst]. 不会关闭 [dst]
|
||||||
*/
|
*/
|
||||||
suspend fun ByteReadChannel.copyTo(dst: OutputStream) {
|
suspend fun ByteReadChannel.copyTo(dst: OutputStream) {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
ByteArrayPool.useInstance { buffer ->
|
ByteArrayPool.useInstance { buffer ->
|
||||||
var size: Int
|
var size: Int
|
||||||
while (this.readAvailable(buffer).also { size = it } > 0) {
|
while (this.readAvailable(buffer).also { size = it } > 0) {
|
||||||
@ -43,7 +43,7 @@ suspend fun ByteReadChannel.copyTo(dst: OutputStream) {
|
|||||||
* 从接收者管道读取所有数据并写入 [dst]. 不会关闭 [dst]
|
* 从接收者管道读取所有数据并写入 [dst]. 不会关闭 [dst]
|
||||||
*/
|
*/
|
||||||
suspend fun ByteReadChannel.copyTo(dst: Output) {
|
suspend fun ByteReadChannel.copyTo(dst: Output) {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
ByteArrayPool.useInstance { buffer ->
|
ByteArrayPool.useInstance { buffer ->
|
||||||
var size: Int
|
var size: Int
|
||||||
while (this.readAvailable(buffer).also { size = it } > 0) {
|
while (this.readAvailable(buffer).also { size = it } > 0) {
|
||||||
@ -75,7 +75,7 @@ suspend fun ByteReadChannel.copyTo(dst: kotlinx.coroutines.io.ByteWriteChannel)
|
|||||||
*/
|
*/
|
||||||
suspend fun ByteReadChannel.copyAndClose(dst: OutputStream) {
|
suspend fun ByteReadChannel.copyAndClose(dst: OutputStream) {
|
||||||
try {
|
try {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
ByteArrayPool.useInstance { buffer ->
|
ByteArrayPool.useInstance { buffer ->
|
||||||
var size: Int
|
var size: Int
|
||||||
while (this.readAvailable(buffer).also { size = it } > 0) {
|
while (this.readAvailable(buffer).also { size = it } > 0) {
|
||||||
@ -92,7 +92,7 @@ suspend fun ByteReadChannel.copyAndClose(dst: OutputStream) {
|
|||||||
*/
|
*/
|
||||||
suspend fun ByteReadChannel.copyAndClose(dst: Output) {
|
suspend fun ByteReadChannel.copyAndClose(dst: Output) {
|
||||||
try {
|
try {
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
ByteArrayPool.useInstance { buffer ->
|
ByteArrayPool.useInstance { buffer ->
|
||||||
var size: Int
|
var size: Int
|
||||||
while (this.readAvailable(buffer).also { size = it } > 0) {
|
while (this.readAvailable(buffer).also { size = it } > 0) {
|
||||||
|
@ -30,7 +30,7 @@ import kotlin.jvm.JvmSynthetic
|
|||||||
|
|
||||||
@JvmOverloads
|
@JvmOverloads
|
||||||
@Suppress("DuplicatedCode") // false positive. foreach is not common to UByteArray and ByteArray
|
@Suppress("DuplicatedCode") // false positive. foreach is not common to UByteArray and ByteArray
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
fun List<Byte>.toUHexString(separator: String = " ", offset: Int = 0, length: Int = this.size - offset): String {
|
fun List<Byte>.toUHexString(separator: String = " ", offset: Int = 0, length: Int = this.size - offset): String {
|
||||||
require(offset >= 0) { "offset shouldn't be negative: $offset" }
|
require(offset >= 0) { "offset shouldn't be negative: $offset" }
|
||||||
require(length >= 0) { "length shouldn't be negative: $length" }
|
require(length >= 0) { "length shouldn't be negative: $length" }
|
||||||
@ -54,7 +54,7 @@ fun List<Byte>.toUHexString(separator: String = " ", offset: Int = 0, length: In
|
|||||||
|
|
||||||
@JvmOverloads
|
@JvmOverloads
|
||||||
@Suppress("DuplicatedCode") // false positive. foreach is not common to UByteArray and ByteArray
|
@Suppress("DuplicatedCode") // false positive. foreach is not common to UByteArray and ByteArray
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
fun ByteArray.toUHexString(separator: String = " ", offset: Int = 0, length: Int = this.size - offset): String {
|
fun ByteArray.toUHexString(separator: String = " ", offset: Int = 0, length: Int = this.size - offset): String {
|
||||||
this.checkOffsetAndLength(offset, length)
|
this.checkOffsetAndLength(offset, length)
|
||||||
if (length == 0) {
|
if (length == 0) {
|
||||||
@ -99,7 +99,7 @@ inline fun ByteArray.encodeToString(charset: Charset = Charsets.UTF_8): String =
|
|||||||
inline fun ByteArray.toReadPacket(offset: Int = 0, length: Int = this.size - offset) =
|
inline fun ByteArray.toReadPacket(offset: Int = 0, length: Int = this.size - offset) =
|
||||||
ByteReadPacket(this, offset = offset, length = length)
|
ByteReadPacket(this, offset = offset, length = length)
|
||||||
|
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <R> ByteArray.read(t: ByteReadPacket.() -> R): R {
|
inline fun <R> ByteArray.read(t: ByteReadPacket.() -> R): R {
|
||||||
contract {
|
contract {
|
||||||
callsInPlace(t, InvocationKind.EXACTLY_ONCE)
|
callsInPlace(t, InvocationKind.EXACTLY_ONCE)
|
||||||
|
@ -51,7 +51,7 @@ class ChunkedInput(
|
|||||||
*
|
*
|
||||||
* 若 [ByteReadPacket.remaining] 小于 [sizePerPacket], 将会返回唯一元素 [this] 的 [Sequence]
|
* 若 [ByteReadPacket.remaining] 小于 [sizePerPacket], 将会返回唯一元素 [this] 的 [Sequence]
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun ByteReadPacket.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
fun ByteReadPacket.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
||||||
ByteArrayPool.checkBufferSize(sizePerPacket)
|
ByteArrayPool.checkBufferSize(sizePerPacket)
|
||||||
if (this.remaining <= sizePerPacket.toLong()) {
|
if (this.remaining <= sizePerPacket.toLong()) {
|
||||||
@ -76,7 +76,7 @@ fun ByteReadPacket.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
|||||||
* 对于一个 1000 长度的 [ByteReadChannel] 和参数 [sizePerPacket] = 300, 将会产生含四个元素的 [Sequence],
|
* 对于一个 1000 长度的 [ByteReadChannel] 和参数 [sizePerPacket] = 300, 将会产生含四个元素的 [Sequence],
|
||||||
* 其长度分别为: 300, 300, 300, 100.
|
* 其长度分别为: 300, 300, 300, 100.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun ByteReadChannel.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
fun ByteReadChannel.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
||||||
ByteArrayPool.checkBufferSize(sizePerPacket)
|
ByteArrayPool.checkBufferSize(sizePerPacket)
|
||||||
if (this.isClosedForRead) {
|
if (this.isClosedForRead) {
|
||||||
@ -100,7 +100,7 @@ fun ByteReadChannel.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
|||||||
* 对于一个 1000 长度的 [Input] 和参数 [sizePerPacket] = 300, 将会产生含四个元素的 [Sequence],
|
* 对于一个 1000 长度的 [Input] 和参数 [sizePerPacket] = 300, 将会产生含四个元素的 [Sequence],
|
||||||
* 其长度分别为: 300, 300, 300, 100.
|
* 其长度分别为: 300, 300, 300, 100.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class, ExperimentalCoroutinesApi::class)
|
@OptIn(MiraiInternalAPI::class, ExperimentalCoroutinesApi::class)
|
||||||
internal fun Input.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
internal fun Input.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
||||||
ByteArrayPool.checkBufferSize(sizePerPacket)
|
ByteArrayPool.checkBufferSize(sizePerPacket)
|
||||||
|
|
||||||
@ -127,7 +127,7 @@ internal fun Input.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
|||||||
*
|
*
|
||||||
* 若 [ByteReadPacket.remaining] 小于 [sizePerPacket], 将会返回唯一元素 [this] 的 [Sequence]
|
* 若 [ByteReadPacket.remaining] 小于 [sizePerPacket], 将会返回唯一元素 [this] 的 [Sequence]
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class, ExperimentalCoroutinesApi::class)
|
@OptIn(MiraiInternalAPI::class, ExperimentalCoroutinesApi::class)
|
||||||
internal fun InputStream.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
internal fun InputStream.chunkedFlow(sizePerPacket: Int): Flow<ChunkedInput> {
|
||||||
ByteArrayPool.checkBufferSize(sizePerPacket)
|
ByteArrayPool.checkBufferSize(sizePerPacket)
|
||||||
|
|
||||||
|
@ -27,7 +27,7 @@ import kotlin.jvm.JvmMultifileClass
|
|||||||
import kotlin.jvm.JvmName
|
import kotlin.jvm.JvmName
|
||||||
import kotlin.jvm.JvmSynthetic
|
import kotlin.jvm.JvmSynthetic
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
fun ByteReadPacket.copyTo(outputStream: OutputStream) {
|
fun ByteReadPacket.copyTo(outputStream: OutputStream) {
|
||||||
ByteArrayPool.useInstance {
|
ByteArrayPool.useInstance {
|
||||||
while (this.isNotEmpty) {
|
while (this.isNotEmpty) {
|
||||||
@ -50,7 +50,7 @@ inline fun ByteReadPacket.readPacketExact(
|
|||||||
n: Int = remaining.toInt()//not that safe but adequate
|
n: Int = remaining.toInt()//not that safe but adequate
|
||||||
): ByteReadPacket = this.readBytes(n).toReadPacket()
|
): ByteReadPacket = this.readBytes(n).toReadPacket()
|
||||||
|
|
||||||
@UseExperimental(ExperimentalContracts::class)
|
@OptIn(ExperimentalContracts::class)
|
||||||
inline fun <C : Closeable, R> C.withUse(block: C.() -> R): R {
|
inline fun <C : Closeable, R> C.withUse(block: C.() -> R): R {
|
||||||
contract {
|
contract {
|
||||||
callsInPlace(block, InvocationKind.EXACTLY_ONCE)
|
callsInPlace(block, InvocationKind.EXACTLY_ONCE)
|
||||||
|
@ -68,6 +68,6 @@ fun BytePacketBuilder.writeHex(uHex: String) {
|
|||||||
/**
|
/**
|
||||||
* 会使用 [ByteArrayPool] 缓存
|
* 会使用 [ByteArrayPool] 缓存
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
inline fun BytePacketBuilder.encryptAndWrite(key: ByteArray, encoder: BytePacketBuilder.() -> Unit) =
|
inline fun BytePacketBuilder.encryptAndWrite(key: ByteArray, encoder: BytePacketBuilder.() -> Unit) =
|
||||||
TEA.encrypt(BytePacketBuilder().apply(encoder).build(), key) { decrypted -> writeFully(decrypted) }
|
TEA.encrypt(BytePacketBuilder().apply(encoder).build(), key) { decrypted -> writeFully(decrypted) }
|
@ -35,7 +35,7 @@ internal class CombinedMessageTest {
|
|||||||
|
|
||||||
private val toAdd = "1".toMessage()
|
private val toAdd = "1".toMessage()
|
||||||
|
|
||||||
@UseExperimental(ExperimentalTime::class)
|
@OptIn(ExperimentalTime::class)
|
||||||
@Test
|
@Test
|
||||||
fun speedTest() = repeat(100) {
|
fun speedTest() = repeat(100) {
|
||||||
var count = 1L
|
var count = 1L
|
||||||
@ -86,7 +86,7 @@ internal class CombinedMessageTest {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalTime::class)
|
@OptIn(ExperimentalTime::class)
|
||||||
@Test
|
@Test
|
||||||
fun testFastIteration() {
|
fun testFastIteration() {
|
||||||
println("start!")
|
println("start!")
|
||||||
|
@ -24,7 +24,9 @@ import net.mamoe.mirai.utils.*
|
|||||||
* @see kotlinx.coroutines.isActive 判断 [Bot] 是否正常运行中. (在线, 且没有被 [close])
|
* @see kotlinx.coroutines.isActive 判断 [Bot] 是否正常运行中. (在线, 且没有被 [close])
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, LowLevelAPI::class, MiraiExperimentalAPI::class, JavaHappyAPI::class)
|
@OptIn(
|
||||||
|
MiraiInternalAPI::class, LowLevelAPI::class, MiraiExperimentalAPI::class, JavaHappyAPI::class
|
||||||
|
)
|
||||||
actual abstract class Bot actual constructor() : CoroutineScope, LowLevelBotAPIAccessor, BotJavaHappyAPI() {
|
actual abstract class Bot actual constructor() : CoroutineScope, LowLevelBotAPIAccessor, BotJavaHappyAPI() {
|
||||||
actual companion object {
|
actual companion object {
|
||||||
/**
|
/**
|
||||||
@ -244,6 +246,6 @@ actual abstract class Bot actual constructor() : CoroutineScope, LowLevelBotAPIA
|
|||||||
*/
|
*/
|
||||||
actual abstract fun close(cause: Throwable?)
|
actual abstract fun close(cause: Throwable?)
|
||||||
|
|
||||||
@UseExperimental(LowLevelAPI::class, MiraiExperimentalAPI::class)
|
@OptIn(LowLevelAPI::class, MiraiExperimentalAPI::class)
|
||||||
actual final override fun toString(): String = "Bot(${uin})"
|
actual final override fun toString(): String = "Bot(${uin})"
|
||||||
}
|
}
|
@ -132,7 +132,7 @@ actual abstract class BotJavaHappyAPI actual constructor() {
|
|||||||
message: String? = null,
|
message: String? = null,
|
||||||
remark: String? = null
|
remark: String? = null
|
||||||
): AddFriendResult {
|
): AddFriendResult {
|
||||||
@UseExperimental(MiraiExperimentalAPI::class)
|
@OptIn(MiraiExperimentalAPI::class)
|
||||||
return runBlocking { addFriend(id, message, remark) }
|
return runBlocking { addFriend(id, message, remark) }
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -169,7 +169,7 @@ actual abstract class BotJavaHappyAPI actual constructor() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
internal fun <R, C : CoroutineScope> C.future(block: suspend C.() -> R): Future<R> {
|
internal fun <R, C : CoroutineScope> C.future(block: suspend C.() -> R): Future<R> {
|
||||||
val future = object : Future<R> {
|
val future = object : Future<R> {
|
||||||
val value: CompletableDeferred<R> = CompletableDeferred()
|
val value: CompletableDeferred<R> = CompletableDeferred()
|
||||||
@ -214,7 +214,7 @@ internal fun <R, C : CoroutineScope> C.future(block: suspend C.() -> R): Future<
|
|||||||
}
|
}
|
||||||
|
|
||||||
launch {
|
launch {
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
future.value.completeWith(kotlin.runCatching { block() })
|
future.value.completeWith(kotlin.runCatching { block() })
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -32,7 +32,7 @@ import net.mamoe.mirai.utils.WeakRefProperty
|
|||||||
* @author Him188moe
|
* @author Him188moe
|
||||||
*/
|
*/
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
@UseExperimental(MiraiInternalAPI::class, JavaHappyAPI::class)
|
@OptIn(MiraiInternalAPI::class, JavaHappyAPI::class)
|
||||||
actual abstract class Contact : CoroutineScope, ContactJavaHappyAPI() {
|
actual abstract class Contact : CoroutineScope, ContactJavaHappyAPI() {
|
||||||
/**
|
/**
|
||||||
* 这个联系人所属 [Bot].
|
* 这个联系人所属 [Bot].
|
||||||
|
@ -20,7 +20,7 @@ import net.mamoe.mirai.utils.WeakRefProperty
|
|||||||
/**
|
/**
|
||||||
* 群成员.
|
* 群成员.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class, JavaHappyAPI::class)
|
@OptIn(MiraiInternalAPI::class, JavaHappyAPI::class)
|
||||||
@Suppress("INAPPLICABLE_JVM_NAME")
|
@Suppress("INAPPLICABLE_JVM_NAME")
|
||||||
actual abstract class Member : MemberJavaHappyAPI() {
|
actual abstract class Member : MemberJavaHappyAPI() {
|
||||||
/**
|
/**
|
||||||
|
@ -29,7 +29,7 @@ import java.net.URL
|
|||||||
* 一条从服务器接收到的消息事件.
|
* 一条从服务器接收到的消息事件.
|
||||||
* JVM 平台相关扩展
|
* JVM 平台相关扩展
|
||||||
*/
|
*/
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual abstract class MessagePacket<TSender : QQ, TSubject : Contact> actual constructor() : MessagePacketBase<TSender, TSubject>() {
|
actual abstract class MessagePacket<TSender : QQ, TSubject : Contact> actual constructor() : MessagePacketBase<TSender, TSubject>() {
|
||||||
// region 上传图片
|
// region 上传图片
|
||||||
suspend inline fun uploadImage(image: BufferedImage): Image = subject.uploadImage(image)
|
suspend inline fun uploadImage(image: BufferedImage): Image = subject.uploadImage(image)
|
||||||
|
@ -28,7 +28,7 @@ import net.mamoe.mirai.utils.unsafeWeakRef
|
|||||||
* @see MessageReceipt.sourceTime 源时间
|
* @see MessageReceipt.sourceTime 源时间
|
||||||
*/
|
*/
|
||||||
@Suppress("FunctionName")
|
@Suppress("FunctionName")
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual open class MessageReceipt<C : Contact> actual constructor(
|
actual open class MessageReceipt<C : Contact> actual constructor(
|
||||||
actual val source: MessageSource,
|
actual val source: MessageSource,
|
||||||
target: C,
|
target: C,
|
||||||
@ -94,7 +94,7 @@ actual open class MessageReceipt<C : Contact> actual constructor(
|
|||||||
*/
|
*/
|
||||||
actual open suspend fun quote(): QuoteReplyToSend {
|
actual open suspend fun quote(): QuoteReplyToSend {
|
||||||
this.source.ensureSequenceIdAvailable()
|
this.source.ensureSequenceIdAvailable()
|
||||||
@UseExperimental(LowLevelAPI::class)
|
@OptIn(LowLevelAPI::class)
|
||||||
return _unsafeQuote()
|
return _unsafeQuote()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -57,7 +57,7 @@ actual fun localIpAddress(): String = InetAddress.getLocalHost().hostAddress
|
|||||||
|
|
||||||
actual val Http: HttpClient get() = HttpClient(CIO)
|
actual val Http: HttpClient get() = HttpClient(CIO)
|
||||||
|
|
||||||
@UseExperimental(MiraiInternalAPI::class)
|
@OptIn(MiraiInternalAPI::class)
|
||||||
actual fun ByteArray.unzip(offset: Int, length: Int): ByteArray {
|
actual fun ByteArray.unzip(offset: Int, length: Int): ByteArray {
|
||||||
this.checkOffsetAndLength(offset, length)
|
this.checkOffsetAndLength(offset, length)
|
||||||
if (length == 0) return ByteArray(0)
|
if (length == 0) return ByteArray(0)
|
||||||
|
@ -21,7 +21,7 @@ import java.io.File
|
|||||||
/**
|
/**
|
||||||
* 加载一个设备信息. 若文件不存在或为空则随机并创建一个设备信息保存.
|
* 加载一个设备信息. 若文件不存在或为空则随机并创建一个设备信息保存.
|
||||||
*/
|
*/
|
||||||
@UseExperimental(UnstableDefault::class)
|
@OptIn(UnstableDefault::class)
|
||||||
fun File.loadAsDeviceInfo(context: Context = ContextImpl()): DeviceInfo {
|
fun File.loadAsDeviceInfo(context: Context = ContextImpl()): DeviceInfo {
|
||||||
if (!this.exists() || this.length() == 0L) {
|
if (!this.exists() || this.length() == 0L) {
|
||||||
return SystemDeviceInfo(context).also {
|
return SystemDeviceInfo(context).also {
|
||||||
@ -35,7 +35,7 @@ fun File.loadAsDeviceInfo(context: Context = ContextImpl()): DeviceInfo {
|
|||||||
|
|
||||||
|
|
||||||
@Serializable
|
@Serializable
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
actual open class SystemDeviceInfo actual constructor() : DeviceInfo() {
|
actual open class SystemDeviceInfo actual constructor() : DeviceInfo() {
|
||||||
actual constructor(context: Context) : this() {
|
actual constructor(context: Context) : this() {
|
||||||
this.context = context
|
this.context = context
|
||||||
|
@ -80,7 +80,7 @@ actual class PlatformSocket : Closeable {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalIoApi::class)
|
@OptIn(ExperimentalIoApi::class)
|
||||||
actual suspend fun connect(serverHost: String, serverPort: Int) {
|
actual suspend fun connect(serverHost: String, serverPort: Int) {
|
||||||
withContext(Dispatchers.IO) {
|
withContext(Dispatchers.IO) {
|
||||||
socket = Socket(serverHost, serverPort)
|
socket = Socket(serverHost, serverPort)
|
||||||
|
@ -142,7 +142,7 @@ internal class LockFreeLinkedListTest {
|
|||||||
list.size shouldBeEqualTo 0
|
list.size shouldBeEqualTo 0
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalUnsignedTypes::class)
|
@OptIn(ExperimentalUnsignedTypes::class)
|
||||||
@Test
|
@Test
|
||||||
fun withInlineClassElements() {
|
fun withInlineClassElements() {
|
||||||
val list = LockFreeLinkedList<UInt>()
|
val list = LockFreeLinkedList<UInt>()
|
||||||
@ -270,7 +270,7 @@ internal class LockFreeLinkedListTest {
|
|||||||
*/
|
*/
|
||||||
}
|
}
|
||||||
|
|
||||||
@UseExperimental(ExperimentalCoroutinesApi::class)
|
@OptIn(ExperimentalCoroutinesApi::class)
|
||||||
@MiraiExperimentalAPI
|
@MiraiExperimentalAPI
|
||||||
internal suspend inline fun <E : LockFreeLinkedList<*>> E.concurrentDo(numberOfCoroutines: Int, times: Int, crossinline todo: E.() -> Unit) =
|
internal suspend inline fun <E : LockFreeLinkedList<*>> E.concurrentDo(numberOfCoroutines: Int, times: Int, crossinline todo: E.() -> Unit) =
|
||||||
coroutineScope {
|
coroutineScope {
|
||||||
|
Loading…
Reference in New Issue
Block a user