簡體   English   中英

spark job(scala)將類型Date寫入Cassandra

[英]spark job (scala) write type Date to Cassandra

我正在使用DSE 5.1(Spark 2.0.2.6和cassandra 3.10.0.1652)

我的Cassandra表:

CREATE TABLE ks.tbl (
   dk int,
   date date,
   ck int,
   val int,
PRIMARY KEY (dk, date, ck)
) WITH CLUSTERING ORDER BY (date DESC, ck ASC);

具有以下數據:

 dk | date       | ck | val
----+------------+----+-----
  1 | 2017-01-01 |  1 | 100
  1 | 2017-01-01 |  2 | 200

我的代碼必須讀取此數據並編寫相同的內容,但是要有昨天的日期(它可以成功編譯):

package com.datastax.spark.example

import com.datastax.spark.connector._
import com.datastax.spark.connector.cql.CassandraConnector
import org.apache.spark.sql.hive.HiveContext
import org.apache.spark.{SparkConf, SparkContext}
import com.github.nscala_time.time._
import com.github.nscala_time.time.Imports._

object test extends App {

  val conf = new SparkConf().setAppName("DSE calculus app TEST")
  val sc = new SparkContext(conf)

  val yesterday= (DateTime.now - 1.days).toString(StaticDateTimeFormat.forPattern("yyyy-MM-dd"))

  val tbl = sc.cassandraTable("ks","tbl").select("dk","date","ck","val").where("dk=1")

  tbl.map(row => (row.getInt("dk"),yesterday,row.getInt("ck"),row.getInt("val"))).saveToCassandra("ks","tbl")

  sc.stop()
  sys.exit(0)
}

當我運行此應用程序時:

dse spark-submit --class com.datastax.spark.example.test test-assembly-0.1.jar

無法正確寫入Cassandra。 似乎日期變量未正確插入地圖中。 我得到的錯誤是:

Error:
WARN  2017-05-08 22:23:16,472 org.apache.spark.scheduler.TaskSetManager: Lost task 0.0 in stage 0.0 (TID 0, <IP of one of my nodes>): java.io.IOException: Failed to write statements to ks.tbl.
        at com.datastax.spark.connector.writer.TableWriter$$anonfun$writeInternal$1.apply(TableWriter.scala:207)
        at com.datastax.spark.connector.writer.TableWriter$$anonfun$writeInternal$1.apply(TableWriter.scala:175)
        at com.datastax.spark.connector.cql.CassandraConnector$$anonfun$withSessionDo$1.apply(CassandraConnector.scala:112)
        at com.datastax.spark.connector.cql.CassandraConnector$$anonfun$withSessionDo$1.apply(CassandraConnector.scala:111)
        at com.datastax.spark.connector.cql.CassandraConnector.closeResourceAfterUse(CassandraConnector.scala:145)
        at com.datastax.spark.connector.cql.CassandraConnector.withSessionDo(CassandraConnector.scala:111)
        at com.datastax.spark.connector.writer.TableWriter.writeInternal(TableWriter.scala:175)
        at com.datastax.spark.connector.writer.TableWriter.insert(TableWriter.scala:162)
        at com.datastax.spark.connector.writer.TableWriter.write(TableWriter.scala:149)
        at com.datastax.spark.connector.RDDFunctions$$anonfun$saveToCassandra$1.apply(RDDFunctions.scala:36)
        at com.datastax.spark.connector.RDDFunctions$$anonfun$saveToCassandra$1.apply(RDDFunctions.scala:36)
        at org.apache.spark.scheduler.ResultTask.runTask(ResultTask.scala:70)
        at org.apache.spark.scheduler.Task.run(Task.scala:86)
        at org.apache.spark.executor.Executor$TaskRunner.run(Executor.scala:274)
        at java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1142)
        at java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:617)
        at java.lang.Thread.run(Thread.java:748)

但是,當我按如下所示直接在map語句中插入日期(字符串)時,代碼確實正確插入了數據:

tbl.map(row => (row.getInt("dk"),"2017-02-02",row.getInt("ck"),row.getInt("val"))).saveToCassandra("ks","tbl")

如果我將昨天設置為整數(自紀元以來的天數),它也可以正確插入數據。 這將是最佳選擇,但不能使“昨天”以這種方式運行

編輯:實際上,這不能正確插入數據。 無論我將“昨天”設置為1還是1億,它總是插入紀元('1970-01-01)

失敗的代碼可以正常運行,就像我在DSE Spark控制台中所期望的那樣。

我只是不知道我在做什么錯。 歡迎任何幫助。

EDIT2: 准分子0 stderr日志確實表明它試圖在列日期中插入Null值,這顯然是不可能的,因為它是一個群集列。

在為Spark Job編寫代碼時,重要的是要意識到何時設置了特定變量以及何時對其進行了序列化。 讓我們來看看App trait文檔中的注釋

注意事項

應該注意的是,此特性是使用DelayedInit功能實現的,這意味着在執行main方法之前,不會初始化對象的字段。

這意味着在實際運行代碼時,可能不會在執行程序上初始化對App主體中使用的變量的引用。

我的猜測是您編寫的lambda包含對val的引用,該引用在App類的Delayed init部分中初始化。 這意味着未運行Main方法的執行程序上的代碼的序列化版本將獲得值的未初始​​化版本(空)。

將常量切換為lazy val (或將其移動到單獨的對象或類中)將通過確保值是遠程初始化(惰性val)或簡單地序列化初始化(單獨的類/對象)來解決此問題。

我想我知道你的問題是什么。
您可能會看到完整的日志文件。 您只需附加一部分...
今天有類似的錯誤,當使用replication_factor創建密鑰空間時:3當我只有一個cassandra實例時。

所以我改變它,問題就解決了。

ALTER KEYSPACE "some_keyspace_name" WITH REPLICATION =
  { 'class' : 'SimpleStrategy', 'replication_factor' : 1 };

這是我的error.log文件

日志的重要部分:

Logging.scala[logError]:72) - Failed to execute: com.datastax.spark.connector.writer.RichBoundStatement@4746499f
com.datastax.driver.core.exceptions.UnavailableException: Not enough replicas available for query at consistency LOCAL_QUORUM (2 required but only 1 alive)

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM