Python 消费Kafka手动提交 批量存入Elasticsearch

一、第三方包选择

pip install kafka ,对比了kafka和pykafka,还是选择kafka,消费速度更快
pip install elasticsearch==7.12.0(ES版本)

二、创建es连接对象

复制代码
from elasticsearch import Elasticsearch
from elasticsearch.helpers import bulk

class Create_ES(object):
    _instance = None

    def __new__(cls, *args, **kwargs):
        if cls._instance is None:
            cls._instance = super().__new__(cls)
        return cls._instance

    def __init__(self, hosts):
        try:
            self.es = Elasticsearch([{'host':host, 'port':9200}])
        except Exception as e:
            print('Connect ES Fail db:{} error:{}'.format(hosts, str(e)))

    def get_conn(self):
        return self.es

    def set_multi_data(self, datas):
        '''批量插入数据'''
        success = bulk(self.es, datas, raise_on_error=True)
        return success

三、消费kafka数据

复制代码
from kafka import KafkaConsumer, TopicPartition, OffsetAndMetadata
from . import Create_ES

class AppKfkConsumer(object):
    def __init__(self):
        self.server = 'localhost:9092'
        self.topic = KAFKA_TOPIC
        self.consumer = None
        self.tp = None
        self.consumer_timeout_ms = 5000  # 设置消费超时时间,
        self.type = 'members'
        self.group_id = 'test1'  # 设置消费group_id,避免重复消费
        self.es_index = 'index'  # es的index

    def get_connect(self):
        self.consumer = KafkaConsumer(
                                     group_id=self.group_id,
                                     auto_offset_reset='earliest',  # 从最早的数据开始消费
                                     bootstrap_servers=self.server,
                                     enable_auto_commit=False,  # 关闭自动提交
                                     consumer_timeout_ms=self.consumer_timeout_ms
                       )
        self.tp = TopicPartition(topic=self.topic, partition=0)  # 设置我们要消费的分区
        self.consumer.assign([self.tp])  # 由consumer对象分配分区

    def beginConsumer(self):
        now_offset = 0  # 当前偏移量
               
        es_conn = Create_ES()
        Actions = []
        while True:
            for message in self.consumer:
                now_offset = message.offset  # 获取当前偏移量
                data = eval(message.value.decode())  # 解析数据
                action = {
                    "_index": self.es_index,
                    "_type": self.type,
                    "_source": data
                }
                Actions.append(action)
                if len(Actions) >= 50000:
                    result = es_conn.set_multi_data(Actions)  # 批量插入数据
                    Actions = []
                    # 提交偏移量,now_offset+1的原因是因为我发现如果不加1,下次消费会从上次消费最后一条数据开始,重复消费
                    self.consumer.commit(offsets={tp:(OffsetAndMetadata(now_offset+1, None))})

            if len(Actions) > 0:
                result = es_conn.set_multi_data(Actions)
                Actions = []
                self.consumer.commit(offsets={tp:(OffsetAndMetadata(now_offset+1, None))})


    def delconnect(self):
        self.consumer.close()

# 执行任务
ks = AppKfkConsumer()
ks.get_connect()
ks.beginConsumer()
相关推荐
likeGhee13 分钟前
python缓存装饰器实现方案
开发语言·python·缓存
项目題供诗25 分钟前
黑马python(二十五)
开发语言·python
读书点滴29 分钟前
笨方法学python -练习14
java·前端·python
笑衬人心。44 分钟前
Ubuntu 22.04 修改默认 Python 版本为 Python3 笔记
笔记·python·ubuntu
蛋仔聊测试1 小时前
Playwright 中 Page 对象的常用方法详解
python
前端付豪1 小时前
17、自动化才是正义:用 Python 接管你的日常琐事
后端·python
jioulongzi1 小时前
记录一次莫名奇妙的跨域502(badgateway)错误
开发语言·python
破无差2 小时前
python实现简单的地图绘制与标记20250705
python
喜欢吃豆2 小时前
目前最火的agent方向-A2A快速实战构建(二): AutoGen模型集成指南:从OpenAI到本地部署的全场景LLM解决方案
后端·python·深度学习·flask·大模型
好开心啊没烦恼2 小时前
Python 数据分析:DataFrame,生成,用字典创建 DataFrame ,键值对数量不一样怎么办?
开发语言·python·数据挖掘·数据分析