我发现这段代码成功读取了kafka主题并在屏幕上打印了每条消息。我想扩展它以对字符串执行其他操作,而不是仅仅在屏幕上打印。为此,我想了解迭代消息的while循环中发生了什么。 it.hasNext()做什么?它会查找下一条消息或新消息列表。什么时候它会离开这个循环?
import kafka.consumer.ConsumerIterator;
import kafka.consumer.KafkaStream;
public class ConsumerTest implements Runnable {
private KafkaStream m_stream;
private int m_threadNumber;
public ConsumerTest(KafkaStream a_stream, int a_threadNumber) {
m_threadNumber = a_threadNumber;
m_stream = a_stream;
}
public void run() {
**ConsumerIterator<byte[], byte[]> it = m_stream.iterator();
while (it.hasNext())**
System.out.println("Thread " + m_threadNumber + ": " + new String(it.next().message()));
System.out.println("Shutting down Thread: " + m_threadNumber);
}
}
答案 0 :(得分:1)
Kafka迭代器.hasNext()方法通常总是返回true!因此,您永远不会在标准操作中脱离循环。但是,如果发生异常,则可能返回false并停止提取。
因此,一般情况下,您将进入循环,并且对it.next()的调用实际上是阻塞,直到消息被消费,在这种情况下它将被返回。
答案 1 :(得分:1)
即使这是一个老问题,kafka 0.8可能很少用于生产,而kafka 0.10提供了更丰富的API,我想补充一点,ConsumerIterator的方法hasNext()
是一个等待消息的阻塞操作。
因此,如果您希望使用使用者阅读之前发送的所有数据并在完成后返回,则可以将属性"consumer.timeout.ms"
设置为例如100
导致hasNext()
在阻止时间超过超时时抛出ConsumerTimeoutException
。
在你的代码中,只需捕获while循环中的异常:
try {
while (it.hasNext()) {
String message = new String(it.next().message()));
// do sth with message
}
} catch {
case t: ConsumerTimeoutException => // empty
} finally {
// close your consumer
}