Spark上有json4s的NotSerializableException
基本上,我必须使用Spark分析HDFS上的一些复杂JSON 我使用“for comprehensions”来(预)过滤JSON和“extract”方法 将json4s封装到case类中 这个很好用Spark上有json4s的NotSerializableException,json,scala,hdfs,apache-spark,json4s,Json,Scala,Hdfs,Apache Spark,Json4s,基本上,我必须使用Spark分析HDFS上的一些复杂JSON 我使用“for comprehensions”来(预)过滤JSON和“extract”方法 将json4s封装到case类中 这个很好用 def foo(rdd: RDD[String]) = { case class View(C: String,b: Option[Array[List[String]]], t: Time) case class Time($numberLong: String) implicit val f
def foo(rdd: RDD[String]) = {
case class View(C: String,b: Option[Array[List[String]]], t: Time)
case class Time($numberLong: String)
implicit val formats = DefaultFormats
rdd.map { jsonString =>
val jsonObj = parse(jsonString)
val listsOfView = for {
JObject(value) <- jsonObj
JField(("v"), JObject(views)) <- value
normalized <- views.map(x => (x._2))
} yield normalized
}
def foo(rdd:rdd[String])={
案例类视图(C:String,b:Option[Array[List[String]],t:Time)
案例课堂时间($numberLong:String)
隐式val格式=默认格式
rdd.map{jsonString=>
val jsonObj=parse(jsonString)
val listsOfView=for{
JObject(value)Spark序列化RDD转换上的闭包,并将这些闭包“发送”给Worker以供分布式执行。
这要求闭包中的所有代码(通常也包括包含对象中的代码)都应该是可序列化的
看着(该特征的伴生对象)的impl:
很明显,这个对象是不可序列化的,并且不能这样做。(ThreadLocal本身就是不可序列化的)
您似乎没有在代码中使用Date
类型,因此您可以删除这些类型吗
implicit val formats=DefaultFormats
或者用可序列化的东西替换DefaultFormats?这实际上已经被修复;JSON4S从3.3.0版开始是可序列化的:解决我的问题的是,我在rdd.foreach{}中使用了implicit val formats=DefaultFormats
loop。它解决了我的可序列化异常
以下是解决问题的代码片段:
case class rfId(rfId: String) {}
// ... some code here ...
rdd.foreach { record =>
val value = record.value()
// Bring in default date formats etc and makes json4s serializable
implicit val formats = DefaultFormats
val json = parse(value)
println(json.camelizeKeys.extract[rfId]) // Prints `rfId(ABC12345678)`
}
请参阅,但是JSON4S 3.3与任何Spark版本都不兼容,除非您对依赖项进行着色,因为二进制/运行时与包含Spark的JSON4S 3.2不兼容。
object DefaultFormats extends DefaultFormats {
val losslessDate = new ThreadLocal(new java.text.SimpleDateFormat("yyyy-MM-dd'T'HH:mm:ss.SSS'Z'"))
val UTC = TimeZone.getTimeZone("UTC")
}
case class rfId(rfId: String) {}
// ... some code here ...
rdd.foreach { record =>
val value = record.value()
// Bring in default date formats etc and makes json4s serializable
implicit val formats = DefaultFormats
val json = parse(value)
println(json.camelizeKeys.extract[rfId]) // Prints `rfId(ABC12345678)`
}