
message Entry { //Entryは単一のサブスクリプションイベント構造です。1つのイベントはMySQLの1つのbinlog eventに相当します。Header header = 1; //イベントヘッダーEvent event = 2; //イベントボディ}message Header {int32 version = 1; //EntryプロトコルバージョンSourceType sourceType = 2; //ソースデータベースのタイプ情報。MySQL、Oracleなどのタイプが含まれます。MessageType messageType = 3; //メッセージのタイプ、つまりEventのタイプです。BEGIN、COMMIT、DMLなどが含まれます。uint32 timestamp = 4; //Eventの元のbinlogにおけるタイムスタンプint64 serverId = 5; //ソースのserverIdstring fileName = 6; //ソースbinlogのファイル名uint64 position = 7; //ソースbinlogファイル内のイベントのオフセットstring gtid = 8; //現在のトランザクションのgtidstring schemaName = 9; //変更の影響を受けるスキーマstring tableName = 10; //変更の影響を受けるテーブルuint64 seqId = 11; //グローバル増分シーケンス番号uint64 eventIndex = 12; //大きなeventをシャード化する場合、各シャードは0から番号が振られます。現在のバージョンでは意味がなく、今後の拡張用に予約されています。bool isLast = 13; //現在のeventがeventシャードの最後のブロックであるかどうか。最後のブロックである場合はtrueです。現在のバージョンでは意味がなく、今後の拡張用に予約されています。repeated KVPair properties = 15;}message Event {BeginEvent beginEvent = 1; //binlog内のbeginイベントDMLEvent dmlEvent = 2; //binlog内のdmlイベントCommitEvent commitEvent = 3; //binlog内のcommitイベントDDLEvent ddlEvent = 4; //binlog内のddlイベントRollbackEvent rollbackEvent = 5; //rollbackイベント。現在のバージョンでは意味がありません。HeartbeatEvent heartbeatEvent = 6; //ソースデータベースが定期的に送信するハートビートイベントCheckpointEvent checkpointEvent = 7; //購読バックエンドが追加するcheckpointイベントです。10秒ごとに1つ自動生成され、Kafkaの生産および消費場所の管理に使用されます。repeated KVPair properties = 15;}
message Entries {repeated Entry items = 1; //entry list}
message Envelope {int32 version = 1; //プロトコルバージョン。data内容のデコード方法を決定します。uint32 total = 2;uint32 index = 3;bytes data = 4; //現在のversionが1の場合、data内のデータはEntriesがPBシリアル化された結果であることを示します。repeated KVPair properties = 15;}
// Flink-kafka コンシューマーを作成します。FlinkKafkaConsumer<RecordMsgObject> consumer =new FlinkKafkaConsumer<>(topic, new DeserializeProtobufToRecordMsgObject(), props);
// カスタムデシリアライザ。元のメッセージを RecordMsgObject オブジェクトにデシリアライズします。@Overridepublic RecordMsgObject deserialize(ConsumerRecord<byte[], byte[]> record) throws Exception {RecordMsgObject obj = new RecordMsgObject();obj.topic = record.topic();obj.partition = record.partition();obj.offset = record.offset();obj.partitionSeq = getPartitionSeq(record);obj.key = new String(record.key());obj.headers = record.headers();// ここで受信されるのは Envelope のバイナリ値です。obj.value = record.value();return obj;}
//受信したメッセージを partition ごとに処理します。stream.keyBy(RecordMsgObject::getPartition).process(new SubscribeMsgProcess(trans2sql)).setParallelism(1);
// envlope をデシリアライズします。このデモでは、デフォルトで1つの envlope に bnlog-event の全データを格納できます。SubscribeProtobufData.Envelope envelope = SubscribeProtobufData.Envelope.parseFrom(record.value);if (1 != envelope.getVersion()) {throw new IllegalStateException(String.format("unsupported version: %d", envelope.getVersion()));}
// デシリアライズして Entries を取得します。ByteString envelopeData = envelope.getData();SubscribeProtobufData.Entries entries;if (1 == envelope.getTotal()) {entries = SubscribeProtobufData.Entries.parseFrom(envelopeData.toByteArray());} else {entries = SubscribeProtobufData.Entries.parseFrom(shardMsgMap.get(shardId).toByteArray());shardMsgMap.remove(shardId);}
// 各 Entry を順に処理し、Entry のタイプに応じて sql を出力します。for (SubscribeProtobufData.Entry entry : entries.getItemsList()) {onEntry(record.partition, record.offset, ps, entry, trans2sql);}
message Data {DataType dataType = 1;string charset = 2; //DataType_STRING のエンコーディングタイプ。値は bv に格納されます。string sv = 3; //DataType_INT8/16/32/64/UINT8/16/32/64/Float32/64/DataType_DECIMAL の文字列値。bytes bv = 4; //DataType_STRING/DataType_BYTES の値。}
enum DataType {NIL = 0; //値は NULL です。INT8 = 1;INT16 = 2;INT32 = 3;INT64 = 4;UINT8 = 5;UINT16 = 6;UINT32 = 7;UINT64 = 8;FLOAT32 = 9;FLOAT64 = 10;BYTES = 11;DECIMAL = 12;STRING = 13;NA = 14; //値は存在しません (N/A)}
DATE、TIME、DATETIME タイプはタイムゾーンをサポートしていません。TIMESTAMP タイプはタイムゾーンをサポートします。このタイプのフィールドは、保存時にシステムが現在のタイムゾーンから UTC(Universal Time Coordinated)に変換して保存し、クエリ時にシステムが UTC から現在のタイムゾーンに変換してクエリすることを示します。TDSQL MySQLフィールドタイプ | 対応する Protobuf DataType 列挙値 |
MYSQL_TYPE_NULL | NIL |
MYSQL_TYPE_INT8 | INT8 |
MYSQL_TYPE_INT16 | INT16 |
MYSQL_TYPE_INT24 | INT32 |
MYSQL_TYPE_INT32 | INT32 |
MYSQL_TYPE_INT64 | INT64 |
MYSQL_TYPE_BIT | INT64 |
MYSQL_TYPE_YEAR | INT64 |
MYSQL_TYPE_FLOAT | FLOAT32 |
MYSQL_TYPE_DOUBLE | FLOAT64 |
MYSQL_TYPE_VARCHAR | STRING |
MYSQL_TYPE_STRING | STRING |
MYSQL_TYPE_VAR_STRING | STRING |
MYSQL_TYPE_TIMESTAMP | STRING |
MYSQL_TYPE_DATE | STRING |
MYSQL_TYPE_TIME | STRING |
MYSQL_TYPE_DATETIME | STRING |
MYSQL_TYPE_TIMESTAMP_NEW | STRING |
MYSQL_TYPE_DATE_NEW | STRING |
MYSQL_TYPE_TIME_NEW | STRNG |
MYSQL_TYPE_DATETIME_NEW | STRING |
MYSQL_TYPE_ENUM | STRING |
MYSQL_TYPE_SET | STRING |
MYSQL_TYPE_DECIMAL | DECIMAL |
MYSQL_TYPE_DECIMAL_NEW | DECIMAL |
MYSQL_TYPE_JSON | BYTES |
MYSQL_TYPE_BLOB | BYTES |
MYSQL_TYPE_TINY_BLOB | BYTES |
MYSQL_TYPE_MEDIUM_BLOB | BYTES |
MYSQL_TYPE_LONG_BLOB | BYTES |
MYSQL_TYPE_GEOMETRY | BYTES |
フィードバック