从Kafka请求java对象时出错
我开始学习卡夫卡,现在, 我正在发送/接收序列化/理想化的java类。 我的问题是:我的配置中遗漏了什么,所以我无法从Kafka反序列化对象 这是我的班级: 我在主类中的属性: producerPropsObject.put(ProducerConfig.CLIENT\u ID\u CONFIG, AppConfigs.applicationProducerSerializedObject); producerPropsObject.put(ProducerConfig.BOOTSTRAP\u SERVERS\u CONFIG, AppConfigs.bootstrapserver); producerPropsObject.put(ProducerConfig.KEY\u SERIALIZER\u CLASS\u CONFIG, StringSerializer.class.getName()); producerPropsObject.put(ProducerConfig.VALUE\u SERIALIZER\u CLASS\u CONFIG, FooSerializer.class.getName()); producerPropsObject.put(“主题”,AppConfigs.topicNameForSerializedObject) consumerPropsObject.put(ConsumerConfig.GROUP\u ID\u CONFIG,AppConfigs.applicationProducerSerializedObject); consumerPropsObject.put(ConsumerConfig.BOOTSTRAP\u SERVERS\u CONFIG,AppConfigs.bootstrapsservers); consumerPropsObject.put(ConsumerConfig.KEY_反序列化程序_CLASS_CONFIG,StringDeserializer.CLASS.getName()); consumerPropsObject.put(ConsumerConfig.VALUE\u反序列化程序\u CLASS\u配置,FooDeserializer.CLASS.getName()); consumerPropsObject.put(ConsumerConfig.MAX\u POLL\u INTERVAL\u MS\u CONFIG,300000); consumerPropsObject.put(ConsumerConfig.ENABLE\u AUTO\u COMMIT\u CONFIG,true); consumerPropsObject.put(ConsumerConfig.AUTO_OFFSET_RESET_CONFIG,“最早”); consumerPropsObject.put(“主题”,AppConfigs.topicNameForSerializedObject) 以下是序列化程序/反序列化程序实现: 最后,我试图从main生产和消费我的食物的方式: 看起来,它很好用,因为我后来在卡夫卡主题中看到了我的键和值从Kafka请求java对象时出错,java,apache-kafka,deserialization,Java,Apache Kafka,Deserialization,我开始学习卡夫卡,现在, 我正在发送/接收序列化/理想化的java类。 我的问题是:我的配置中遗漏了什么,所以我无法从Kafka反序列化对象 这是我的班级: 我在主类中的属性: producerPropsObject.put(ProducerConfig.CLIENT\u ID\u CONFIG, AppConfigs.applicationProducerSerializedObject); producerPropsObject.put(ProducerConfig.BOOTSTRAP\u
public void producerobjecttokafka(最终属性producerProps){
最终字符串[]ar=新字符串[]{“矩阵”、“裸枪”、“第五元素”、“铁杆”、“乱世佳人”};
卡夫卡制作人=新卡夫卡制作人(producerProps);
final Foo j=新Foo(ar[getAnInt(4)],getAnInt(10),getAnDouble());
send(新的ProducerRecord(producerProps.getProperty(“主题”),j.getItem(),j.toString().getBytes());
producer.flush();
producer.close();
}
但是,当我的消费者捕获输出时:
public void ConsumerFoodFromKafka(最终属性ConsumerOps){
最终消费者支持者=新卡夫卡消费者(consumerProps);
最终螺纹分离螺纹=新螺纹(()->{
试一试{
myConsumer.subscribe(Collections.singletonList(consumerProps.getProperty(“主题”));
while(continueToRunFlag){
最终StringBuilder sb=新StringBuilder();
最终消费者记录消费者记录=myConsumer.poll(持续时间:百万分之十);
如果(consumerRecords.count()>0){
用于(消费记录cRec:消费记录){
sb.append(cRec.key()).append(我不知道为什么您使用bytearray outputstream,但试图在反序列化程序中读取JSON,但这解释了错误。您甚至可以通过直接调用serialize/deserialize方法,在根本不使用Kafka的情况下对其进行测试
在提供的链接中,序列化程序使用objectMapper.writeValueAsString
,它返回JSON文本,而不是特定于Java的outputstream。如果您希望在不同的编程语言之间使用和生成数据(大多数公司都是这样),您应该避免这种特定的序列化格式
注意:Confluent为Kafka提供了Avro、Protobuf和JSON序列化程序,因此如果您想使用其中一种格式,您不需要编写自己的序列化程序。如果您想从JSON反序列化,那么您需要将其序列化为JSON,在您的序列化程序中也使用jackson,一切都应该很好
公共类FooSerializer实现org.apache.kafka.common.serialization.Serializer{
公共无效配置(映射,布尔b){}
公共字节[]序列化(字符串s,对象o){
试一试{
ObjectMapper om=new ObjectMapper();//来自jackson的ObjectMapper
字节[]b=om.writeValueAsString(o.getBytes();
返回b;
}catch(IOE异常){返回新字节[0];}
}
公共void close(){}
}
你也尝试过使用jackson进行序列化吗?没有,我只是遵循了一个在线示例……这里没有关于序列化失败的任何消息,因为你序列化的不是json的字节,而是你对象的字节,你需要序列化为json,这就是我建议使用jackson的原因serializer@rizesky不需要JSON,卡夫卡根本不在乎只要它是bytes@OneCricketeer这不是kafka的问题,请阅读问题,这是他的反序列化程序问题,kafka在其对象的字节流中接受他的消息,但不是json的字节,而是其java对象的字节,这取决于其对可序列化接口的实现(是否超出左默认值),这就是为什么他的json desealizer if无法反序列化,因为它需要字节的json来执行,但他提供了他的java对象的字节。如果您仍然不理解,请阅读什么是序列化。thanksAgree,他可能认为序列化正在创建该对象的json。serializaton只是创建序列化对象的字节序列我无法存储在磁盘中或通过socketGuys发送,非常感谢您的帮助…事实上,我错过了这两种不同的序列化方式…就像我说的:我刚刚开始。。。
public class Foo {
private String item;
private int quantity;
private Double price;
public Foo(String item, int quantity, final double price) {
this.item = item;
this.quantity = quantity;
this.price = price;
}
public String getItem() { return item; }
public int getQuantity() { return quantity; }
public Double getPrice() { return price; }
public void setQuantity(int quantity) { this.quantity = quantity; }
public void setPrice(double price) { this.price = price; }
@Override
public String toString() {
return "item=" + item + ", quantity=" + quantity + ", price=" + price;
}
}
public class FooSerializer implements org.apache.kafka.common.serialization.Serializer {
public void configure(Map map, boolean b) { }
public byte[] serialize(String s, Object o) {
try {
ByteArrayOutputStream baos = new ByteArrayOutputStream();
ObjectOutputStream oos = new ObjectOutputStream(baos);
oos.writeObject(o);
oos.close();
byte[] b = baos.toByteArray();
return b;
} catch (IOException e) { return new byte[0]; }
}
public void close() { }
}
public class FooDeserializer implements org.apache.kafka.common.serialization.Deserializer {
@Override
public void close() { }
@Override
public Foo deserialize(String arg0, byte[] arg1) {
//Option #1:
//ObjectMapper mapper = new ObjectMapper();
//Option #2:
JsonFactory factory = new JsonFactory();
factory.enable(JsonParser.Feature.ALLOW_SINGLE_QUOTES);
ObjectMapper mapper = new ObjectMapper(factory);
Foo fooObj = null;
try {
//Option #1:
//fooObj = mapper.readValue(arg1, Foo.class); // BREAKS HERE!!!
//Option #2:
fooObj = mapper.reader().forType(Foo.class).readValue(arg1); // BREAKS HERE!!!
}
catch (Exception e) { e.printStackTrace(); }
return fooObj;
}
}
public void produceObjectToKafka(final Properties producerProps) {
final String[] ar = new String[]{"Matrix", "Naked Gun", "5th Element", "Die Hard", "Gone with a wind"};
KafkaProducer<String, byte[]> producer = new KafkaProducer<>(producerProps);
final Foo j = new Foo(ar[getAnInt(4)], getAnInt(10), getAnDouble());
producer.send(new ProducerRecord<>(producerProps.getProperty("topic"), j.getItem(), j.toString().getBytes()));
producer.flush();
producer.close();
}
public void consumeFooFromKafka(final Properties consumerProps) {
final Consumer<String, Foo> myConsumer = new KafkaConsumer<>(consumerProps);
final Thread separateThread = new Thread(() -> {
try {
myConsumer.subscribe(Collections.singletonList(consumerProps.getProperty("topic")));
while (continueToRunFlag) {
final StringBuilder sb = new StringBuilder();
final ConsumerRecords<String, Foo> consumerRecords = myConsumer.poll(Duration.ofMillis(10));
if (consumerRecords.count() > 0) {
for (ConsumerRecord<String, Foo> cRec : consumerRecords) {
sb.append( cRec.key() ).append("<<").append(cRec.value().getItem() + ",").append(cRec.value().getQuantity() + ",").append(cRec.value().getPrice()).append("|");
}
}
if (sb.length() > 0) { System.out.println(sb.toString()); }
}
}
finally {
myConsumer.close();
}
});
separateThread.start();
}