開発者は、アプリケーションを開発するために内蔵されたカフカのクライアントAPIを使用することができます
プロデューサー
書き込みメッセージにカフカアプリケーション:などの情報インテリジェント家電、他のアプリケーションとの非同期通信を記録、ログメッセージの保存、メトリックを記録し、ユーザーの活動を記録
送信メッセージフロー
- ProducerRecordオブジェクトを作成しProducerRecordオブジェクトがターゲットトピック、パーティション、キー、値が含まれている必要があり、開始します。バイト配列オブジェクトのシリアル化にプロデューサと最初のキー値にプロデューサオブジェクトを送信する場合。
- データは、パーティションは、バッチレコードにレコードを追加するパーティションを選択し、パーティションに伝達され、バッチは、同じメッセージに送信され、パーティションまたはパーティションベースのハッシュキーに関連します。
- サーバーがメッセージを受信すると、それが応答を返します。書き込み成功、テーマやパーティション情報が含まれていRecordMetaDataオブジェクトを返し、オフセット、ZKに戻るべき記録。書き込み失敗は、エラーが、それはあなたがプロデューサー後にエラーが表示されるメッセージを再送信し、返されます。
作成プロデューサーコード
private Properties kafkaProps = new Properties();
kafkaProps.put("bootstrap.servers", "broker1:9092,broker2:9092");
kafkaProps.put("key.serializer",
"org.apache.kafka.common.serialization.StringSerializer");
kafkaProps.put("value.serializer",
"org.apache.kafka.common.serialization.StringSerializer");
producer = new KafkaProducer<String, String>(kafkaProps);
三つの方法からメッセージを送信
- 送信し忘れています。メッセージがサーバーに送信された後、それが到達するために正常であるか否かを気にしません。
- 同期伝送。利用センド()、送信今後のオブジェクトを返し、呼び出しのget()待ちのメッセージが正常に送信できるようになるまで
- 非同期伝送。()伝送、及び使用送信するコールバック関数を指定し、サーバは、呼び出し関数式に応答を返します
シリアライザ
あなたはシリアライザを指定する必要がありますプロデューサオブジェクトを作成します。
オブジェクトがカフカ単純な文字列又は整数に送信されない場合、フレームワーク配列は、アブロ、倹約、いるProtobuf、またはカスタムシリアル化装置を使用するように、メッセージの録音を作成するために使用されてもよいです。
カスタム・シリアライズ
//简单一个客户类
public class Customer {
private int customerID;
private String customerName;
public Customer(int ID, String name) {
this.customerID = ID;
this.customerName = name;
}
public int getID() {
return customerID;
}
public String getName() {
return customerName;
}
}
//创建序列化器
import org.apache.kafka.common.errors.SerializationException;
import java.nio.ByteBuffer;
import java.util.Map;
public class CustomerSerializer implements Serializer<Customer> {
@Override
public void configure(Map configs, boolean isKey) {
// 不做任何配置
}
@Override
/**
Customer对象被序列化成:
表示customerID的4字节整数
表示customerName长度的4字节整数(如果customerName为空,则长度为0)
表示customerName的N个字节
*/
public byte[] serialize(String topic, Customer data) {
try {
byte[] serializedName;
int stringSize;
if (data == null)
return null;
else {
if (data.getName() != null) {
serializedName = data.getName().getBytes("UTF-8");
stringSize = serializedName.length;
} else {
serializedName = new byte[0];
stringSize = 0;
}
}
ByteBuffer buffer = ByteBuffer.allocate(4 + 4 + stringSize);
buffer.putInt(data.getID());
buffer.putInt(stringSize);
buffer.put(serializedName);
return buffer.array();
} catch (Exception e) {
throw new SerializationException("Error when serializing Customer to
byte[] " + e);
}
}
@Override
public void close() {
// 不需要关闭任何东西
}
}
使用アブロシリアライズ
ファイルの読み書きの際には、スキーマを使用する必要がある場合、データは、スキーマは、一般的に、データファイルに埋め込まれます、バイナリファイルまたはJSONファイル、アブロにシリアライズされます。特長は、新しいスキーマを使用して書き込み情報は、情報を読み取るための責任をそのまま使用し続けることができます。
パーティション
キービットNULLは、ラウンドロビン・パーティションが等しく、各パーティションに配布メッセージを使用する場合、キーは、対応するパーティションにマッピングされたハッシュキーは、キーが常に同じパーティションに同じである、空ではありません。
カスタム分割戦略
import org.apache.kafka.clients.producer.Partitioner;
import org.apache.kafka.common.Cluster;
import org.apache.kafka.common.PartitionInfo;
import org.apache.kafka.common.record.InvalidRecordException;
import org.apache.kafka.common.utils.Utils;
public class BananaPartitioner implements Partitioner {
public void configure(Map<String, ?> configs) {}
public int partition(String topic, Object key, byte[] keyBytes, Object value, byte[] valueBytes, Cluster cluster) {
List<PartitionInfo> partitions = cluster.partitionsForTopic(topic);
int numPartitions = partitions.size();
if ((keyBytes == null) || (!(key instanceOf String))) ➋
throw new InvalidRecordException("We expect all messages to have customer name as key")
if (((String) key).equals("Banana"))
return numPartitions; // Banana总是被分配到最后一个分区
// 其他记录被散列到其他分区
return (Math.abs(Utils.murmur2(keyBytes)) % (numPartitions - 1))
}
public void close() {}
}