当前位置: 首页 > 知识库问答 >
问题:

数据源用完时如何停止火花流

尤祖鹤
2023-03-14

我有一个spark流媒体作业,它每5秒钟读取一次Kafka,对传入的数据进行一些转换,然后写入文件系统。

这实际上不需要是一个流式作业,实际上,我只想每天运行一次,将消息排入文件系统。但我不知道如何停止这项工作。

如果我向streamingContext传递超时。等待终止,它不会停止进程,它所做的只是导致进程在流上迭代时产生错误(请参见下面的错误)

实现我所要做的事情的最佳方式是什么

这是Python上的Spark 1.6

编辑:

多亏了@marios,解决方案如下:

ssc.start()
ssc.awaitTermination(10)
ssc.stop()

在停止之前运行脚本十秒钟。

简化代码:

conf = SparkConf().setAppName("Vehicle Data Consolidator").set('spark.files.overwrite','true')
sc = SparkContext(conf=conf)
ssc = StreamingContext(sc, 5)
stream = KafkaUtils.createStream(
    ssc,
    kafkaParams["zookeeper.connect"],
    "vehicle-data-importer",
    topicPartitions,
    kafkaParams)

stream.saveAsTextFiles('stream-output/kafka-vehicle-data')

ssc.start()
ssc.awaitTermination(10)

错误:

16/01/29 15:05:44 INFO BlockManagerInfo: Added input-0-1454097944200 in memory on localhost:58960 (size: 3.0 MB, free: 48.1 MB)
16/01/29 15:05:44 WARN BlockManager: Block input-0-1454097944200 replicated to only 0 peer(s) instead of 1 peers
16/01/29 15:05:44 INFO BlockGenerator: Pushed block input-0-1454097944200
16/01/29 15:05:45 ERROR JobScheduler: Error generating jobs for time 1454097945000 ms
py4j.Py4JException: Cannot obtain a new communication channel
    at py4j.CallbackClient.sendCommand(CallbackClient.java:232)
    at py4j.reflection.PythonProxyHandler.invoke(PythonProxyHandler.java:111)
    at com.sun.proxy.$Proxy14.call(Unknown Source)
    at org.apache.spark.streaming.api.python.TransformFunction.callPythonTransformFunction(PythonDStream.scala:92)
    at org.apache.spark.streaming.api.python.TransformFunction.apply(PythonDStream.scala:78)
    at org.apache.spark.streaming.api.python.PythonTransformedDStream.compute(PythonDStream.scala:230)
    at org.apache.spark.streaming.dstream.DStream$$anonfun$getOrCompute$1$$anonfun$1$$anonfun$apply$7.apply(DStream.scala:352)
    at org.apache.spark.streaming.dstream.DStream$$anonfun$getOrCompute$1$$anonfun$1$$anonfun$apply$7.apply(DStream.scala:352)
    at scala.util.DynamicVariable.withValue(DynamicVariable.scala:57)
    at org.apache.spark.streaming.dstream.DStream$$anonfun$getOrCompute$1$$anonfun$1.apply(DStream.scala:351)
    at org.apache.spark.streaming.dstream.DStream$$anonfun$getOrCompute$1$$anonfun$1.apply(DStream.scala:351)
    at org.apache.spark.streaming.dstream.DStream.createRDDWithLocalProperties(DStream.scala:426)
    at org.apache.spark.streaming.dstream.DStream$$anonfun$getOrCompute$1.apply(DStream.scala:346)
    at org.apache.spark.streaming.dstream.DStream$$anonfun$getOrCompute$1.apply(DStream.scala:344)
    at scala.Option.orElse(Option.scala:257)
    at org.apache.spark.streaming.dstream.DStream.getOrCompute(DStream.scala:341)
    at org.apache.spark.streaming.dstream.ForEachDStream.generateJob(ForEachDStream.scala:47)
    at org.apache.spark.streaming.DStreamGraph$$anonfun$1.apply(DStreamGraph.scala:115)
    at org.apache.spark.streaming.DStreamGraph$$anonfun$1.apply(DStreamGraph.scala:114)
    at scala.collection.TraversableLike$$anonfun$flatMap$1.apply(TraversableLike.scala:251)
    at scala.collection.TraversableLike$$anonfun$flatMap$1.apply(TraversableLike.scala:251)
    at scala.collection.mutable.ResizableArray$class.foreach(ResizableArray.scala:59)
    at scala.collection.mutable.ArrayBuffer.foreach(ArrayBuffer.scala:47)
    at scala.collection.TraversableLike$class.flatMap(TraversableLike.scala:251)
    at scala.collection.AbstractTraversable.flatMap(Traversable.scala:105)
    at org.apache.spark.streaming.DStreamGraph.generateJobs(DStreamGraph.scala:114)
    at org.apache.spark.streaming.scheduler.JobGenerator$$anonfun$3.apply(JobGenerator.scala:248)
    at org.apache.spark.streaming.scheduler.JobGenerator$$anonfun$3.apply(JobGenerator.scala:246)
    at scala.util.Try$.apply(Try.scala:161)
    at org.apache.spark.streaming.scheduler.JobGenerator.generateJobs(JobGenerator.scala:246)
    at org.apache.spark.streaming.scheduler.JobGenerator.org$apache$spark$streaming$scheduler$JobGenerator$$processEvent(JobGenerator.scala:181)
    at org.apache.spark.streaming.scheduler.JobGenerator$$anon$1.onReceive(JobGenerator.scala:87)
    at org.apache.spark.streaming.scheduler.JobGenerator$$anon$1.onReceive(JobGenerator.scala:86)
    at org.apache.spark.util.EventLoop$$anon$1.run(EventLoop.scala:48)
16/01/29 15:05:45 INFO MemoryStore: Block input-0-1454097944800 stored as bytes in memory (estimated size 3.0 MB, free 466.1 MB)
16/01/29 15:05:45 INFO BlockManagerInfo: Added input-0-1454097944800 in memory on localhost:58960 (size: 3.0 MB, free: 45.1 MB)

共有3个答案

慕高格
2023-03-14

这里的问题从1.6开始,在与Dstream处理线程相同的线程中的ssc.stop调用将创建死锁,因为Stop将等待轮询器线程完成创建deadlock.sp另一个线程的停止调用

朱皓
2023-03-14

有一个try Kafka“consumer.timeout.ms”参数,它将优雅地结束KafkaReceiver。(来自Kafka0.8配置)

如果在指定间隔之后没有消息可供使用,则向消费者抛出超时异常

HDF = KafkaUtils.createStream(ssc, topics={strLoc : 1}, kafkaParams={"consumer.timeout.ms":"20000" }, zkQuorum='xxx:2181', groupId='xxx-consumer-group')

在当前流式执行中,您将无法接收任何新的kafka消息,并且始终获得空RDD
并检查DSteam中空RDD的计数。foreachRDD(函数)。如果继续得到空RDD,请终止流执行。

通寂离
2023-03-14

似乎正确的调用方法是waitTerminationOrTimeout(self, timeout)。

我不确定它是否也会停止流式处理上下文。所以也许你可以打电话给ssc。超时结束后立即停止()。

ssc.start()
ssc.awaitTerminationOrTimeout(10)
ssc.stop()

注意:在这里查看类似的问题。

 类似资料:
  • 我有一个 Spark 流式处理作业,它读取 Cosmos 更改源数据,如下所示,在具有 DBR 8.2 的数据砖集群中运行。 虽然作业正常工作,但偶尔,流会突然停止,并且在log4j输出中出现以下循环。重新启动作业将处理“待办事项”中的所有数据。以前有人经历过这样的事情吗?我不确定是什么原因造成的。有什么想法吗?

  • 在spark streaming中,流数据将由在worker上运行的接收器接收。数据将被周期性地推入数据块中,接收者将向驱动程序发送receivedBlockInfo。我想知道这会引发流将块分发到集群吗?(换句话说,它会使用分发存储策略吗)。如果它不在集群中分发数据,如何保证工作负载平衡?(我们有一个10s节点的集群,但只有几个接收器)

  • 在PySpark中或者至少在Scala中,Apache Spark中是否有与Pandas Melt函数等价的函数? 到目前为止,我一直在用Python运行一个示例数据集,现在我想对整个数据集使用Spark。

  • 类似的问题,但没有足够的观点来评论。 根据最新的Spark文档,< code>udf有两种不同的用法,一种用于SQL,另一种用于DataFrame。我找到了许多关于如何在sql中使用< code>udf的例子,但是还没有找到任何关于如何在数据帧中直接使用< code>udf的例子。 o.p.针对上述问题提供的解决方案使用,这是,将根据Spark Java API文档在Spark 2.0中删除。在那

  • 当我尝试将数据帧写入Hive Parket分区表时 它将在HDFS中创建大量块,每个块只有少量数据。 我了解它是如何进行的,因为每个 spark 子任务将创建一个块,然后将数据写入其中。 我也理解,块数会提高Hadoop的性能,但达到阈值后也会降低性能。 如果我想自动设置数字分区,有人有一个好主意吗?

  • 我有两个包含两列的DataFrames > <code>df1</code>,带有架构<code>(键1:长,值)</code> <code>df2</code>,带架构<code>(键2:数组[Long],值)</code> 我需要在键列上连接这些DataFrames(查找和中的值之间的匹配值)。但问题是它们的类型不同。有办法做到这一点吗?