作为Apache Flink的新手,并以流程处理框架的一般方式,我有几个问题,尤其是并行性问题。
首先这是我的代码:
object KafkaConsuming {
def main(args: Array[String]) {
// **** CONFIGURATION & PARAMETERS ****
val params: ParameterTool = ParameterTool.fromArgs(args)
val env = StreamExecutionEnvironment.getExecutionEnvironment
env.setParallelism(8)
env.getConfig.setGlobalJobParameters(params)
// **** Kafka CONNECTION ****
val properties = new Properties();
properties.setProperty("bootstrap.servers", params.get("server"));
// **** Get KAFKA source ****
val stream: DataStream[String] = env.addSource(new FlinkKafkaConsumer010[String](params.get("topic"), new SimpleStringSchema(), properties))
// **** PROCESSING ****
val logs: DataStream[MinifiedLog] = stream.map(x => LogParser2.parse(x))
val sessions = logs.map { x => (x.timestamp, x.bytesSent, 1l, 1)}
val sessionCnt: DataStream[(Long, Long, Long, Int)] = sessions
.keyBy(3).window(TumblingProcessingTimeWindows.of(Time.seconds(10)))
.reduce( (x: (Long, Long, Long, Int), y: (Long, Long, Long, Int)) => (x._1, x._2 + y._2, x._3 + y._3, x._4))
.map { z => (z._1, z._2 / 10, z._3 / 10, z._4)}
// **** OUTPUT ****
val output: DataStream[String] = sessionCnt.map(x => (x.toString() + "\n"))
output.writeToSocket("X.X.X.X", 3333, new SimpleStringSchema)
env.execute("Kafka consuming")
}
}
当我想在我的集群上运行它时,我运行以下命令:
./bin/flink run -m yarn-cluster -yn 8 /directories/myjar.jar --server X.X.X.X --topic mytopic
这很好用。现在我的问题是:
我在Flink Web UI中得到了这个:
1。为什么收到的记录总是发送的记录的一半,而数据量是相同的?
然后,如果我进入窗口的细节:
显然所有的过程都在我的奴隶4和一个线程上完成!源头也是如此。只有一个线程用于接收数据。
2。为什么Flink没有使用该步骤的所有线程?
我注意到源,窗口和接收器由不同的slave处理,但我仍然希望该过程在我的集群上并行完成。
我在这篇文章中读到:https://stackoverflow.com/a/32329010/5035392如果Kafka源只有一个分区(这是我的情况),Flink就无法在不同的节点上共享任务。但是,我的窗口处理应该能够做到吗?
如果这些都是微不足道的问题我很抱歉。我不确定我做错了是用Flink还是我的群集配置。谢谢。
答案 0 :(得分:1)
广告。 2同一个密钥的所有值都在一个TaskManager
上处理。
在您的情况下,sessions.keyBy(3)
流的每个元素都具有相同的键 - > 1
因此所有计算都在一个任务槽中执行。