主线程休眠小于1000时无法生成消息

时间:2017-06-28 12:43:19

标签: apache-kafka kafka-consumer-api kafka-producer-api

当我使用Kafka的Java API时,如果我让主线程的睡眠时间少于2000ns,它就无法生成任何消息。我真的想知道为什么会这样?

这是我的制片人:

public class Producer {
    private final KafkaProducer<String, String> producer;
    private final String topic;

    public Producer(String topic, String[] args) {
        //......
        //......
        producer = new KafkaProducer<>(props);
        this.topic = topic;
    }

    public void producerMsg() throws InterruptedException {
        String data = "Apache Storm is a free and open source distributed";
        data = data.replaceAll("[\\pP‘’“”]", "");
        String[] words = data.split(" ");
        Random _rand = new Random();

        Random rnd = new Random();
        int events = 10;
        for (long nEvents = 0; nEvents < events; nEvents++) {
            long runtime = new Date().getTime();
            int lastIPnum = rnd.nextInt(255);
            String ip = "192.168.2." + lastIPnum;
            String msg = words[_rand.nextInt(words.length)];
            try {
                producer.send(new ProducerRecord<>(topic, ip, msg));
                System.out.println("Sent message: (" + ip + ", " + msg + ")");
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }

    public static void main(String[] args) throws InterruptedException {
        Producer producer = new Producer(Constants.TOPIC, args);
        producer.producerMsg();
        //If I write Thread.sleep(1000),It will not work!!!!!!!!!!!!!!!!!!!!
        Thread.sleep(2000);
    }
}

欣赏

1 个答案:

答案 0 :(得分:0)

您可以显示用于配置Producer的道具吗?我只是猜测它可能......

在producerMsg()中,您使用异步方式来使用生成器,所以只需要生成器.send(),这意味着将消息放入内部缓冲区以生成稍后将发送的批处理。生产者有一个内部线程从缓冲区获取并发送批处理。也许只有1000毫秒不足以达到生产者真正发送消息的条件(参见batch.size和linger.ms),主应用程序结束,生产者死亡而不发送消息。给它更多的时间(2000毫秒),它的工作原理。顺便说一句,我没有尝试过代码。

所以理由似乎是你的:

props.put("linger.ms", 1000);

与你的睡眠相匹配。因此,生产者将在1000毫秒后开始发送消息,因为批次尚未满(batch.size为16 MB)。同时,主线程在休眠1秒后结束,并且生产者不发送消息。你必须使用较低的linger.ms时间。