转自:http://shift-alt-ctrl.iteye.com/blog/1930791
kafka作为分布式日志收集或系统监控服务,我们有必要在合适的场合使用它。kafka的部署包括zookeeper环境/kafka环境,同时还需要进行一些配置操作.接下来介绍如何使用kafka.
我们使用3个zookeeper实例构建zk集群,使用2个kafka broker构建kafka集群.
其中kafka为0.8V,zookeeper为3.4.5V
一.Zookeeper集群构建
我们有3个zk实例,分别为zk-0,zk-1,zk-2;如果你仅仅是测试使用,可以使用1个zk实例.
1) zk-0
调整配置文件:
- clientPort=2181
- server.0=127.0.0.1:2888:3888
- server.1=127.0.0.1:2889:3889
- server.2=127.0.0.1:2890:3890
- ##只需要修改上述配置,其他配置保留默认值
启动zookeeper
- ./zkServer.sh start
2) zk-1
调整配置文件(其他配置和zk-0一只):
- clientPort=2182
- ##只需要修改上述配置,其他配置保留默认值
启动zookeeper
- ./zkServer.sh start
3) zk-2
调整配置文件(其他配置和zk-0一只):
- clientPort=2183
- ##只需要修改上述配置,其他配置保留默认值
启动zookeeper
- ./zkServer.sh start
二. Kafka集群构建
因为Broker配置文件涉及到zookeeper的相关约定,因此我们先展示broker配置文件.我们使用2个kafka broker来构建这个集群环境,分别为kafka-0,kafka-1.
1) kafka-0
在config目录下修改配置文件为:
- broker.id=0
- port=9092
- num.network.threads=2
- num.io.threads=2
- socket.send.buffer.bytes=1048576
- socket.receive.buffer.bytes=1048576
- socket.request.max.bytes=104857600
- log.dir=./logs
- num.partitions=2
- log.flush.interval.messages=10000
- log.flush.interval.ms=1000
- log.retention.hours=168
- #log.retention.bytes=1073741824
- log.segment.bytes=536870912
- ##replication机制,让每个topic的partitions在kafka-cluster中备份2个
- ##用来提高cluster的容错能力..
- default.replication.factor=1
- log.cleanup.interval.mins=10
- zookeeper.connect=127.0.0.1:2181,127.0.0.1:2182,127.0.0.1:2183
- zookeeper.connection.timeout.ms=1000000
因为kafka用scala语言编写,因此运行kafka需要首先准备scala相关环境。
- > cd kafka-0
- > ./sbt update
- > ./sbt package
- > ./sbt assembly-package-dependency
其中最后一条指令执行有可能出现异常,暂且不管。 启动kafka broker:
- > JMS_PORT=9997 bin/kafka-server-start.sh config/server.properties &
因为zookeeper环境已经正常运行了,我们无需通过kafka来挂载启动zookeeper.如果你的一台机器上部署了多个kafka broker,你需要声明JMS_PORT.
2) kafka-1
- broker.id=1
- port=9093
- ##其他配置和kafka-0保持一致
然后和kafka-0一样执行打包命令,然后启动此broker.
- > JMS_PORT=9998 bin/kafka-server-start.sh config/server.properties &
仍然可以通过如下指令查看topic的"partition"/"replicas"的分布和存活情况.
- > bin/kafka-list-topic.sh --zookeeper localhost:2181
- topic: my-replicated-topic partition: 0 leader: 2 replicas: 1,2,0 isr: 2
- topic: test partition: 0 leader: 0 replicas: 0 isr: 0
到目前为止环境已经OK了,那我们就开始展示编程实例吧。[配置参数详解]
三.项目准备
项目基于maven构建,不得不说kafka java客户端实在是太糟糕了;构建环境会遇到很多麻烦。建议参考如下pom.xml;其中各个依赖包必须版本协调一致。如果kafka client的版本和kafka server的版本不一致,将会有很多异常,比如"broker id not exists"等;因为kafka从0.7升级到0.8之后(正名为2.8.0),client与server通讯的protocol已经改变.
- <dependencies>
- <dependency>
- <groupId>log4j</groupId>
- <artifactId>log4j</artifactId>
- <version>1.2.14</version>
- </dependency>
- <dependency>
- <groupId>org.apache.kafka</groupId>
- <artifactId>kafka_2.8.2</artifactId>
- <version>0.8.0</version>
- <exclusions>
- <exclusion>
- <groupId>log4j</groupId>
- <artifactId>log4j</artifactId>
- </exclusion>
- </exclusions>
- </dependency>
- <dependency>
- <groupId>org.scala-lang</groupId>
- <artifactId>scala-library</artifactId>
- <version>2.8.2</version>
- </dependency>
- <dependency>
- <groupId>com.yammer.metrics</groupId>
- <artifactId>metrics-core</artifactId>
- <version>2.2.0</version>
- </dependency>
- <dependency>
- <groupId>com.101tec</groupId>
- <artifactId>zkclient</artifactId>
- <version>0.3</version>
- </dependency>
- </dependencies>
四.Producer端代码
1) producer.properties文件:此文件放在/resources目录下
- #partitioner.class=
- ##broker列表可以为kafka server的子集,因为producer需要从broker中获取metadata
- ##尽管每个broker都可以提供metadata,此处还是建议,将所有broker都列举出来
- ##此值,我们可以在spring中注入过来
- ##metadata.broker.list=127.0.0.1:9092,127.0.0.1:9093
- ##,127.0.0.1:9093
- ##同步,建议为async
- producer.type=sync
- compression.codec=0
- serializer.class=kafka.serializer.StringEncoder
- ##在producer.type=async时有效
- #batch.num.messages=100
2) KafkaProducerClient.java代码样例
- import java.util.ArrayList;
- import java.util.Collection;
- import java.util.List;
- import java.util.Properties;
- import kafka.javaapi.producer.Producer;
- import kafka.producer.KeyedMessage;
- import kafka.producer.ProducerConfig;
- /**
- * User: guanqing-liu
- */
- public class KafkaProducerClient {
- private Producer<String, String> inner;
- private String brokerList;//for metadata discovery,spring setter
- private String location = "kafka-producer.properties";//spring setter
- private String defaultTopic;//spring setter
- public void setBrokerList(String brokerList) {
- this.brokerList = brokerList;
- }
- public void setLocation(String location) {
- this.location = location;
- }
- public void setDefaultTopic(String defaultTopic) {
- this.defaultTopic = defaultTopic;
- }
- public KafkaProducerClient(){}
- public void init() throws Exception {
- Properties properties = new Properties();
- properties.load(Thread.currentThread().getContextClassLoader().getResourceAsStream(location));
- if(brokerList != null) {
- properties.put("metadata.broker.list", brokerList);
- }
- ProducerConfig config = new ProducerConfig(properties);
- inner = new Producer<String, String>(config);
- }
- public void send(String message){
- send(defaultTopic,message);
- }
- public void send(Collection<String> messages){
- send(defaultTopic,messages);
- }
- public void send(String topicName, String message) {
- if (topicName == null || message == null) {
- return;
- }
- KeyedMessage<String, String> km = new KeyedMessage<String, String>(topicName,message);
- inner.send(km);
- }
- public void send(String topicName, Collection<String> messages) {
- if (topicName == null || messages == null) {
- return;
- }
- if (messages.isEmpty()) {
- return;
- }
- List<KeyedMessage<String, String>> kms = new ArrayList<KeyedMessage<String, String>>();
- int i= 0;
- for (String entry : messages) {
- KeyedMessage<String, String> km = new KeyedMessage<String, String>(topicName,entry);
- kms.add(km);
- i++;
- if(i % 20 == 0){
- inner.send(kms);
- kms.clear();
- }
- }
- if(!kms.isEmpty()){
- inner.send(kms);
- }
- }
- public void close() {
- inner.close();
- }
- /**
- * @param args
- */
- public static void main(String[] args) {
- KafkaProducerClient producer = null;
- try {
- producer = new KafkaProducerClient();
- //producer.setBrokerList("");
- int i = 0;
- while (true) {
- producer.send("test-topic", "this is a sample" + i);
- i++;
- Thread.sleep(2000);
- }
- } catch (Exception e) {
- e.printStackTrace();
- } finally {
- if (producer != null) {
- producer.close();
- }
- }
- }
- }
3) spring配置
- <bean id="kafkaProducerClient" class="com.test.kafka.KafkaProducerClient" init-method="init" destroy-method="close">
- <property name="zkConnect" value="${zookeeper_cluster}"></property>
- <property name="defaultTopic" value="${kafka_topic}"></property>
- </bean>
五.Consumer端
1) consumer.properties:文件位于/resources目录下
- ## 此值可以配置,也可以通过spring注入
- ##zookeeper.connect=127.0.0.1:2181,127.0.0.1:2182,127.0.0.1:2183
- ##,127.0.0.1:2182,127.0.0.1:2183
- # timeout in ms for connecting to zookeeper
- zookeeper.connectiontimeout.ms=1000000
- #consumer group id
- group.id=test-group
- #consumer timeout
- #consumer.timeout.ms=5000
- auto.commit.enable=true
- auto.commit.interval.ms=60000
2) KafkaConsumerClient.java代码样例
- package com.test.kafka;
- import java.nio.ByteBuffer;
- import java.nio.CharBuffer;
- import java.nio.charset.Charset;
- import java.util.HashMap;
- import java.util.List;
- import java.util.Map;
- import java.util.Properties;
- import java.util.concurrent.ExecutorService;
- import java.util.concurrent.Executors;
- import kafka.consumer.Consumer;
- import kafka.consumer.ConsumerConfig;
- import kafka.consumer.ConsumerIterator;
- import kafka.consumer.KafkaStream;
- import kafka.javaapi.consumer.ConsumerConnector;
- import kafka.message.Message;
- import kafka.message.MessageAndMetadata;
- /**
- * User: guanqing-liu
- */
- public class KafkaConsumerClient {
- private String groupid; //can be setting by spring
- private String zkConnect;//can be setting by spring
- private String location = "kafka-consumer.properties";//配置文件位置
- private String topic;
- private int partitionsNum = 1;
- private MessageExecutor executor; //message listener
- private ExecutorService threadPool;
- private ConsumerConnector connector;
- private Charset charset = Charset.forName("utf8");
- public void setGroupid(String groupid) {
- this.groupid = groupid;
- }
- public void setZkConnect(String zkConnect) {
- this.zkConnect = zkConnect;
- }
- public void setLocation(String location) {
- this.location = location;
- }
- public void setTopic(String topic) {
- this.topic = topic;
- }
- public void setPartitionsNum(int partitionsNum) {
- this.partitionsNum = partitionsNum;
- }
- public void setExecutor(MessageExecutor executor) {
- this.executor = executor;
- }
- public KafkaConsumerClient() {}
- //init consumer,and start connection and listener
- public void init() throws Exception {
- if(executor == null){
- throw new RuntimeException("KafkaConsumer,exectuor cant be null!");
- }
- Properties properties = new Properties();
- properties.load(Thread.currentThread().getContextClassLoader().getResourceAsStream(location));
- if(groupid != null){
- properties.put("groupid", groupid);
- }
- if(zkConnect != null){
- properties.put("zookeeper.connect", zkConnect);
- }
- ConsumerConfig config = new ConsumerConfig(properties);
- connector = Consumer.createJavaConsumerConnector(config);
- Map<String, Integer> topics = new HashMap<String, Integer>();
- topics.put(topic, partitionsNum);
- Map<String, List<KafkaStream<byte[], byte[]>>> streams = connector.createMessageStreams(topics);
- List<KafkaStream<byte[], byte[]>> partitions = streams.get(topic);
- threadPool = Executors.newFixedThreadPool(partitionsNum * 2);
- //start
- for (KafkaStream<byte[], byte[]> partition : partitions) {
- threadPool.execute(new MessageRunner(partition));
- }
- }
- public void close() {
- try {
- threadPool.shutdownNow();
- } catch (Exception e) {
- //
- } finally {
- connector.shutdown();
- }
- }
- class MessageRunner implements Runnable {
- private KafkaStream<byte[], byte[]> partition;
- MessageRunner(KafkaStream<byte[], byte[]> partition) {
- this.partition = partition;
- }
- public void run() {
- ConsumerIterator<byte[], byte[]> it = partition.iterator();
- while (it.hasNext()) {
- // connector.commitOffsets();手动提交offset,当autocommit.enable=false时使用
- MessageAndMetadata<byte[], byte[]> item = it.next();
- try{
- executor.execute(new String(item.message(),charset));// UTF-8,注意异常
- }catch(Exception e){
- //
- }
- }
- }
- public String getContent(Message message){
- ByteBuffer buffer = message.payload();
- if (buffer.remaining() == 0) {
- return null;
- }
- CharBuffer charBuffer = charset.decode(buffer);
- return charBuffer.toString();
- }
- }
- public static interface MessageExecutor {
- public void execute(String message);
- }
- /**
- * @param args
- */
- public static void main(String[] args) {
- KafkaConsumerClient consumer = null;
- try {
- MessageExecutor executor = new MessageExecutor() {
- public void execute(String message) {
- System.out.println(message);
- }
- };
- consumer = new KafkaConsumerClient();
- consumer.setTopic("test-topic");
- consumer.setPartitionsNum(2);
- consumer.setExecutor(executor);
- consumer.init();
- } catch (Exception e) {
- e.printStackTrace();
- } finally {
- if(consumer != null){
- consumer.close();
- }
- }
- }
- }
3) spring配置(略)
需要提醒的是,上述LogConsumer类中,没有太多的关注异常情况,必须在MessageExecutor.execute()方法中抛出异常时的情况.
在测试时,建议优先启动consumer,然后再启动producer,这样可以实时的观测到最新的消息。
相关推荐
总的来说,"jstorm集成kafka代码实例"是一个实践性的教程,帮助开发者了解如何在Java环境中将JStorm和Kafka结合,构建实时数据处理系统。通过这个例子,你不仅可以学习到如何编写相关代码,还能理解两个组件协同工作...
**Kafka学习实例** 在大数据实时处理领域,Apache Kafka是一个不可或缺的组件,它是一个分布式流处理平台,用于构建实时数据管道和流应用。本实例主要围绕Kafka的集群配置、生产和消费实例进行深入探讨。 首先,...
6. **测试与监控**:部署并启动 Storm 拓扑后,你需要监控系统的运行状态,确保数据正确地从 Kafka 流入 Storm,并最终通过 JDBC 存储到数据库中。可以使用 Storm UI 或其他监控工具进行监控。 在“StormKafkaJdbc...
6. **Kafka Connect**:这是一个用于集成Kafka与其他系统的工具,可以方便地导入和导出数据,比如从数据库到Kafka,或者从Kafka到数据仓库。 7. **Zookeeper**:Kafka依赖Zookeeper进行集群协调,包括管理broker、...
在IT行业中,Kafka是一个非常重要的分布式流处理平台,由LinkedIn开发并贡献给了Apache软件基金会。Kafka实例是实现大规模实时数据处理...通过实践Kafka-Demo,你将更深入地了解如何在实际环境中部署和操作Kafka实例。
这个"Kafka实例"的压缩包文件很可能是提供了一个实际的开发环境,包括消费者和生产者的Java代码示例,适用于在IntelliJ IDEA这样的集成开发环境中运行的Maven项目。下面将详细讨论Kafka、消费者、生产者以及与Maven...
生产者通过API与Kafka集群交互,选择消息的存储位置,并确保数据的顺序。 **消费者**则是从Kafka主题中读取并处理数据的应用程序。Kafka支持多消费者组,每个组内的消费者可以并行消费消息,实现负载均衡。消费者...
- 集群部署时,需要配置多个Kafka和Zookeeper实例,并在配置文件中正确设置集群间的连接信息。 通过以上步骤,你可以在本地环境中成功部署Kafka和Zookeeper,为你的大数据实时处理需求打下基础。记得根据实际情况...
集群模式是Kafka的一种部署方式,它可以提供冗余和负载均衡。在集群中,多个Kafka broker(服务器)共同分发和存储消息,确保服务的高可用性和容错性。 要实现集群模式的Kafka生产者和消费者,你需要以下步骤: 1....
使用Kafka .Net库,你可以创建生产者和消费者实例,它们是与Kafka集群交互的基本单元。生产者负责生成消息并将其发布到特定的主题,而消费者则订阅这些主题并处理接收到的消息。Kafka .Net支持同步和异步消息发送,...
10. 代码实践《kafka学习代码》中可能包含了一些示例,涵盖了producer、consumer的创建、消息发送与接收、配置调整等内容,是深入理解Kafka工作原理和使用技巧的重要参考资料。 总结,Kafka作为一个分布式流处理...
- **测试与部署**:单元测试代码,然后将应用部署到生产环境。 5. **Kafka Streams的应用场景**: - **实时数据分析**:实时监控系统性能、用户行为分析等。 - **ETL流程**:从不同的数据源抽取数据,转换后加载...
- **生产者示例**:使用Kafka的Java API,编写生产者代码,通过new Producer()创建实例,然后使用send()方法发送消息到指定主题。 - **消费者示例**:创建消费者实例,通过subscribe()订阅主题,然后使用poll()...
代码实例在Kafka学习资料中可能会展示如何配置Producer和Consumer,如何创建Topic和Partition,如何设置和管理消费者组,以及如何通过Kafka事务来保证消息的原子性。这些代码示例将会是理解Kafka实际操作的基础。 ...
**SpringBoot集成Kafka进行消息发布与订阅** 在现代微服务架构中,消息队列(Message Queue)扮演着至关重要的角色,它能够有效地解耦系统组件,提高系统的响应速度和可扩展性。Apache Kafka作为一款高吞吐量、低...
Scala代码中,开发者将实现一个类,该类连接到Kafka集群,创建Producer实例,并发送消息到指定的Topic。这通常涉及配置Producer的属性,如bootstrap服务器列表、序列化方式等。 `Consumer`则是接收和处理消息的一端...
【标题】"storm集成kafka插demo.zip"指的是一个演示如何将Apache Storm与Apache Kafka集成的实例项目。这个压缩包包含了一个示例,用于展示如何在Storm拓扑中消费和处理Kafka的消息。 【描述】"storm集成kafka插件...
这里提到的 "zk" 可能是指配置 Kafka 时需要的 Zookeeper 实例,虽然现在大多数新部署的 Kafka 集群使用内置的元数据管理。 **2. Spring Kafka 的配置** 配置 Spring Kafka 主要涉及以下几个方面: - **Bootstrap...
Kafka的部署需要一个Zookeeper集群,因为Zookeeper是Kafka的核心依赖,用于协调集群中的各个节点。因此,提供的zookeeper安装包也是必不可少的。Zookeeper是一个分布式的、开放源码的协调服务,它为分布式应用提供了...
2. 创建Kafka生产者实例,配置参数如服务器地址、主题等: ```cpp KafkaProducer producer("localhost:9092"); ``` 3. 创建消息,设置消息属性: ```cpp KafkaMessage message("my-topic", "Hello, Kafka!"); ...