1

I am new to Kafka and am facing the below issue for mymodel class User [Request processing failed; nested exception is org.apache.kafka.common.errors.SerializationException: Can't convert value of class model.User to class org.apache.kafka.common.serialization.StringSerializer specified in value.serializer] with root cause java.lang.ClassCastException: class model.User cannot be cast to class java.lang.String (model.User is in unnamed module of loader 'app'; java.lang.String is in module java.base of loader 'bootstrap') at org.apache.kafka.common.serialization.StringSerializer.serialize(StringSerializer.java:28) ~[kafka-clients-2.7.1.jar:na] at*

I am suspecting it to be due to wrong imports of StringSerializer and JSONSerializer in KafkaConfiguration .Below is my code

1- KafkaConfiguration

package config;

import java.util.HashMap;
import java.util.Map;

import org.apache.kafka.clients.producer.ProducerConfig;
import org.apache.kafka.connect.json.JsonSerializer;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;
import org.springframework.kafka.core.DefaultKafkaProducerFactory;
import org.springframework.kafka.core.KafkaTemplate;
import org.springframework.kafka.core.ProducerFactory;

import com.fasterxml.jackson.databind.ser.std.StringSerializer;

import model.User;

@Configuration
public class KafkaConfiguration {
    
    @Bean
    public ProducerFactory<String,User> producerFactory()
    {
        Map<String,Object> config=new HashMap<>();
        
        config.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG,"127.0.0.1:9092");
        config.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG,StringSerializer.class);
        config.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG,JsonSerializer.class);
        return new DefaultKafkaProducerFactory<>(config);
    }
    
    @Bean
    public KafkaTemplate<String,User> kafkaTemplate()
    {
        return new KafkaTemplate<>(producerFactory());
    }

}

2- UserResource class

package com.example.demo;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.kafka.core.KafkaTemplate;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;
import org.springframework.web.bind.annotation.RequestMapping;
import org.springframework.web.bind.annotation.RestController;

import model.User;

@RestController
@RequestMapping("kafka")
public class UserResource {

    @Autowired
    KafkaTemplate<String,User> kafkatemplate;
    public static final String TOPIC="Kafka_Example";

    
    @GetMapping("/publish/{name}")
    public String postMessage(@PathVariable("name") final String name)
    {
        
    kafkatemplate.send(TOPIC,new User(name,"Technology",12000L));
    
    return "Published successfully";
    }
}

3- User class

package model;

public class User {

    private String name;
    private String dept;
    private long salary;
    
    
    public User(String name, String dept, long salary) {
        super();
        this.name = name;
        this.dept = dept;
        this.salary = salary;
    }
    

    public String getName() {
        return name;
    }
    public void setName(String name) {
        this.name = name;
    }
    public String getDept() {
        return dept;
    }
    public void setDept(String dept) {
        this.dept = dept;
    }
    public long getSalary() {
        return salary;
    }
    public void setSalary(long salary) {
        this.salary = salary;
    }
    
    
    
}

Can anyone please let me know where I am going wrong?Is it something regarding to imports(if so,what are the correct ones)?

Thanks

java_user
  • 13
  • 2
  • 7

2 Answers2

1

Solution

  1. You need to import string serializer and json serializer with this class
 org.apache.kafka.common.serialization.StringSerializer
 org.springframework.kafka.support.serializer.JsonSerializer
  1. Package name of you model class must be same with your controller class and spring application main class.

I follow these two things , issue has been resolved

Jatin Bansal
  • 123
  • 8
0

Your code correct but you import wrong StringSerializer use below import

org.apache.kafka.common.serialization.StringSerializer
org.springframework.kafka.support.serializer.JsonSerializer
S. Anushan
  • 728
  • 1
  • 6
  • 12
  • Thanks for your reply but even after these imports,it is throwing the same error,I am using "http://localhost:8081/kafka/publish/Hello" in browser and as soon as I hit this the error is there – java_user Jul 10 '21 at 16:06
  • Whitelabel Error Page This application has no explicit mapping for /error, so you are seeing this as a fallback. Sat Jul 10 21:47:59 IST 2021 There was an unexpected error (type=Internal Server Error, status=500). I am getting this on console and then error,i added one logging statement in that method too it is not being called only.However,if I pass String object instead of JSON it is working fine and consumer is able to consume – java_user Jul 10 '21 at 16:18
  • What json your passing ? Didn't get, in your URL only path variable bthere right? Are you sending anything additionally? – S. Anushan Jul 10 '21 at 16:31
  • And now you don't that deserialization error right? – S. Anushan Jul 10 '21 at 16:34
  • I am passing JSON(User Object) by my code- "kafkatemplate.send(TOPIC,new User(name,"Technology",12000L));" In the URL,I am only extracting name variable and sending other values as hard coded On Console,i am stiil getting "[Request processing failed; nested exception is org.apache.kafka.common.errors.SerializationException" which is mentioned in the question – java_user Jul 11 '21 at 03:59
  • On hitting this link "localhost:8081/kafka/publish/Hello" in browser,I am getting "Whitelabel Error Page This application has no explicit mapping for /error, so you are seeing this as a fallback. Sat Jul 10 21:47:59 IST 2021 There was an unexpected error (type=Internal Server Error, status=500)." – java_user Jul 11 '21 at 04:00
  • If I am passing a strng value rather than a JSON object,then it is working fine which is if I am writing "kafkatemplate.send(TOPIC, message);" then it is consuming my message – java_user Jul 11 '21 at 04:02
  • I also tried to add a logging statement inside UserResource method "@GetMapping("/publish/{name}") public String postMessage(@PathVariable("name") final String name) { System.out.println("inside this");" then "inside this is not getting printed on my console – java_user Jul 11 '21 at 04:04
  • For the same link "localhost:8081/kafka/publish/Hello",it is working for String and not JSON and I am trying to understand what is wrong here – java_user Jul 11 '21 at 04:05
  • Hey I think your older message causing the problem. – S. Anushan Jul 11 '21 at 04:21
  • Use above import – S. Anushan Jul 11 '21 at 04:21
  • bin/kafka-topics.sh --zookeeper 127.0.0.1:2181 --delete --topic someTopic – S. Anushan Jul 11 '21 at 04:22
  • And use again or else create new topic and publish the messages – S. Anushan Jul 11 '21 at 04:22
  • And I didn't see any wrong in your code may be due to old records.... Clear cache or delete the topic and create again as I said above. – S. Anushan Jul 11 '21 at 04:24
  • On creating new topic,the error is not there but still the messages are not being consumed – java_user Jul 17 '21 at 13:07