SpringBoot Kafka: ไม่ได้โหลดวิธี Bean 'kafkaTemplate' ใน 'KafkaAutoConfiguration'

ฉันใช้ springboot และพยายามเขียน KafkaProducer เพื่อส่งข้อความในคิว Kafka ฉันได้สร้างวิธีการเหล่านี้ในคลาส @Configuration

@Bean
public KafkaTemplate<String, String> kafkaTemplate(){
    return new KafkaTemplate<>(producerFactory());
}

@Bean
public ProducerFactory<String, String> producerFactory() {
    Map<String, Object> configProps = new HashMap<>();
    configProps.put(ProducerConfig.BOOTSTRAP_SERVERS_CONFIG, bootstrapAddress); //bootstrapAddress holds address of kafka server
    configProps.put(ProducerConfig.KEY_SERIALIZER_CLASS_CONFIG, StringSerializer.class);
    configProps.put(ProducerConfig.VALUE_SERIALIZER_CLASS_CONFIG, StringSerializer.class);
    return new DefaultKafkaProducerFactory<>(configProps);
}

และฉันได้ Autowired KafkaTemplate bean นี้ในคลาส KafkaMessageProducer ของฉันที่ดูแลการจัดการฟังก์ชันการส่งของ KafkaTemplate

@Autowired
KafkaTemplate<String, String> kafkaTemplate;

แต่ฉันกำลังเผชิญกับข้อผิดพลาดนี้เมื่อฉันพยายามรวบรวมโค้ด

Field kafkaTemplate in <pathoffile>.KafkaMessageProducer required a bean of type 'org.springframework.kafka.core.KafkaTemplate' that could not be found.
    - Bean method 'kafkaTemplate' in 'KafkaAutoConfiguration' not loaded because @ConditionalOnMissingBean (types: org.springframework.kafka.core.KafkaTemplate; SearchStrategy: all) found bean 'avroKafkaTemplate'
Action:Consider revisiting the conditions above or defining a bean of type 'org.springframework.kafka.core.KafkaTemplate' in your configuration.

นอกจากนี้ หากฉันพยายามแยก KafkaAutoConfiguration ในโปรเจ็กต์ Spring ของฉัน ฉันได้รับข้อผิดพลาดว่า Bean ไม่สามารถโหลดได้เนื่องจาก KafkaAutoConfiguration ถูกปิดใช้งาน' มีความคิดใดว่าทำไมฉันถึงได้รับข้อผิดพลาด Bean นี้และอะไรคือวิธีแก้ปัญหา

แก้ไข: - ฉันพบ bean ต่อไปนี้ในไฟล์ jar ที่โปรเจ็กต์ของฉันใช้

@Bean
@Conditional({EnableQueueCondition.class})
public KafkaTemplate<String, String> kafkaTemplate() {
    KafkaTemplate<String, String> kafkaTemplate = new KafkaTemplate(this.producerFactory());
    kafkaTemplate.setProducerListener(new ProducerListenerImpl());
    return kafkaTemplate;
}

นี่คือที่มาของข้อผิดพลาด แต่ฉันไม่รู้ว่าจะบอกสปริงไม่ให้มองถั่วนี้ได้อย่างไร และใช้ถั่วที่ฉันกำหนดไว้ ฉันได้ลองใช้คำอธิบายประกอบหลักและรอบคัดเลือกบน bean แล้ว แต่ก็ยังให้ข้อผิดพลาดเดิม อาจมีความเป็นไปได้หรือไม่ที่ bean ที่ฉันกำหนดไว้จะไม่ถูกสร้างขึ้นหรือไม่พบ และ KafkaAutoConfiguration กำลังมองหา bean เริ่มต้นที่ถูกแทนที่โดย avroKafkaTemplate bean วิธีแก้ปัญหานี้อาจมีอะไรบ้าง?


person Vishal Rastogi    schedule 09.09.2020    source แหล่งที่มา


คำตอบ (2)


จากสแต็กเทรซ มี KafkaTemplate bean อีกอัน - avroKafkaTemplate ดังนั้นฉันเดาว่ามีการกำหนดค่าอื่นที่ทำซ้ำคำจำกัดความ KafkaTemplate

person Mikalai Lushchytski    schedule 09.09.2020
comment
ใช่อาจจะแต่ฉันไม่แน่ใจ คุณคิดว่าฉันจะแก้ไขปัญหานี้ได้อย่างไร? - person Vishal Rastogi; 09.09.2020
comment
คุณมีการกำหนดค่าด้วยวิธี avroKafkaTemplate() หรือไม่? นี่คือ bean แบบกำหนดเองอย่างแน่นอน - person Mikalai Lushchytski; 09.09.2020
comment
Codebase ที่ฉันทำงานอยู่นั้นค่อนข้างใหญ่ แต่แม้จะค้นหาผ่านมัน ฉันไม่พบรายการที่ตรงกับ avroKafkaTemplate เลย - person Vishal Rastogi; 09.09.2020
comment
คุณมีการพึ่งพาใด ๆ ที่ให้การกำหนดค่าของตนเองหรือไม่? เช่นเดียวกับโมดูลย่อยอื่น ๆ ซึ่งมีการกำหนดค่า bean ด้วย ? - person Mikalai Lushchytski; 09.09.2020
comment
ใช่ มีพวกมันเยอะมาก - person Vishal Rastogi; 09.09.2020
comment
ดังนั้น อาจเป็นหนึ่งในนั้นที่นิยาม avroKafkaTemplate bean - person Mikalai Lushchytski; 09.09.2020
comment
คุณช่วยลองเพิ่ม @Primary ตัวระบุให้กับคำจำกัดความ KafkaTemplate bean ของคุณได้ไหม - person Mikalai Lushchytski; 09.09.2020
comment
ใช่ ฉันลองแล้วและ @Qualifier ด้วย แต่ยังคงมีข้อผิดพลาดเหมือนเดิม นอกจากนี้ ฉันยังพบ Bean ที่มี avroKafkaTemplate ในไฟล์ jar ที่โปรเจ็กต์ของฉันใช้อยู่ ดังนั้น Spring จึงได้รับ bean นี้ แต่ฉันคิดว่า avroKafkaTemplate จะถูกค้นหาเฉพาะเมื่อไม่พบ KafkaTemplate bean (ที่ฉันกำหนดไว้) และ bean เริ่มต้นจะไม่ถูกส่งคืนเนื่องจาก avroKafka bean นี้ คุณคิดว่าเราอาจทำอะไรในสถานการณ์นี้? - person Vishal Rastogi; 09.09.2020
comment
คลาส @Configuration ของคุณถูกกำหนดอย่างถูกต้องและโหลดแล้วหรือไม่ คุณช่วยยืนยันได้ไหมว่าคำจำกัดความ KafkaTemplate bean ของคุณโหลดจริงแล้ว ตัวอย่างเช่น พิมพ์ไปที่คอนโซลภายในวิธี - person Mikalai Lushchytski; 09.09.2020

โดยค่าเริ่มต้น spring boot ให้ KafkaTemplate bean หากคุณเพิ่มการพึ่งพา kafka ใน POM

คุณเพียงแค่ต้องกำหนดคุณสมบัติในตัวอย่างไฟล์ application.yml ของคุณ:

server: port: 9000
spring:
   kafka:
     consumer:
        bootstrap-servers: localhost:9092
        group-id: group_id
        auto-offset-reset: earliest
        key-deserializer: org.apache.kafka.common.serialization.StringDeserializer
        value-deserializer: org.apache.kafka.common.serialization.StringDeserializer
     producer:
        bootstrap-servers: localhost:9092
        key-serializer: org.apache.kafka.common.serialization.StringSerializer
        value-serializer: org.apache.kafka.common.serialization.StringSerializer

เปิดใช้งานการกำหนดค่าอัตโนมัติ

@Configuration
@EnableKafka

และ autowire the kafkaTemplate:

 @Autowired
 private KafkaTemplate<String, String> kafkaTemplate;

หากกรณีของคุณ โรงงานกำหนดค่าอัตโนมัติกำลังมองหา ProducerFactory<String, Strng>ซึ่งไม่ตรงกับการกำหนดค่าของคุณ

 @Bean
 @ConditionalOnMissingBean(ProducerFactory.class)
        public ProducerFactory<String, Strng> kafkaProducerFactory()

ดังนั้นเปลี่ยนชื่อ ProducerFactory() ของคุณเป็น kafkaProducerFactory() มันจะแก้ปัญหาของคุณได้

person Imran Ahmad    schedule 09.09.2020
comment
Imran การเปลี่ยนชื่อ ProducerFactory() เป็น kafkaProducerFactory() ใช้งานไม่ได้ แต่ก็ยังแสดงข้อผิดพลาดเดิม เพิ่มการพึ่งพาในไฟล์ POM - person Vishal Rastogi; 09.09.2020
comment
ในโค้ดของฉันมันใช้งานได้.... ฉันเพิ่งกำหนด bean ของฉันแบบนี้: @Bean public KafkaTemplate kafkaTemplate(ProducerFactory‹String, String› pf) { return new KafkaTemplate(pf); } ตรวจสอบให้แน่ใจว่าใช้ EnableAutoConfiguration - person Imran Ahmad; 09.09.2020
comment
ใช่ เปิดใช้งานแล้ว ฉันได้อัปเดตคำถามพร้อมรายละเอียดเพิ่มเติมแล้ว โปรดดูและดูว่าอาจช่วยแก้ปัญหาได้หรือไม่ - person Vishal Rastogi; 09.09.2020
comment
หากไม่จำเป็นต้องใช้ bean นั้นในโปรเจ็กต์ของคุณ คุณสามารถยกเว้นคลาสเฉพาะไม่ให้ถูกสแกนเป็น bean ด้วยพารามิเตอร์ละเว้นฟิลเตอร์ของคำอธิบายประกอบ @ComponentScan ตัวอย่าง: @ComponentScan(value = {'com.xyz.abc'}, excludeFilters = { @ComponentScan.Filter(type = FilterType.ASSIGNABLE_TYPE, คลาส = { firstClass.class, SecondClass.class }) }) - person Imran Ahmad; 09.09.2020