[英]Why use Avro with Kafka - How to handle POJOs
我有一個春季應用程序,是我的kafka制作人,我想知道為什么avro是最好的方式去。 我讀到了它以及它所提供的一切,但為什么我不能將我自己用傑克遜創建的POJO序列化並將其發送給kafka?
我這樣說是因為avro的POJO代並不是那么直截了當。 最重要的是,它需要maven插件和.avsc文件。
所以例如我在我的kafka制作人上創建了一個名為User的POJO:
public class User {
private long userId;
private String name;
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public long getUserId() {
return userId;
}
public void setUserId(long userId) {
this.userId = userId;
}
}
我將其序列化並將其發送到我在kafka中的用戶主題。 然后我有一個消費者,它本身有一個POJO用戶並反序列化該消息。 這是空間問題嗎? 以這種方式序列化和反序列化也不是更快嗎? 更不用說維護模式注冊表有一個開銷。
這是速度和存儲的問題。 在序列化數據時,您經常需要傳輸實際模式,因此會導致有效負載大小的增加。
Total Payload Size
+-----------------+--------------------------------------------------+
| Schema | Serialised Data |
+-----------------+--------------------------------------------------+
Schema Registry為模式和元數據提供集中存儲庫,以便所有模式都在中央系統中注冊。 這個集中式系統使生產者只能包含模式的ID而不是完整模式本身(文本格式)。
Total Payload Size
+----+--------------------------------------------------+
| ID | Serialised Data |
+----+--------------------------------------------------+
因此,序列化變得更快。
此外,架構注冊表版本控制可以實施數據策略,這些策略可能有助於防止較新的架構破壞與現有版本的兼容性,這些版本可能會導致停機或管道中的任何其他重大問題。
你不需要AVSC, 你可以使用AVDL文件 ,它基本上看起來像只有字段的POJO
@namespace("com.example.mycode.avro")
protocol ExampleProtocol {
record User {
long id;
string name;
}
}
當使用Maven插件的idl-protocol
目標時,將為您創建此AVSC,而不是您自己編寫它。
{
"type" : "record",
"name" : "User",
"namespace" : "com.example.mycode.avro",
"fields" : [ {
"name" : "id",
"type" : "long"
}, {
"name" : "name",
"type" : "string"
} ]
}
它還會在您的類路徑中放置一個SpecificData
POJO User.java
,以便在您的代碼中使用。
如果您已經有POJO,則無需使用AVSC或AVDL文件。 有轉換POJO的庫。 例如,你可以使用 Jackson ,它不僅僅是JSON,你只需要為Kafka創建一個JacksonAvroSerializer
,或者查找是否存在。
Avro還具有基於反射的內置庫 。
那么問題 - 為什么Avro(對於Kafka)?
好吧,擁有一個架構是一件好事 。 想想RDBMS表,你可以解釋一下表,然后你會看到所有的列。 轉移到NoSQL文檔數據庫,它們可以包含任何內容,這就是Kafka的JSON世界。
假設您的Kafka群集中的消費者不知道主題中的內容,他們必須確切地知道主題中產生了誰/什么。 他們可以嘗試控制台消費者,如果它是像JSON這樣的明文,那么他們必須弄清楚他們感興趣的一些字段,然后一次又一次地執行類似HashMap的.get("name")
操作,只運行當一個字段不存在時進入NPE。 使用Avro,您可以清楚地定義默認值和可空字段。
您不需要使用模式注冊表,但它為RDBMS類比提供了這種類型的explain topic
語義。 它還使您無需發送架構以及每條消息,以及Kafka主題上額外帶寬的費用。 注冊表不僅對Kafka有用,因為它可以用於Spark,Flink,Hive等所有圍繞流數據攝取的數據科學分析。
假設您確實想要使用JSON,那么請嘗試使用MsgPack ,您可能會看到Kafka吞吐量增加並節省了代理上的磁盤空間
首先 - 卡夫卡不知道關鍵/價值內容。 它操作字節,它的客戶端(生產者/消費者)負責照顧de / serialization。
到目前為止,最常見的選項似乎是JSON,protobuf和Avro。
我個人喜歡Avro以及為什么我經常使用它並推薦給其他人:
1)這是一個足夠緊湊的二進制序列化,具有模式和邏輯類型 (有助於區分timestamp in long millis
的常規long
和timestamp in long millis
)
2)Avro模式非常具有描述性並且完整記錄
3)大多數廣泛使用的編程語言都是必須的!
4)Confluent(和其他)為模式提供存儲庫,即所謂的“模式注冊表”,以便為模式提供集中存儲。 在Avro中,消息僅包含架構版本ID,而不包含架構本身。
5)如果您使用的是Java,那么使用模式中的POJO基類生成可以獲得很大的好處。
當然,您可以將其中的一部分與其他選項一起使用。 您應該嘗試比較適合您的用例的所有選項。
PS我非常個人的建議是:如果不是String
,請選擇Avro。 適用於鍵和值。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.