コンテンツにスキップ

2023/9/11

Topics

Room

  • 自作クラスを Entity に持つときは TypeConverter を指定する
  • 2.3 から enum class はデフォルトでサポートされてるので TypeConverter がいらなくなった
  • value class がサポートされていない
  • View > ToolWindows > App Inspection > Database Inspector で DB が見れる
  • Migration
    • Column を追加して Migration するときは defaultValue が必要
      • ALTER TABLE table ADD COLUMN id NOT NULL Default '' とかしても default value が expected と違うってエラーになる
      • もうだいたい AutoMigration で完結するんじゃ?
    • テスト
      • testhelper ライブラリが提供されてる
      • Database に TypeConverters を指定してると MigrationTestHelper の createDatabase で typeConverters が null になって Exception
        • 2.4.3 -> 2.5.2 で解決されてる

[kotlin-serialization](https://kotlinlang.org/docs/serialization.html

  • Throwable は Serializable じゃないのでできない
    • CustomSerializer 作るしかない
      • タイプ保存しても元のクラスに戻すには when で知る限りの exception を列挙するしかない?🤔
      • encodeStructure だと StackTraceElement の List がたくさんあるのでシリアライズ用の Serializable を用意してやりくりしてみた
object ThrowableSerializer : KSerializer<Throwable> {  

    @Serializable  
    private data class SerializableThrowable(  
        val message: String?,  
        val stackTrace: List<SerializableStackTraceElement>  
    )  

    @Serializable  
    private data class SerializableStackTraceElement(  
        val className: String?,  
        val methodName: String?,  
        val fileName: String?,  
        val lineNumber: Int  
    )  

    override val descriptor: SerialDescriptor = buildClassSerialDescriptor("Throwable") {  
        element<String>("message")  
        element<SerializableStackTraceElement>("stack_trace")  
    }  

    override fun deserialize(decoder: Decoder): Throwable {  
        val throwable = decoder.decodeSerializableValue(SerializableThrowable.serializer())  
        return Throwable(message = throwable.message).also {  
            it.stackTrace = throwable.stackTrace.map { s ->  
                StackTraceElement(s.className, s.methodName, s.fileName, s.lineNumber)  
            }.toTypedArray()  
        }  
    }  

    override fun serialize(encoder: Encoder, value: Throwable) {  
        val throwable = SerializableThrowable(  
            value.message,
            value.stackTrace.map {  
                SerializableStackTraceElement(  
                    className = it.className,  
                    methodName = it.methodName,  
                    fileName = it.fileName,  
                    lineNumber = it.lineNumber  
                )
            }
        )
        encoder.encodeSerializableValue(SerializableThrowable.serializer(), throwable)
    }
}

コメント