diff --git a/mirai-core/src/commonMain/kotlin/network/components/SsoProcessor.kt b/mirai-core/src/commonMain/kotlin/network/components/SsoProcessor.kt index 330e0bdb3..0675b7cd2 100644 --- a/mirai-core/src/commonMain/kotlin/network/components/SsoProcessor.kt +++ b/mirai-core/src/commonMain/kotlin/network/components/SsoProcessor.kt @@ -182,7 +182,9 @@ internal class SsoProcessorImpl( } override suspend fun logout(handler: NetworkHandler) { - handler.sendWithoutExpect(StatSvc.Register.offline(client)) + if (firstLoginSucceed) { + handler.sendWithoutExpect(StatSvc.Register.offline(client)) + } } private fun createClient(bot: QQAndroidBot): QQAndroidClient { @@ -265,6 +267,7 @@ internal class SsoProcessorImpl( logger.info { "Login successful" } break@mainloop } + is LoginPacketResponse.DeviceLockLogin -> { response = WtLogin20(client).sendAndExpect() } @@ -278,6 +281,7 @@ internal class SsoProcessorImpl( is UrlDeviceVerificationResult -> { WtLogin9(client, allowSlider).sendAndExpect() } + is SmsDeviceVerificationResult -> { WtLogin7(client, result.token, result.code).sendAndExpect() } diff --git a/mirai-core/src/commonTest/kotlin/network/handler/SelectorLoginRecoveryTest.kt b/mirai-core/src/commonTest/kotlin/network/handler/SelectorLoginRecoveryTest.kt index d009b2897..56f8d2c4b 100644 --- a/mirai-core/src/commonTest/kotlin/network/handler/SelectorLoginRecoveryTest.kt +++ b/mirai-core/src/commonTest/kotlin/network/handler/SelectorLoginRecoveryTest.kt @@ -10,6 +10,7 @@ package net.mamoe.mirai.internal.network.handler import kotlinx.coroutines.test.runTest +import net.mamoe.mirai.internal.network.components.FirstLoginResult import net.mamoe.mirai.internal.network.components.SsoProcessor import net.mamoe.mirai.internal.network.framework.AbstractRealNetworkHandlerTest import net.mamoe.mirai.internal.network.framework.TestCommonNetworkHandler @@ -51,4 +52,34 @@ internal class SelectorLoginRecoveryTest : assertEquals(exceptionMessage, e.message) } } + + /** + * 登录时遇到未知错误, [WtLogin] 会抛 [IllegalStateException] (即抛不可挽救的异常), + * selector 应该 close Bot, 不要 logout, 要重新抛出捕获的异常. + */ + @Test + fun `do not call logout when closing bot due to failed to login`() = runTest { + val exceptionMessage = "Login failed!" + setComponent(SsoProcessor, object : TestSsoProcessor(bot) { + override suspend fun login(handler: NetworkHandler) { + throw IllegalStateException(exceptionMessage) + } + + override suspend fun logout(handler: NetworkHandler) { + if (firstLoginSucceed) { + throw AssertionError("Congratulations! You called logout!") + } + } + }) + + assertEquals(null, bot.components[SsoProcessor].firstLoginResult) + bot.components[SsoProcessor].setFirstLoginResult(null) + assertFailsWith<IllegalStateException> { + bot.login() + }.let { e -> + assertEquals(exceptionMessage, e.message) + } + assertEquals(FirstLoginResult.OTHER_FAILURE, bot.components[SsoProcessor].firstLoginResult) + bot.close() + } } \ No newline at end of file