Java異常之----org.springframework.beans.factory.UnsatisfiedDependencyException:FeignClient註解及參數問題

本文目錄

一、背景描述

二、錯誤信息

三、出錯原因

四、解決方案


一、背景描述

在用分佈式架構SpringBoot的SpringCloud技術開發過程中,FeignClient 是一個常用的註解,且很重要的功能。

簡單理解就是,分佈式架構服務之間,各子模塊系統內部通信的核心。一般在一個系統調用另一個系統的接口時使用,註解如下:

@FeignClient(contextId = "hostControlClient", value = SystemConstant.APPLICATION_NAME)
public interface HostControlClient {
    
    /**
     * 主機重啓
     * @param sn
     * @return
     */
    @PostMapping(value = "/host/reboot")
    CommResponse hostReboot(@RequestParam("sn") String sn);
    
    /**
     * 修改主機oem
     * @param sn
     * @param oemFirm
     * @return
     */
    @PostMapping(value = "/host/updateOem")
    CommResponse updateOemFirm(@RequestParam("sn") String sn, @RequestParam("sn") String oemFirm);

}

該註解一般創建在 interface 接口中,然後在業務類@Autowired 進去使用非常簡單方便。 

二、錯誤信息

創建好interface接口後,當然要把調用該服務的接口方法定義出來,該方法對應着本FeignClient服務的controller接口,必須重寫該接口方法(返回對象,參數值完全一樣)。比如下面的Controller

@Slf4j
@Api(value = "hostControlClient", tags = "下發主機api接口")
@RestController
public class HostControlClientController implements HostControlClient {

    @Autowired
    private HostControlService hostControlService;

    // 以下是很多方法
}

但是啓動這個項目的時候,控制檯日誌報錯,完整錯誤信息如下:

org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'hostControlClientController': Unsatisfied dependency expressed through field 'hostControlClientService'; nested exception is org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'hostControlClientServiceImpl' defined in file [G:\****\2項目代碼\trunk\雲端\back-iot-operation(家居運營平臺)\back-iot-operation\iot-operation-business\target\classes\com\uiotsoft\back\iotoperation\business\service\impl\HostControlClientServiceImpl.class]: Unsatisfied dependency expressed through constructor parameter 0; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'com.uiotsoft.back.iotdevice.api.client.host.HostControlClient': FactoryBean threw exception on object creation; nested exception is java.lang.UnsupportedOperationException
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:596)
	at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:90)
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor.postProcessProperties(AutowiredAnnotationBeanPostProcessor.java:374)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.populateBean(AbstractAutowireCapableBeanFactory.java:1411)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:592)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:515)
	at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:320)
	at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:318)
	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:199)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.preInstantiateSingletons(DefaultListableBeanFactory.java:843)
	at org.springframework.context.support.AbstractApplicationContext.finishBeanFactoryInitialization(AbstractApplicationContext.java:877)
	at org.springframework.context.support.AbstractApplicationContext.refresh(AbstractApplicationContext.java:549)
	at org.springframework.boot.web.servlet.context.ServletWebServerApplicationContext.refresh(ServletWebServerApplicationContext.java:142)
	at org.springframework.boot.SpringApplication.refresh(SpringApplication.java:775)
	at org.springframework.boot.SpringApplication.refreshContext(SpringApplication.java:397)
	at org.springframework.boot.SpringApplication.run(SpringApplication.java:316)
	at org.springframework.boot.SpringApplication.run(SpringApplication.java:1260)
	at org.springframework.boot.SpringApplication.run(SpringApplication.java:1248)
	at com.uiotsoft.back.iotoperation.MainServer.main(MainServer.java:23)
Caused by: org.springframework.beans.factory.UnsatisfiedDependencyException: Error creating bean with name 'hostControlClientServiceImpl' defined in file [G:\****\2項目代碼\trunk\雲端\back-iot-operation(家居運營平臺)\back-iot-operation\iot-operation-business\target\classes\com\uiotsoft\back\iotoperation\business\service\impl\HostControlClientServiceImpl.class]: Unsatisfied dependency expressed through constructor parameter 0; nested exception is org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'com.uiotsoft.back.iotdevice.api.client.host.HostControlClient': FactoryBean threw exception on object creation; nested exception is java.lang.UnsupportedOperationException
	at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:769)
	at org.springframework.beans.factory.support.ConstructorResolver.autowireConstructor(ConstructorResolver.java:218)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.autowireConstructor(AbstractAutowireCapableBeanFactory.java:1341)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBeanInstance(AbstractAutowireCapableBeanFactory.java:1187)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.doCreateBean(AbstractAutowireCapableBeanFactory.java:555)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.createBean(AbstractAutowireCapableBeanFactory.java:515)
	at org.springframework.beans.factory.support.AbstractBeanFactory.lambda$doGetBean$0(AbstractBeanFactory.java:320)
	at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:222)
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:318)
	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:199)
	at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:277)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1248)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1168)
	at org.springframework.beans.factory.annotation.AutowiredAnnotationBeanPostProcessor$AutowiredFieldElement.inject(AutowiredAnnotationBeanPostProcessor.java:593)
	... 19 common frames omitted
Caused by: org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'com.uiotsoft.back.iotdevice.api.client.host.HostControlClient': FactoryBean threw exception on object creation; nested exception is java.lang.UnsupportedOperationException
	at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.doGetObjectFromFactoryBean(FactoryBeanRegistrySupport.java:178)
	at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.getObjectFromFactoryBean(FactoryBeanRegistrySupport.java:101)
	at org.springframework.beans.factory.support.AbstractBeanFactory.getObjectForBeanInstance(AbstractBeanFactory.java:1674)
	at org.springframework.beans.factory.support.AbstractAutowireCapableBeanFactory.getObjectForBeanInstance(AbstractAutowireCapableBeanFactory.java:1249)
	at org.springframework.beans.factory.support.AbstractBeanFactory.doGetBean(AbstractBeanFactory.java:257)
	at org.springframework.beans.factory.support.AbstractBeanFactory.getBean(AbstractBeanFactory.java:199)
	at org.springframework.beans.factory.config.DependencyDescriptor.resolveCandidate(DependencyDescriptor.java:277)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.addCandidateEntry(DefaultListableBeanFactory.java:1471)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.findAutowireCandidates(DefaultListableBeanFactory.java:1428)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.doResolveDependency(DefaultListableBeanFactory.java:1211)
	at org.springframework.beans.factory.support.DefaultListableBeanFactory.resolveDependency(DefaultListableBeanFactory.java:1168)
	at org.springframework.beans.factory.support.ConstructorResolver.resolveAutowiredArgument(ConstructorResolver.java:857)
	at org.springframework.beans.factory.support.ConstructorResolver.createArgumentArray(ConstructorResolver.java:760)
	... 32 common frames omitted
Caused by: java.lang.UnsupportedOperationException: null
	at java.util.Collections$UnmodifiableCollection.add(Collections.java:1055)
	at org.springframework.cloud.openfeign.support.FeignUtils.addTemplateParameter(FeignUtils.java:60)
	at org.springframework.cloud.openfeign.support.SpringMvcContract$SimpleAnnotatedParameterContext.setTemplateParameter(SpringMvcContract.java:460)
	at org.springframework.cloud.openfeign.annotation.RequestParamParameterProcessor.processArgument(RequestParamParameterProcessor.java:69)
	at org.springframework.cloud.openfeign.support.SpringMvcContract.processAnnotationsOnParameter(SpringMvcContract.java:292)
	at feign.Contract$BaseContract.parseAndValidateMetadata(Contract.java:110)
	at org.springframework.cloud.openfeign.support.SpringMvcContract.parseAndValidateMetadata(SpringMvcContract.java:188)
	at feign.Contract$BaseContract.parseAndValidatateMetadata(Contract.java:66)
	at feign.hystrix.HystrixDelegatingContract.parseAndValidatateMetadata(HystrixDelegatingContract.java:46)
	at feign.ReflectiveFeign$ParseHandlersByName.apply(ReflectiveFeign.java:154)
	at feign.ReflectiveFeign.newInstance(ReflectiveFeign.java:52)
	at feign.Feign$Builder.target(Feign.java:251)
	at org.springframework.cloud.openfeign.HystrixTargeter.target(HystrixTargeter.java:55)
	at org.springframework.cloud.openfeign.FeignClientFactoryBean.loadBalance(FeignClientFactoryBean.java:238)
	at org.springframework.cloud.openfeign.FeignClientFactoryBean.getTarget(FeignClientFactoryBean.java:267)
	at org.springframework.cloud.openfeign.FeignClientFactoryBean.getObject(FeignClientFactoryBean.java:247)
	at org.springframework.beans.factory.support.FactoryBeanRegistrySupport.doGetObjectFromFactoryBean(FactoryBeanRegistrySupport.java:171)
	... 44 common frames omitted

三、出錯原因

看上面一背景描述裏的代碼第二個方法 updateOemFirm()的參數定義時,@RequestParam兩個參數名字一樣,而在Spring 4.0版本後,@RequestParam 註解對參數傳值有了很好的封裝特性並嚴格校驗的原因,檢測到兩個參數名一樣,故導致這此報錯。

CommResponse updateOemFirm(@RequestParam("sn") String sn, @RequestParam("sn") String oemFirm);

四、解決方案

將上述的錯誤寫法修改爲:

CommResponse updateOemFirm(@RequestParam("sn") String sn, @RequestParam("oemFirm") String oemFirm);

項目重啓,問題得到完美解決。

 

 

拓展資料:那天晚上和@FeignClient註解的深度交流:https://www.jianshu.com/p/41aa8f8f6ad4

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章