Spring org.springframework.beans.ConversionNotSupportedException同时覆盖父类的getter

问题描述

各位专家,您好,我想弄清楚为什么我的案例无法正常工作。
情况:
一个名为 AbstractCheckoutStepValidator 的类,这里是它的 xml 配置:

<bean id="abstractCheckoutStepValidator" class="...checkout.steps.validation.AbstractCheckoutStepValidator" abstract="true">
  <property name="checkoutFlowFacade" ref="checkoutFlowFacade"/>
  <property name="checkoutFacade" ref="checkoutFacade"/>
</bean>

代码

public abstract class AbstractCheckoutStepValidator implements CheckoutStepValidator
{
    private CheckoutFacade checkoutFacade;
    private CheckoutFlowFacade checkoutFlowFacade;

    @Override
    public abstract ValidationResults validateOnEnter(final RedirectAttributes redirectAttributes);

    @Override
    public ValidationResults validateOnExit()
    {
        return ValidationResults.SUCCESS;
    }

    public CheckoutFacade getCheckoutFacade()
    {
        return checkoutFacade;
    }

    @required
    public void setCheckoutFacade(final CheckoutFacade checkoutFacade)
    {
        this.checkoutFacade = checkoutFacade;
    }

    public CheckoutFlowFacade getCheckoutFlowFacade()
    {
        return checkoutFlowFacade;
    }

    @required
    public void setCheckoutFlowFacade(final CheckoutFlowFacade checkoutFlowFacade)
    {
        this.checkoutFlowFacade = checkoutFlowFacade;
    }

}

这里是 DefaultMultiStepCheckoutStepValidator 类,它扩展了 AbstractCheckoutStepValidator 并覆盖了它的 getter

public class DefaultMultiStepCheckoutStepValidator extends AbstractCheckoutStepValidator {
    private static final Logger LOGGER = Logger.getLogger(DefaultMultiStepCheckoutStepValidator.class);

    @Resource(name = "companyCheckoutFacade")
    private CompanyCheckoutFacade companyCheckoutFacade;


    // omitted code


    @Override
    public CompanyCheckoutFacade getCheckoutFacade() {
        return companyCheckoutFacade;
    }
}

这个类的xml配置:

<bean id="defaultMultiStepCheckoutValidator" class="...checkout.steps.validation.impl.DefaultMultiStepCheckoutStepValidator" parent="abstractCheckoutStepValidator" />

从技术角度来看应该没问题,如果 getter 返回父类,那么我可以使用它的子类之一,它是 CompanyCheckoutFacade extends CheckoutFacade。 ( 我有一个类似的例子,比如这里:

@Override
protected CompanyCartFacade getCartFacade() {
    return (CompanyCartFacade) super.getCartFacade();
}

在这里我确信返回的 bean 可以被转换为这个子类,这就是为什么我从父类调用 getter 并且这个 getter 在父类或子类中都可以正常工作)
同样在代码中,我通过注释注入依赖项,并且该字段与父类中的 checkoutFacade 字段无关... 如果我使用上面的代码启动服务器,则会出现以下错误

Error creating bean with name 'defaultMultiStepCheckoutValidator' defined in ServletContext resource [/WEB-INF/config/multi-step-checkout-config.xml]: Initialization of bean Failed; nested exception is org.springframework.beans.ConversionNotSupportedException: Failed to convert property value of type '...order.impl.DefaultCheckoutFacade' to required type '...facades.order.CompanyCheckoutFacade' for property 'checkoutFacade'; nested exception is java.lang.IllegalStateException: Cannot convert value of type '...order.impl.DefaultCheckoutFacade' to required type '...facades.order.CompanyCheckoutFacade' for property 'checkoutFacade': no matching editors or conversion strategy found
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveReference(BeanDeFinitionValueResolver.java:342) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveValueIfNecessary(BeanDeFinitionValueResolver.java:113) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.lambda$resolveManagedMap$1(BeanDeFinitionValueResolver.java:453) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at java.util.LinkedHashMap.forEach(LinkedHashMap.java:684) ~[?:?]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveManagedMap(BeanDeFinitionValueResolver.java:451) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveValueIfNecessary(BeanDeFinitionValueResolver.java:181) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.applyPropertyValues(AbstractAutowireCapablebeanfactory.java:1697) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.populateBean(AbstractAutowireCapablebeanfactory.java:1442) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.doCreateBean(AbstractAutowireCapablebeanfactory.java:593) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.createBean(AbstractAutowireCapablebeanfactory.java:516) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.Abstractbeanfactory.lambda$doGetBean$0(Abstractbeanfactory.java:324) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.Abstractbeanfactory.doGetBean(Abstractbeanfactory.java:322) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.Abstractbeanfactory.getBean(Abstractbeanfactory.java:202) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveReference(BeanDeFinitionValueResolver.java:330) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveValueIfNecessary(BeanDeFinitionValueResolver.java:113) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.lambda$resolveManagedMap$1(BeanDeFinitionValueResolver.java:453) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at java.util.LinkedHashMap.forEach(LinkedHashMap.java:684) ~[?:?]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveManagedMap(BeanDeFinitionValueResolver.java:451) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.BeanDeFinitionValueResolver.resolveValueIfNecessary(BeanDeFinitionValueResolver.java:181) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.applyPropertyValues(AbstractAutowireCapablebeanfactory.java:1697) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.populateBean(AbstractAutowireCapablebeanfactory.java:1442) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.doCreateBean(AbstractAutowireCapablebeanfactory.java:593) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.createBean(AbstractAutowireCapablebeanfactory.java:516) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.Abstractbeanfactory.lambda$doGetBean$0(Abstractbeanfactory.java:324) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.DefaultSingletonBeanRegistry.getSingleton(DefaultSingletonBeanRegistry.java:234) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.Abstractbeanfactory.doGetBean(Abstractbeanfactory.java:322) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.Abstractbeanfactory.getBean(Abstractbeanfactory.java:207) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.support.AbstractAutowireCapablebeanfactory.resolveBeanByName(AbstractAutowireCapablebeanfactory.java:453) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.context.annotation.CommonAnnotationBeanPostProcessor.autowireResource(CommonAnnotationBeanPostProcessor.java:527) ~[spring-context-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.context.annotation.CommonAnnotationBeanPostProcessor.getResource(CommonAnnotationBeanPostProcessor.java:497) ~[spring-context-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.context.annotation.CommonAnnotationBeanPostProcessor$ResourceElement.getResourcetoInject(CommonAnnotationBeanPostProcessor.java:650) ~[spring-context-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.annotation.InjectionMetadata$InjectedElement.inject(InjectionMetadata.java:239) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.beans.factory.annotation.InjectionMetadata.inject(InjectionMetadata.java:130) ~[spring-beans-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        at org.springframework.context.annotation.CommonAnnotationBeanPostProcessor.postProcessproperties(CommonAnnotationBeanPostProcessor.java:318) ~[spring-context-5.2.9.RELEASE.jar:5.2.9.RELEASE]
        ... 27 more


问题是
从上面的错误我真的不明白为什么 spring 试图将类型 '...order.impl.DefaultCheckoutFacade' 的属性值转换为属性 'checkoutFacade' 所需的类型 '...facades.order.CompanyCheckoutFacade'。我没有在我的 getter 中的任何地方使用 checkoutFacade 属性DefaultCheckoutFacadeCheckoutFacade 接口的认实现,我确定xml 配置中的checkoutFacade ref 指的是正确的实现,这里:

<alias name="defaultCheckoutFacade" alias="checkoutFacade"/>
<bean id="defaultCheckoutFacade" class="...order.impl.DefaultCheckoutFacade">
    // properties are omitted
</bean>

我是我的班级,我是说 getter 应该返回不同的实现,仅此而已。 为了摆脱这个错误,我只需要重命名 getter 并且不要覆盖父类中的那个,但我不明白为什么覆盖 getter 的方法不起作用?

感谢您花时间回答问题。

解决方法

暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!

如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。

小编邮箱:dio#foxmail.com (将#修改为@)