package canal import ( //"log" "os" "time" "github.com/golang/protobuf/proto" "github.com/withlin/canal-go/client" pbe "github.com/withlin/canal-go/protocol/entry" "proxy/logger" ) func ConectCanalServer(ipaddr string) { // 192.168.199.17 替换成你的canal server的地址 // example 替换成-e canal.destinations=example 你自己定义的名字 connector := client.NewSimpleCanalConnector(ipaddr, 11111, "", "", "example", 60000, 60*60*1000) err := connector.Connect() if err != nil { logger.CanalLog.Errorln(err) os.Exit(1) } // https://github.com/alibaba/canal/wiki/AdminGuide //mysql 数据解析关注的表,Perl正则表达式. // //多个正则之间以逗号(,)分隔,转义符需要双斜杠(\\) // //常见例子: // // 1. 所有表:.* or .*\\..* // 2. canal schema下所有表: canal\\..* // 3. canal下的以canal打头的表:canal\\.canal.* // 4. canal schema下的一张表:canal\\.test1 // 5. 多个规则组合使用:canal\\..*,mysql.test1,mysql.test2 (逗号分隔) filter := "canal.instance.filter.regex=boss.tb_prd_prd_inst_551,boss.tb_prd_ofr_detail_inst_551,boss.tb_bil_tariff,boss.tb_prd_ofr,boss.tb_bil_evt_pricing_strategy,boss.config_area,boss.tb_bil_pricing_area,boss.ratable_history,boss.tb_bil_holiday_rel,boss.tb_bil_holiday" //err = connector.Subscribe(".*\\..*") err = connector.Subscribe(filter) if err != nil { logger.CanalLog.Errorln(err) os.Exit(1) } var counter int= 0 for { message, err := connector.Get(100, nil, nil) if err != nil { logger.CanalLog.Errorln(err) os.Exit(1) } batchId := message.Id if batchId == -1 || len(message.Entries) <= 0 { time.Sleep(200 * time.Millisecond) counter++ if counter == 300 { logger.CanalLog.Infoln("===Idle===") counter = 0 } continue } printEntry(message.Entries) counter = 0 } } /* func updateRedisTable(oneR *RecordChange) { var synType int if oneR.EventType == pbe.EventType_INSERT { synType = 1 } else if oneR.EventType == pbe.EventType_DELETE { synType = 3 } else { synType = 2 } switch oneR.TableName { case TbAcctInfo: mdb.UpdateRedisAcctTable(synType, oneR.ChgAcctInfo.PrdInstId, oneR.ChgAcctInfo.ServiceNbr) case TbOfrDetail: mdb.UpdateRedisAcctTableOfr(synType, oneR.ChgOfrDetail.OfrDetailInstId) case TbTariff: mdb.UpdateRedisTariffTable(synType, oneR.ChgTariff.TariffId) case TbOfrInfo: mdb.UpdateRedisTariffTableByOfr(synType, oneR.ChgOfrInfo.OfrId) case TbPricingStrategy: mdb.UpdateRedisTariffTableByStrategy(synType, oneR.ChgPricingStrategy.EventPricingStrategyId) case TbConfigArea:// update prefix table, while update config_area table mdb.UpdateRedisPrefixTableByConfigArea(synType, oneR.ChgConfigArea.AreaId, oneR.ChgConfigArea.OldAreaCode, oneR.ChgConfigArea.NewAreaCode) case TbPricingArea: mdb.UpdateRedisPrefixTable(synType, oneR.ChgPricingArea.NewStrategyId, oneR.ChgPricingArea.NewAreaId) case TbRr: if rrId > 0 { mdb.UpdateRedisRrTable(synType, rrId, ratableVal, usedVal, beginTime, endTime) } else { if ofrId > 0 {// ofr: CALC_PRIORITY mdb.UpdateRdbRrOfrPriority(ofrId, tariffSeq) } else if strategyId > 0 {// strategy: EVENT_PRIORITY mdb.UpdateRdbRrStrategyPriority(strategyId, tariffSeq) } } case TbHoliday: mdb.UpdateRedisHolidayDisTableByTariffId(synType, TariffId, tariffSeq) case TbBilHoliday: mdb.UpdateRedisHolidayDisTableByHolidayId(synType, holidayId) default: } }*/ func printEntry(entrys []pbe.Entry) { for _, entry := range entrys { if entry.GetEntryType() == pbe.EntryType_TRANSACTIONBEGIN || entry.GetEntryType() == pbe.EntryType_TRANSACTIONEND { continue } rowChange := new(pbe.RowChange) err := proto.Unmarshal(entry.GetStoreValue(), rowChange) checkError(err) if rowChange != nil { eventType := rowChange.GetEventType() header := entry.GetHeader() logger.CanalLog.Infof("================> binlog[%s : %d],name[%s,%s], eventType: %s", header.GetLogfileName(), header.GetLogfileOffset(), header.GetSchemaName(), header.GetTableName(), header.GetEventType()) for _, rowData := range rowChange.GetRowDatas() { /*oneRecordChg := ParseAndFilterChange(eventType, header.GetTableName(), rowData) if oneRecordChg == nil { continue } updateRedisTable(oneRecordChg)*/ if eventType == pbe.EventType_DELETE { printColumn(rowData.GetBeforeColumns()) } else if eventType == pbe.EventType_INSERT { printColumn(rowData.GetAfterColumns()) } else { logger.CanalLog.Infoln("-------> before") printColumn(rowData.GetBeforeColumns()) logger.CanalLog.Infoln("-------> after") printColumn(rowData.GetAfterColumns()) } } } } } func printColumn(columns []*pbe.Column) { for _, col := range columns { logger.CanalLog.Infof("%s : %s update= %t", col.GetName(), col.GetValue(), col.GetUpdated()) } } func checkError(err error) { if err != nil { logger.CanalLog.Errorf("Fatal error: %s", err.Error()) os.Exit(1) } }