反序列化Scala对象时的java.lang.ClassCastException

反序列化Scala对象时的java.lang.ClassCastException,scala,serialization,sbt,deserialization,ammonite,Scala,Serialization,Sbt,Deserialization,Ammonite,我有一个这样的物体 case class QueryResult(events: List[Event]) 我需要序列化反序列化。对于序列化,我有这个隐式类 implicit class Serializer(obj: Object) { def serialize: Array[Byte] = { val stream = new ByteArrayOutputStream() val objectOutputStream = new ObjectOutp

我有一个这样的物体

case class QueryResult(events: List[Event])
我需要序列化反序列化。对于序列化,我有这个隐式类

  implicit class Serializer(obj: Object) {
    def serialize: Array[Byte] = {
      val stream = new ByteArrayOutputStream()
      val objectOutputStream = new ObjectOutputStream(stream)
      objectOutputStream.writeObject(obj)
      objectOutputStream.close
      stream.toByteArray
    }
  }
它的用法就像

val byteArray = QueryResult(events).serialize
那么对于去序列化,我有这个特性,可以通过companion类进行扩展

trait Deserializer[A] {
  private type resultType = A
  def deserialize(bytes: Array[Byte]): A = {
    val objectInputStream = new ObjectInputStream(
      new ByteArrayInputStream(bytes)
    )
    val value = objectInputStream.readObject.asInstanceOf[resultType]
    objectInputStream.close
    value
  }
}
你会像这样使用它吗

object QueryResult extends Deserializer[QueryResult]
然后您应该能够从这样的字节数组重构
QueryResult
的实例

val QueryResult: QueryResult = QueryResult.deserialize(byteArray)
问题是,这有时会导致如下错误

java.lang.ClassCastException: cannot assign instance of scala.collection.generic.DefaultSerializationProxy to field co.app.QueryResult.events of type scala.collection.immutable.List in instance of co.app.QueryResult
  at java.base/java.io.ObjectStreamClass$FieldReflector.setObjFieldValues(ObjectStreamClass.java:2205)
  at java.base/java.io.ObjectStreamClass$FieldReflector.checkObjectFieldValueTypes(ObjectStreamClass.java:2168)
  at java.base/java.io.ObjectStreamClass.checkObjFieldValueTypes(ObjectStreamClass.java:1422)
  at java.base/java.io.ObjectInputStream.defaultCheckFieldValues(ObjectInputStream.java:2450)
  at java.base/java.io.ObjectInputStream.readSerialData(ObjectInputStream.java:2357)
  at java.base/java.io.ObjectInputStream.readOrdinaryObject(ObjectInputStream.java:2166)
  at java.base/java.io.ObjectInputStream.readObject0(ObjectInputStream.java:1668)
  at java.base/java.io.ObjectInputStream.readObject(ObjectInputStream.java:482)
  at java.base/java.io.ObjectInputStream.readObject(ObjectInputStream.java:440)
  at co.app.Deserializer.deserialize(Types.scala:51)
  at co.app.Deserializer.deserialize$(Types.scala:47)
  at co.app.LocalStorage$QueryResults$.get(LocalStorage.scala:241)
  ... 36 elided


现在,当我说有时,我的意思是当我将代码组装到一个jar中并使用
java
cli运行它时,反序列化可以工作,但是当我试图通过
sbt test
sbt console
ammonite
执行该代码时,反序列化就会中断。你知道为什么在这种情况下它会崩溃吗?还有可能的修复建议吗?

你如何序列化你试图反序列化的对象?如果在同一执行中序列化然后反序列化(即类似于
反序列化(serialize(myObject))
),它是否有效?请注意,我不知道您的用例,但默认情况下,我不建议使用java序列化。你最好用一个专门的库来解决这个问题。@juh你的第一个问题的答案并不总是否定的。当我在一行上尝试serde时,同样的错误也会发生,但仅在某些情况下。当我从
java
cli运行jar时,代码运行良好。我更新了帖子,解释了我是如何进行序列化的。您可能是对的,切换到专用库可能是一种方法。如何序列化您尝试反序列化的对象?如果在同一执行中序列化然后反序列化(即类似于
反序列化(serialize(myObject))
),它是否有效?请注意,我不知道您的用例,但默认情况下,我不建议使用java序列化。你最好用一个专门的库来解决这个问题。@juh你的第一个问题的答案并不总是否定的。当我在一行上尝试serde时,同样的错误也会发生,但仅在某些情况下。当我从
java
cli运行jar时,代码运行良好。我更新了帖子,解释了我是如何进行序列化的。您可能是对的,切换到专用库可能是一个不错的选择。