mongoshake 是个开源的用户mongo数据迁移和同步的工具,支持往各种目标源头写数据

具体:https://github.com/alibaba/MongoShake

有业务场景想把oplog 写入到kafka 中,如果直接在collector.conf 设置kafka 信息会导致写入kafka 中数据是乱码

官方解释是直接从collector 采集到的oplog是带有控制信息的。直接写入kafka 的内容使用时要进行剥离。

在下载mongoshake 包时他会提供receiver 进行控制信息剥离

mongo --> collector --> kafka --> receiver --> 业务

mongo --> collector --> receiver --> kafka --> 业务

这里更倾向于第二种

collector --> receiver 我采用的是tcp

配置:

collector.conf

tunnel = tcp
tunnel.address = 127.0.0.1:9300

receiver.conf

tunnel = tcp
tunnel.address = 127.0.0.1:9300

这里会很奇怪,也没有设置kafka 的地方啊,这样所有oplog剥离信息都会放在receiver 的log下

这里官方解释是要求我们对源码进行修改、编译,源码是GO 写的,改起来也比较熟悉

下载官方源码

src/mongoshake/receiver/replayer.go

在handler()

/*
* Users should modify this function according to different demands.
*/
func (er *ExampleReplayer) handler() {
config := sarama.NewConfig()//kafka配置
config.Producer.RequiredAcks = sarama.WaitForAll
config.Producer.Return.Successes = true
kafkaClient, err := sarama.NewSyncProducer([]string{conf.Options.KafkaHost}, config)
if err != nil {
LOG.Info("producer close,err:", err)
return
} defer kafkaClient.Close() for msg := range er.pendingQueue {
count := uint64(len(msg.message.RawLogs))
if count == 0 {
// probe request
continue
} // parse batched message
oplogs := make([]*oplog.PartialLog, len(msg.message.RawLogs))
for i, raw := range msg.message.RawLogs {
oplogs[i] = new(oplog.PartialLog)
if err := bson.Unmarshal(raw, oplogs[i]); err != nil {
// impossible switch, need panic and exit
LOG.Crashf("unmarshal oplog[%v] failed[%v]", raw, err)
return
}
oplogs[i].RawSize = len(raw)
//这里是对oplog 做了一些定制化内容
kafkaOpLog := KafkaOpLog{}
kafkaOpLog.Namespace = oplogs[i].Namespace
kafkaOpLog.Query = oplogs[i].Query
kafkaOpLog.Object = oplogs[i].Object.Map()
kafkaOpLog.Operation = oplogs[i].Operation
kafkaOpLog.Timestamp = oplogs[i].Timestamp msg := &sarama.ProducerMessage{}
msg.Topic = conf.Options.KafkaTopic
encode ,err := json.Marshal(kafkaOpLog)
if err != nil {
_ = LOG.Error("oplogs bson.MarshalJSON err",err)
continue
}
msg.Value = sarama.StringEncoder(encode)
msg.Key = sarama.StringEncoder(kafkaOpLog.Namespace)
_, _, err = kafkaClient.SendMessage(msg)
if err != nil {
_ = LOG.Error("send message failed,", err)
return
}
//原来源码中只是打印了log
//LOG.Info(oplogs[i]) // just print for test, users can modify to fulfill different needs
} if callback := msg.completion; callback != nil {
callback() // exec callback
} // get the newest timestamp
n := len(oplogs)
lastTs := utils.TimestampToInt64(oplogs[n-1].Timestamp)
er.Ack = lastTs LOG.Debug("handle ack[%v]", er.Ack) // add logical code below
}
}

然后go build   使用

使用mongoshake进行oplog同步读取,解决乱码问题的更多相关文章

  1. Brophp框架开发时连接数据库读取UTF8乱码的解决(转)

    Brophp框架开发时连接数据库读取UTF8乱码的解决办法 (2012-09-15 10:41:22) 转载▼ 标签: 杂谈 it php 分类: 建站技术 Brophp框架开发时连接数据库读取UTF ...

  2. 解决 python 读取文件乱码问题(UnicodeDecodeError)

    解决 python 读取文件乱码问题(UnicodeDecodeError) 确定你的文件的编码,下面的代码将以'utf-8'为例,否则会忽略编码错误导致输出乱码 解决方案一 with open(r' ...

  3. element ui 上传文件,读取内容乱码解决

    element ui 上传文件,读取内容乱码解决: 加第二个参数 reader.readAsText(file.raw,'gb2312'); <el-upload class="upl ...

  4. mongosync同步1,oplog同步会读取其他集合同步

    使用mongosync同步数据     注意: 我下面的这个mongodb版本较低(3.2.16), 还可以用这个工具来同步数据.工具不支持更高版本的mongodb了. 使用方法: https://g ...

  5. 上传Text文档并转换为PDF(解决乱码)

    前些日子,Insus.NET有分享一篇<上传Text文档并转换为PDF>http://www.cnblogs.com/insus/p/4313092.html 它是按最简单与默认方式来处理 ...

  6. Slave_SQL_Running: No mysql同步故障解决方法

    Slave_SQL_Running: No mysql同步故障解决      今天检查数据库发现一台MySQL Slave未和主机同步,查看Slave状态:mysql> show slave s ...

  7. mysql 使用set names 解决乱码问题的原理

    解决乱码的方法,我们经常使用“set names utf8”,那么为什么加上这句代码就可以解决了呢?下面跟着我一起来深入set names utf8的内部执行原理 先说MySQL的字符集问题.Wind ...

  8. StreamReader 读取文本文件乱码问题

    解决读取文本文件乱码问题.我采取的是读取前先判断文本文件格式. StreamReader sr = new StreamReader(fullfileName, GetFileEncodeType(f ...

  9. 编译VisualVM源码解决乱码问题

    编译VisualVM源码解决乱码问题 起因 今天在使用VisualVM对测试服务器进行JVM监控的时候,发现所有统计图的横纵坐标都是显示乱码(小方块),即使我的Ubuntu系统使用的是英文语言环境.奇 ...

随机推荐

  1. PostGIS 爆管分析之找出总阀门

    这个算法算是被摒弃了,但是很多自己思考过后留下的成果,虽然不用了,留着做记录. 算法目的是为了发生爆管后找到总阀门,这里分了几个步骤: 1.找到爆管点所在管段 2.通过遍历找到爆管点所有影响的阀门 3 ...

  2. 2019-9-11:渗透测试,基础学习,vim编辑器,笔记

    Linux快捷路径符号说明. 代表当前目录.. 上级目录- 代表前一个工作目录~ 表示当前用户的家目录 vmware tools 用来虚拟机和宿主机之间移动数据 vim/vi编辑器vim编辑器三种模式 ...

  3. Dart Learn Notes 01

    关于Dart的几点重要说明 在Dart中所有变量都是一个对象,所有对象都是一个类的实例.每个数字,方法,甚至是Null都是对象.所有的对吸纳更都是集成自Object这个类.(这个说法其实是很像Java ...

  4. C博客作业05--2019-指针

    0.展示PTA总分 1.本章学习总结 1.1 学习内容总结 1.2 本章学习体会 2.PTA实验作业 2.16 -7 输出月份英文名 2.1.1 伪代码 char* getmonth(int n) { ...

  5. LeetCode 5112. 十六进制魔术数字 Hexspeak

    地址 https://leetcode-cn.com/problems/hexspeak/ 题目描述字母大写的十六进制字符串,然后将所有的数字 0 变成字母 O ,将数字 1  变成字母 I . 如果 ...

  6. scrapy实现自动抓取51job并分别保存到redis,mongo和mysql数据库中

    项目简介 利用scrapy抓取51job上的python招聘信息,关键词为“python”,范围:全国 利用redis的set数据类型保存抓取过的url,现实避免重复抓取: 利用脚本实现每隔一段时间, ...

  7. Java8 Stream终端操作使用详解

    话不多说,自己挖的坑自己要填完,今天就给大家讲完Java8中Stream的终端操作使用详解.Stream流的终端操作主要有以下几种,我们来一一讲解. forEach() forEachOrdered( ...

  8. Git实战指南----跟着haibiscuit学Git(第五篇)

    笔名:  haibiscuit 博客园: https://www.cnblogs.com/haibiscuit/ Git地址: https://github.com/haibiscuit?tab=re ...

  9. 程序员的进阶课-架构师之路(14)-B+树、B*树

    版权声明:本文为博主原创文章,遵循CC 4.0 BY-SA版权协议,转载请附上原文出处链接和本声明. 本文链接:https://blog.csdn.net/m0_37609579/article/de ...

  10. 能不能自己写个类,也叫java.lang.String?

    可以,但在应用的时候,需要用自己的类加载器去加载,否则,系统的类加载器永远只是去加载jre.jar包中的那个java.lang.String.由于在tomcat的web应用程序中,都是由webapp自 ...