mirror of
https://github.com/mamoe/mirai.git
synced 2025-04-25 04:50:26 +08:00
Daily QQA update
This commit is contained in:
parent
9b564a2ade
commit
5a0cab2f10
README.md
mirai-api-http/src/main/kotlin/net.mamoe.mirai.api.http
mirai-core-qqandroid/src/commonMain/kotlin/net/mamoe/mirai/qqandroid/network
@ -115,5 +115,5 @@ bot.subscribeAlways<MemberPermissionChangedEvent> {
|
||||
- (见 LICENSE 第 4 节) 您可以免费或收费地传递这个项目的源代码或目标代码(即编译结果), **但前提是提供明显的版权声明** (您需要标注本 `GitHub` 项目地址)
|
||||
|
||||
## Acknowledgement
|
||||
特别感谢 [JetBrains](https://www.jetbrains.com/) 提供的免费 [IntelliJ IDEA](https://www.jetbrains.com/idea/) 等 IDE 授权
|
||||
[<img src=".github/jetbrains-variant-3.png" width="200"/>](https://www.jetbrains.com/)
|
||||
特别感谢 [JetBrains](https://www.jetbrains.com/?from=mirai) 提供的免费 [IntelliJ IDEA](https://www.jetbrains.com/idea/?from=mirai) 等 IDE 授权
|
||||
[<img src=".github/jetbrains-variant-3.png" width="200"/>](https://www.jetbrains.com/?from=mirai)
|
@ -50,8 +50,8 @@ fun Application.mirai() {
|
||||
mirai("/addFriend") {
|
||||
Bot.instanceWhose(qq = param("bot")).addFriend(
|
||||
id = param("qq"),
|
||||
message = paramOrNull<String?>("message")?.let { it },
|
||||
remark = paramOrNull<String?>("remark")?.let { it }
|
||||
message = paramOrNull("message"),
|
||||
remark = paramOrNull("remark")
|
||||
)
|
||||
|
||||
call.ok()
|
||||
|
@ -16,6 +16,9 @@ import net.mamoe.mirai.utils.MiraiInternalAPI
|
||||
import net.mamoe.mirai.utils.cryptor.ECDH
|
||||
import net.mamoe.mirai.utils.cryptor.contentToString
|
||||
import net.mamoe.mirai.utils.io.hexToBytes
|
||||
import net.mamoe.mirai.utils.io.read
|
||||
import net.mamoe.mirai.utils.io.readUShortLVByteArray
|
||||
import net.mamoe.mirai.utils.io.readUShortLVString
|
||||
import net.mamoe.mirai.utils.unsafeWeakRef
|
||||
|
||||
/*
|
||||
@ -123,6 +126,8 @@ internal open class QQAndroidClient(
|
||||
lateinit var qrPushSig: ByteArray
|
||||
|
||||
lateinit var mainDisplayName: ByteArray
|
||||
|
||||
var transportSequenceId = 1
|
||||
}
|
||||
|
||||
class ReserveUinInfo(
|
||||
@ -191,6 +196,9 @@ class WLoginSigInfo(
|
||||
val a2CreationTime: Long,
|
||||
val tgtKey: ByteArray,
|
||||
val userStSig: UserStSig,
|
||||
/**
|
||||
* TransEmpPacket 加密使用
|
||||
*/
|
||||
val userStKey: ByteArray,
|
||||
val userStWebSig: UserStWebSig,
|
||||
val userA5: UserA5,
|
||||
@ -206,7 +214,8 @@ class WLoginSigInfo(
|
||||
val d2Key: ByteArray,
|
||||
val sid: Sid,
|
||||
val aqSig: AqSig,
|
||||
val psKey: PSKey,
|
||||
val psKeyMap: PSKeyMap,
|
||||
val pt4TokenMap: Pt4TokenMap,
|
||||
val superKey: ByteArray,
|
||||
val payToken: ByteArray,
|
||||
val pf: ByteArray,
|
||||
@ -218,7 +227,7 @@ class WLoginSigInfo(
|
||||
val deviceToken: ByteArray
|
||||
) {
|
||||
override fun toString(): String {
|
||||
return "WLoginSigInfo(uin=$uin, encryptA1=${encryptA1.contentToString()}, noPicSig=${noPicSig.contentToString()}, G=${G.contentToString()}, dpwd=${dpwd.contentToString()}, randSeed=${randSeed.contentToString()}, simpleInfo=$simpleInfo, appPri=$appPri, a2ExpiryTime=$a2ExpiryTime, loginBitmap=$loginBitmap, tgt=${tgt.contentToString()}, a2CreationTime=$a2CreationTime, tgtKey=${tgtKey.contentToString()}, userStSig=$userStSig, userStKey=${userStKey.contentToString()}, userStWebSig=$userStWebSig, userA5=$userA5, userA8=$userA8, lsKey=$lsKey, sKey=$sKey, userSig64=$userSig64, openId=${openId.contentToString()}, openKey=$openKey, vKey=$vKey, accessToken=$accessToken, d2=$d2, d2Key=${d2Key.contentToString()}, sid=$sid, aqSig=$aqSig, psKey=$psKey, superKey=${superKey.contentToString()}, payToken=${payToken.contentToString()}, pf=${pf.contentToString()}, pfKey=${pfKey.contentToString()}, da2=${da2.contentToString()}, wtSessionTicket=$wtSessionTicket, wtSessionTicketKey=${wtSessionTicketKey.contentToString()}, deviceToken=${deviceToken.contentToString()})"
|
||||
return "WLoginSigInfo(uin=$uin, encryptA1=${encryptA1.contentToString()}, noPicSig=${noPicSig.contentToString()}, G=${G.contentToString()}, dpwd=${dpwd.contentToString()}, randSeed=${randSeed.contentToString()}, simpleInfo=$simpleInfo, appPri=$appPri, a2ExpiryTime=$a2ExpiryTime, loginBitmap=$loginBitmap, tgt=${tgt.contentToString()}, a2CreationTime=$a2CreationTime, tgtKey=${tgtKey.contentToString()}, userStSig=$userStSig, userStKey=${userStKey.contentToString()}, userStWebSig=$userStWebSig, userA5=$userA5, userA8=$userA8, lsKey=$lsKey, sKey=$sKey, userSig64=$userSig64, openId=${openId.contentToString()}, openKey=$openKey, vKey=$vKey, accessToken=$accessToken, d2=$d2, d2Key=${d2Key.contentToString()}, sid=$sid, aqSig=$aqSig, psKey=${psKeyMap.contentToString()}, superKey=${superKey.contentToString()}, payToken=${payToken.contentToString()}, pf=${pf.contentToString()}, pfKey=${pfKey.contentToString()}, da2=${da2.contentToString()}, wtSessionTicket=$wtSessionTicket, wtSessionTicketKey=${wtSessionTicketKey.contentToString()}, deviceToken=${deviceToken.contentToString()})"
|
||||
}
|
||||
}
|
||||
|
||||
@ -235,7 +244,27 @@ class AccessToken(data: ByteArray, creationTime: Long) : KeyWithCreationTime(dat
|
||||
class D2(data: ByteArray, creationTime: Long, expireTime: Long) : KeyWithExpiry(data, creationTime, expireTime)
|
||||
class Sid(data: ByteArray, creationTime: Long, expireTime: Long) : KeyWithExpiry(data, creationTime, expireTime)
|
||||
class AqSig(data: ByteArray, creationTime: Long) : KeyWithCreationTime(data, creationTime)
|
||||
class PSKey(data: ByteArray, creationTime: Long) : KeyWithCreationTime(data, creationTime)
|
||||
|
||||
class Pt4Token(data: ByteArray, creationTime: Long, expireTime: Long) : KeyWithExpiry(data, creationTime, expireTime)
|
||||
|
||||
typealias PSKeyMap = MutableMap<String, PSKey>
|
||||
typealias Pt4TokenMap = MutableMap<String, Pt4Token>
|
||||
|
||||
internal fun parsePSKeyMapAndPt4TokenMap(data: ByteArray, creationTime: Long, expireTime: Long, outPSKeyMap: PSKeyMap, outPt4TokenMap: Pt4TokenMap) = data.read {
|
||||
repeat(readShort().toInt()) {
|
||||
val domain = readUShortLVString()
|
||||
val psKey = readUShortLVByteArray()
|
||||
val pt4token = readUShortLVByteArray()
|
||||
|
||||
when{
|
||||
psKey.size > 0 -> outPSKeyMap[domain] = PSKey(psKey, creationTime, expireTime)
|
||||
pt4token.size > 0 -> outPt4TokenMap[domain] = Pt4Token(pt4token, creationTime, expireTime)
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
class PSKey(data: ByteArray, creationTime: Long, expireTime: Long) : KeyWithExpiry(data, creationTime, expireTime)
|
||||
|
||||
class WtSessionTicket(data: ByteArray, creationTime: Long) : KeyWithCreationTime(data, creationTime)
|
||||
|
||||
open class KeyWithExpiry(
|
||||
|
@ -312,9 +312,17 @@ internal object LoginPacket : PacketFactory<LoginPacket.LoginPacketResponse, Log
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
// TODO sigMap??? =0x21410e0 // from qq
|
||||
|
||||
val creationTime = currentTimeSeconds
|
||||
val expireTime = creationTime + 2160000L
|
||||
@Suppress("UNREACHABLE_CODE") // FOR STUB
|
||||
|
||||
val outPSKeyMap: PSKeyMap = mutableMapOf()
|
||||
val outPt4TokenMap: Pt4TokenMap = mutableMapOf()
|
||||
|
||||
parsePSKeyMapAndPt4TokenMap(tlvMap119[0x512]?: error("Cannot find tlv 0x512, which is pskeyMap and pt4tokenMap"), creationTime, expireTime, outPSKeyMap, outPt4TokenMap)
|
||||
|
||||
client.wLoginSigInfo = WLoginSigInfo(
|
||||
uin = client.uin,
|
||||
encryptA1 = inline {
|
||||
@ -354,7 +362,8 @@ internal object LoginPacket : PacketFactory<LoginPacket.LoginPacketResponse, Log
|
||||
d2Key = tlvMap119.getOrEmpty(0x305),
|
||||
sid = Sid(tlvMap119.getOrEmpty(0x164), creationTime, expireTime),
|
||||
aqSig = AqSig(tlvMap119.getOrEmpty(0x171), creationTime),
|
||||
psKey = PSKey(tlvMap119.getOrEmpty(0x512), creationTime),
|
||||
psKeyMap = outPSKeyMap,
|
||||
pt4TokenMap = outPt4TokenMap,
|
||||
superKey = tlvMap119.getOrEmpty(0x16d),
|
||||
payToken = payToken,
|
||||
pf = pf,
|
||||
|
@ -1,14 +1,11 @@
|
||||
package net.mamoe.mirai.qqandroid.network.protocol.packet.login
|
||||
|
||||
|
||||
import kotlinx.io.core.ByteReadPacket
|
||||
import net.mamoe.mirai.data.Packet
|
||||
import net.mamoe.mirai.qqandroid.QQAndroidBot
|
||||
import net.mamoe.mirai.qqandroid.network.QQAndroidClient
|
||||
import net.mamoe.mirai.qqandroid.network.protocol.packet.*
|
||||
import net.mamoe.mirai.qqandroid.network.protocol.packet.OutgoingPacket
|
||||
import net.mamoe.mirai.qqandroid.network.protocol.packet.PacketFactory
|
||||
import net.mamoe.mirai.qqandroid.network.protocol.packet.buildLoginOutgoingPacket
|
||||
import net.mamoe.mirai.qqandroid.network.protocol.packet.writeOicqRequestPacket
|
||||
import net.mamoe.mirai.utils.io.toReadPacket
|
||||
|
||||
internal object TransEmpPacket : PacketFactory<TransEmpPacket.Response, LoginPacketDecrypter>(LoginPacketDecrypter) {
|
||||
@ -20,11 +17,11 @@ internal object TransEmpPacket : PacketFactory<TransEmpPacket.Response, LoginPac
|
||||
private const val appId = 16L
|
||||
private const val subAppId = 537062845L
|
||||
|
||||
|
||||
@Suppress("FunctionName")
|
||||
fun SubCommand1(
|
||||
client: QQAndroidClient
|
||||
): OutgoingPacket = buildLoginOutgoingPacket(client, subAppId, ssoExtraData = byteArrayOf().toReadPacket()) {
|
||||
writeOicqRequestPacket(client, EncryptMethodECDH135(client.ecdh), id){
|
||||
writeOicqRequestPacket(client, EncryptMethodECDH135(client.ecdh), id) {
|
||||
|
||||
// oicq.wlogin_sdk.request.trans_emp_1#packTransEmpBody
|
||||
}
|
||||
@ -36,5 +33,4 @@ internal object TransEmpPacket : PacketFactory<TransEmpPacket.Response, LoginPac
|
||||
override suspend fun ByteReadPacket.decode(bot: QQAndroidBot): Response {
|
||||
TODO("not implemented")
|
||||
}
|
||||
|
||||
}
|
Loading…
Reference in New Issue
Block a user