Kaynağa Gözat

Delegate json serialization strategy to BotConfiguration

Him188 5 yıl önce
ebeveyn
işleme
4cb5d654b2

+ 1 - 7
mirai-core-qqandroid/src/commonMain/kotlin/net/mamoe/mirai/qqandroid/QQAndroidBot.common.kt

@@ -19,9 +19,6 @@ import kotlinx.coroutines.CoroutineName
 import kotlinx.coroutines.async
 import kotlinx.coroutines.sync.Mutex
 import kotlinx.coroutines.withContext
-import kotlinx.serialization.UnstableDefault
-import kotlinx.serialization.json.Json
-import kotlinx.serialization.json.JsonConfiguration
 import kotlinx.serialization.json.int
 import net.mamoe.mirai.Bot
 import net.mamoe.mirai.LowLevelAPI
@@ -241,10 +238,7 @@ internal abstract class QQAndroidBotBase constructor(
     override val id: Long
         get() = account.id
 
-    companion object {
-        @OptIn(UnstableDefault::class)
-        val json = Json(JsonConfiguration(ignoreUnknownKeys = true, encodeDefaults = true))
-    }
+    private inline val json get() = configuration.json
 
     override val friends: ContactList<Friend> = ContactList(LockFreeLinkedList())
 

+ 13 - 0
mirai-core/src/commonMain/kotlin/net.mamoe.mirai/utils/BotConfiguration.common.kt

@@ -12,6 +12,9 @@ package net.mamoe.mirai.utils
 
 import kotlinx.coroutines.Job
 import kotlinx.coroutines.SupervisorJob
+import kotlinx.serialization.UnstableDefault
+import kotlinx.serialization.json.Json
+import kotlinx.serialization.json.JsonConfiguration
 import net.mamoe.mirai.Bot
 import kotlin.coroutines.CoroutineContext
 import kotlin.coroutines.EmptyCoroutineContext
@@ -118,6 +121,16 @@ internal open class BotConfigurationBase internal constructor() {
     @MiraiExperimentalAPI
     var fileCacheStrategy: FileCacheStrategy = FileCacheStrategy.PlatformDefault
 
+    /**
+     * Json 序列化器, 使用 'kotlinx.serialization'
+     */
+    @SinceMirai("1.1.0")
+    @MiraiExperimentalAPI
+    var json: Json = kotlin.runCatching {
+        @OptIn(UnstableDefault::class)
+        Json(JsonConfiguration(isLenient = true, ignoreUnknownKeys = true))
+    }.getOrElse { Json(JsonConfiguration.Stable) }
+
     enum class MiraiProtocol(
         /** 协议模块使用的 ID */
         @JvmField internal val id: Long

+ 2 - 2
mirai-core/src/jvmMain/kotlin/net/mamoe/mirai/utils/LoginSolver.jvm.kt

@@ -154,9 +154,9 @@ actual abstract class LoginSolver {
 //////////////// internal
 ///////////////////////////////
 
-internal  fun getFileBasedDeviceInfoSupplier(filename: String): ((Context) -> DeviceInfo)? {
+internal fun BotConfiguration.getFileBasedDeviceInfoSupplier(filename: String): ((Context) -> DeviceInfo)? {
     return {
-        File(filename).loadAsDeviceInfo(it)
+        File(filename).loadAsDeviceInfo(json, it)
     }
 }
 

+ 3 - 12
mirai-core/src/jvmMain/kotlin/net/mamoe/mirai/utils/SystemDeviceInfo.kt

@@ -23,26 +23,17 @@ import kotlin.random.nextInt
 /**
  * 加载一个设备信息. 若文件不存在或为空则随机并创建一个设备信息保存.
  */
-fun File.loadAsDeviceInfo(context: Context = ContextImpl()): DeviceInfo {
+fun File.loadAsDeviceInfo(json: Json, context: Context = ContextImpl()): DeviceInfo {
     if (!this.exists() || this.length() == 0L) {
         return SystemDeviceInfo(context).also {
-            this.writeText(JSON.stringify(SystemDeviceInfo.serializer(), it))
+            this.writeText(json.stringify(SystemDeviceInfo.serializer(), it))
         }
     }
-    return JSON.parse(DeviceInfoData.serializer(), this.readText()).also {
+    return json.parse(DeviceInfoData.serializer(), this.readText()).also {
         it.context = context
     }
 }
 
-@OptIn(UnstableDefault::class)
-private val JSON = Json(
-    JsonConfiguration(
-        ignoreUnknownKeys = true,
-        isLenient = true,
-        prettyPrint = true
-    )
-)
-
 @Serializable
 actual open class SystemDeviceInfo actual constructor() : DeviceInfo() {
     actual constructor(context: Context) : this() {