"github.com/twpayne/go-geom/encoding/wkb"
"github.com/twpayne/go-geom/encoding/wkt"
"github.com/Shopify/sarama"
"your path of code generated by avro compilation/avro"
config := sarama.NewConfig()
brokers := "your brokers addrress"
username := "your username"
password := "your password"
config.Consumer.Offsets.Initial = sarama.OffsetNewest
config.Net.SASL.Enable = true
config.Net.SASL.User = username
config.Net.SASL.Password = password
cons, err := sarama.NewConsumerGroup(strings.Split(brokers, ","), group, config)
partitionCount: make(map[int32]int),
err = cons.Consume(context.Background(), []string{handler.topic}, handler)
fmt.Printf("consume failde, err=%v", err)
partitionCount map[int32]int
func (h *Handler) Setup(session sarama.ConsumerGroupSession) error {
func (h *Handler) Cleanup(sarama.ConsumerGroupSession) error {
func (h *Handler) ConsumeClaim(session sarama.ConsumerGroupSession, claim sarama.ConsumerGroupClaim) error {
for msg := range claim.Messages() {
record, err := avro.DeserializeRecord(bytes.NewReader(msg.Value))
session.MarkMessage(msg, "")
func printRecord(record *avro.Record) {
fmt.Printf("Operation[%s] ObjectName[%s] SourceTimestamp[%v] Id[%v]\n",
record.Operation.String(), record.ObjectName.String, record.SourceTimestamp, record.Id)
switch record.Operation {
fmt.Printf("DDL[%s] \n", record.AfterImages.String)
case avro.OperationINSERT:
for i := 0; i < len(record.AfterImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject); i++ {
after, err := getValue(record.AfterImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject[i])
fmt.Printf("Field[%s] After[%s]\n", record.Fields.ArrayField[i].Name, after)
case avro.OperationUPDATE:
for i := 0; i < len(record.AfterImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject); i++ {
before, err := getValue(record.BeforeImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject[i])
after, err := getValue(record.AfterImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject[i])
fmt.Printf("Field[%s] Before[%s] After[%s]\n", record.Fields.ArrayField[i].Name, before, after)
case avro.OperationDELETE:
for i := 0; i < len(record.BeforeImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject); i++ {
before, err := getValue(record.BeforeImages.ArrayUnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject[i])
fmt.Printf("Field[%s] Before[%s]\n", record.Fields.ArrayField[i].Name, before)
func getValue(in *avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject) (string, error) {
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumInteger:
return in.Integer.Value, nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumCharacter:
return string(in.Character.Value), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumDecimal:
return fmt.Sprintf("%s", in.Decimal.Value), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumFloat:
return fmt.Sprintf("%v", in.Float.Value), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumTimestamp:
return fmt.Sprintf("%v.%v", in.Timestamp.Timestamp, in.Timestamp.Millis), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumDateTime:
var year, month, day, hour, minute, second int32
if in.DateTime.Year != nil {
year = in.DateTime.Year.Int
if in.DateTime.Month != nil {
month = in.DateTime.Month.Int
if in.DateTime.Day != nil {
day = in.DateTime.Day.Int
if in.DateTime.Hour != nil {
hour = in.DateTime.Hour.Int
if in.DateTime.Minute != nil {
minute = in.DateTime.Minute.Int
if in.DateTime.Second != nil {
second = in.DateTime.Second.Int
return fmt.Sprintf("%v-%v-%v %v:%v:%v", year, month, day, hour, minute, second), nil
return fmt.Sprintf("%v:%v:%v", hour, minute, second), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumTimestampWithTimeZone:
var year, month, day, hour, minute, second int32
if in.TimestampWithTimeZone.Value.Year != nil {
year = in.TimestampWithTimeZone.Value.Year.Int
if in.TimestampWithTimeZone.Value.Month != nil {
month = in.TimestampWithTimeZone.Value.Month.Int
if in.TimestampWithTimeZone.Value.Day != nil {
day = in.TimestampWithTimeZone.Value.Day.Int
if in.TimestampWithTimeZone.Value.Hour != nil {
hour = in.TimestampWithTimeZone.Value.Hour.Int
if in.TimestampWithTimeZone.Value.Minute != nil {
minute = in.TimestampWithTimeZone.Value.Minute.Int
if in.TimestampWithTimeZone.Value.Second != nil {
second = in.TimestampWithTimeZone.Value.Second.Int
return fmt.Sprintf("%v-%v-%v %v:%v:%v+%v", year, month, day, hour, minute, second, in.TimestampWithTimeZone.Timezone), nil
return fmt.Sprintf("%v:%v:%v", hour, minute, second), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumBinaryGeometry:
return getReadableGeometry(in.BinaryGeometry.Value)
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumTextGeometry:
return getReadableGeometry([]byte(in.TextGeometry.Value))
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumBinaryObject:
return fmt.Sprintf("%s", string(in.BinaryObject.Value)), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumTextObject:
return fmt.Sprintf("%s", in.TextObject.Value), nil
case avro.UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObjectTypeEnumEmptyObject:
return fmt.Sprintf("%s", in.EmptyObject.String()), nil
return "", fmt.Errorf("invalid value for *UnionNullIntegerCharacterDecimalFloatTimestampDateTimeTimestampWithTimeZoneBinaryGeometryTextGeometryBinaryObjectTextObjectEmptyObject")
func getReadableGeometry(raw []byte) (string, error) {
return "", fmt.Errorf("not a valid geometry %v", raw)
geomObj, err := wkb.Unmarshal(raw[4:])
wktObj, err := wkt.Marshal(geomObj)