为什么在Kafka主题中没有可用记录时打开StreamingQueryStatus.isDataAvailable?

时间:2017-11-13 05:52:53

标签: scala apache-spark apache-kafka spark-structured-streaming

我必须停止Spark结构化流式传输查询。首先,我检查状态是否存在Kafka中可用的任何数据进行处理。如果是,则处理它然后停止查询。

if (query.status.isDataAvailable) {
                    query.processAllAvailable()
                  }
query.stop()

在Jacek Laskowski的建议之后,我修改了实施。 我有流式查询列表,

streamingQueryList.foreach{query =>
query.stop()
}

每次停止查询后,都会抛出以下异常:

java.lang.InterruptedException
    at java.util.concurrent.locks.AbstractQueuedSynchronizer.doAcquireSharedInterruptibly(AbstractQueuedSynchronizer.java:998)
    at java.util.concurrent.locks.AbstractQueuedSynchronizer.acquireSharedInterruptibly(AbstractQueuedSynchronizer.java:1304)
    at scala.concurrent.impl.Promise$DefaultPromise.tryAwait(Promise.scala:202)
    at scala.concurrent.impl.Promise$DefaultPromise.ready(Promise.scala:218)
    at scala.concurrent.impl.Promise$DefaultPromise.ready(Promise.scala:153)
    at org.apache.spark.util.ThreadUtils$.awaitReady(ThreadUtils.scala:222)
    at org.apache.spark.scheduler.DAGScheduler.runJob(DAGScheduler.scala:621)
    at org.apache.spark.SparkContext.runJob(SparkContext.scala:2022)
    at org.apache.spark.sql.execution.datasources.FileFormatWriter$$anonfun$write$1.apply$mcV$sp(FileFormatWriter.scala:179)
    at org.apache.spark.sql.execution.datasources.FileFormatWriter$$anonfun$write$1.apply(FileFormatWriter.scala:164)
    at org.apache.spark.sql.execution.datasources.FileFormatWriter$$anonfun$write$1.apply(FileFormatWriter.scala:164)
    at org.apache.spark.sql.execution.SQLExecution$.withNewExecutionId(SQLExecution.scala:65)
    at org.apache.spark.sql.execution.datasources.FileFormatWriter$.write(FileFormatWriter.scala:164)
    at org.apache.spark.sql.execution.streaming.FileStreamSink.addBatch(FileStreamSink.scala:123)
    at org.apache.spark.

出于调试目的,我打印了recentProgress查询,以了解当前主题从哪里读取火花。我使用控制台消费者检查了主题,Kafka中没有数据,但query.status.isDataAvailable打印为true。即使recentProgress为空,它仍在等待数据处理。由于它无限期等待。

1 个答案:

答案 0 :(得分:1)

我不确定isDataAvailable给出true的原因,但processAllAvailable为您提供了与if (query.status.isDataAvailable)阻止相关的解决方案。< / p>

  

processAllAvailable 阻止,直到源中的所有可用数据都已处理并提交到接收器。

那是你的用例,不是吗?

请注意&#34;此方法用于测试。&#34; &#34;此方法可能会永久阻止&#34; (引用processAllAvailable)的scaladoc。

您应该使用awaitTermination来阻止主线程(因此您的流媒体应用程序已启动并运行)和stop查询(及其后台线程),方便您从另一个&#34 ;监测&#34;线程。

  

awaitTermination()等待query.stop()或异常终止此查询。如果查询因异常而终止,则抛出异常。