在独立/主从火花壳

时间:2016-03-08 00:37:14

标签: scala shell apache-spark spark-dataframe parquet

以下是我用于从Scala中的Parquet读取数据框的更大代码的片段。

case class COOMatrix(row: Seq[Long], col: Seq[Long], data: Seq[Double])

def buildMatrix(cooMatrixFields: DataFrame) = {

  val cooMatrices = cooMatrixFields map {
    case Row(r,c,d) => COOMatrix(r.asInstanceOf[Seq[Long]], c.asInstanceOf[Seq[Long]], d.asInstanceOf[Seq[Double]])
  }

  val matEntries = cooMatrices.zipWithIndex.flatMap {
    case (cooMat, matIndex) =>
      val rowOffset = cooMat.row.distinct.size
      val colOffset = cooMat.col.distinct.size

      val cooMatRowShifted = cooMat.row.map(rowEntry => rowEntry + rowOffset * matIndex)
      val cooMatColShifted = cooMat.col.map(colEntry => colEntry + colOffset * matIndex)

      (cooMatRowShifted, cooMatColShifted, cooMat.data).zipped.map {
        case (i, j, value) => MatrixEntry(i, j, value)
      }
  }

  new CoordinateMatrix(matEntries)
}


val C_entries = sqlContext.read.load(s"${dataBaseDir}/C.parquet")

val C = buildMatrix(C_entries)

我的代码在本地 spark上下文中运行时成功执行

独立群集上,一旦到达强制实际从Parquet读取的操作,相同的代码就会失败。 正确检索数据框架构:

C_entries: org.apache.spark.sql.DataFrame = [C_row: array<bigint>, C_col: array<bigint>, C_data: array<double>]

但执行者在执行此行val C = buildMatrix(C_entries)时崩溃,但有以下异常:

java.lang.ExceptionInInitializerError
    at $line39.$read$$iwC.<init>(<console>:7)
    at $line39.$read.<init>(<console>:61)
    at $line39.$read$.<init>(<console>:65)
    at $line39.$read$.<clinit>(<console>)
    at $line67.$read$$iwC.<init>(<console>:7)
    at $line67.$read.<init>(<console>:24)
    at $line67.$read$.<init>(<console>:28)
    at $line67.$read$.<clinit>(<console>)
    at $line68.$read$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$anonfun$3.apply(<console>:63)
    at $line68.$read$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$iwC$$anonfun$3.apply(<console>:62)
    at scala.collection.Iterator$$anon$11.next(Iterator.scala:328)
    at org.apache.spark.util.Utils$.getIteratorSize(Utils.scala:1597)
    at org.apache.spark.rdd.ZippedWithIndexRDD$$anonfun$2.apply(ZippedWithIndexRDD.scala:52)
    at org.apache.spark.rdd.ZippedWithIndexRDD$$anonfun$2.apply(ZippedWithIndexRDD.scala:52)
    at org.apache.spark.SparkContext$$anonfun$runJob$5.apply(SparkContext.scala:1858)
    at org.apache.spark.SparkContext$$anonfun$runJob$5.apply(SparkContext.scala:1858)
    at org.apache.spark.scheduler.ResultTask.runTask(ResultTask.scala:66)
    at org.apache.spark.scheduler.Task.run(Task.scala:89)
    at org.apache.spark.executor.Executor$TaskRunner.run(Executor.scala:213)
    at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1145)
    at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:615)
    at java.lang.Thread.run(Thread.java:745)
Caused by: java.lang.NullPointerException
    at $line4.$read$$iwC$$iwC.<init>(<console>:15)
    at $line4.$read$$iwC.<init>(<console>:24)
    at $line4.$read.<init>(<console>:26)
    at $line4.$read$.<init>(<console>:30)
    at $line4.$read$.<clinit>(<console>)
    ... 22 more

不确定它是否相关,但在增加日志详细程度时,我注意到了这个异常:

16/03/07 20:59:38 INFO GenerateUnsafeProjection: Code generated in 157.285464 ms
16/03/07 20:59:38 DEBUG ExecutorClassLoader: Did not load class org.apache.spark.sql.catalyst.expressions.GeneratedClass$SpecificUnsafeProjection from REPL class server at http://155.198.193.158:32862
java.lang.ClassNotFoundException: Class file not found at URL http://155.198.193.158:32862/org/apache/spark/sql/catalyst/expressions/GeneratedClass%24SpecificUnsafeProjection.class

我为独立群集尝试了不同的配置:

  • master,1 slave和spark-shell在我的笔记本电脑上运行
  • 主机和1个从机各自运行在不同的机器上,我的笔记本电脑上的spark-shell
  • 一台机器上的master和spark-shell,另一台机器上的1个slave

我已经开始使用默认属性,并且演变为更复杂的属性文件而没有更多成功:

spark.driver.memory                4g
spark.rpc=netty
spark.eventLog.enabled             true
spark.eventLog.dir                 file:///mnt/fastmp/spark_workdir/logs
spark.driver.extraJavaOptions      -Xmx20480m -XX:MaxPermSize=2048m -XX:ReservedCodeCacheSize=2048m
spark.shuffle.service.enabled      true
spark.shuffle.consolidateFiles     true
spark.sql.parquet.binaryAsString   true
spark.speculation                  false
spark.rpc.timeout                 1000
spark.rdd.compress true
spark.core.connection.ack.wait.timeout 600
spark.driver.maxResultSize         0
spark.task.maxFailures             3
spark.shuffle.io.maxRetries        3

我正在运行 spark-1.6.0-bin-hadoop2.6 的预建版本。 此部署中涉及 no HDFS ,所有Parquet文件都存储在所有计算机可用的共享装载(CephFS)上。

我怀疑这与底层文件系统有关,因为我的代码的另一部分在本地和独立模式下都会读取不同的Parquet文件。

1 个答案:

答案 0 :(得分:0)

TL; DR :将您的代码打包为 jar

出于记录目的,问题似乎与使用独立群集有关。

完全相同的代码可以正常使用这些设置:

  • spark-shell和master在同一台机器上
  • 在YARN(AWS EMR集群)上运行并从S3读取镶木地板文件

通过在独立设置的日志中进行更多挖掘,问题似乎与类服务器的此异常相关联:

INFO GenerateUnsafeProjection: Code generated in 157.285464 ms
DEBUG ExecutorClassLoader: Did not load class org.apache.spark.sql.catalyst.expressions.GeneratedClass$SpecificUnsafeProjection from REPL class server at http://155.198.193.158:32862
java.lang.ClassNotFoundException: Class file not found at URL http://155.198.193.158:32862/org/apache/spark/sql/catalyst/expressions/GeneratedClass%24SpecificUnsafeProjection.class

我的理解是spark-shell启动HTTP服务器( jetty ),以便将它从REPL中的代码生成的类提供给工作者。

就我而言,很多课程都成功提供(我甚至设法通过 telnet 检索一些课程)。但是,类服务器无法找到类GeneratedClass(及其所有内部类)。

日志中出现的典型错误消息是:

DEBUG Server: RESPONSE /org/apache/spark/sql/catalyst/expressions/GeneratedClass.class  404 handled=true

我的想法是它在同一服务器上使用master和spark-shell,因为它们在同一个JVM中运行,因此即使HTTP传输失败也可以找到类。

我到目前为止唯一成功的解决方案是构建jar包并使用--jars的{​​{1}}选项或将其作为参数传递给spark-shell