【问题标题】:Object is not an 'instanceof' it's own class对象不是“实例”,它是自己的类
【发布时间】:2014-11-17 18:16:28
【问题描述】:

我正在尝试解决 spring 不使用 factoryBean 的一些问题。我已插入调试器并证明故障出在 AbstraceBeanFactory 的这一行:

if(!(beanInstance instanceof FactoryBean) || BeanFactoryUtils.isFactoryDereference(name)) {
   return beanInstance;
}

特别是“beanInstance instanceof FactoryBean”部分在它应该为真时返回假,导致我返回一个 factorybean 而不是工厂应该构造的 bean。

我的调试器清楚地告诉我 beanInstance 是一个 org.springframework.beans.factory.config.PropertiesFactoryBean。当我告诉 eclipse 扩展 bean 的类时,我看到它清楚地实现了 FactoryBean

为了进一步测试,我去了表达式。假设表达式:

beanInstance instanceof org.springframework.beans.factory.config.PropertiesFactoryBean

返回假。但是 beanInstance.getClass() 返回

(org.springframework.beans.factory.config.PropertiesFactoryBean) (id=112)

看来我的虚拟机对这个类很困惑。我正在尝试找出导致这种混乱的原因,以及如何解决它?

最可能的情况似乎是多个类加载器之间的混淆,但我没有找到任何明显的例子。我的类路径中应该只有一个 PropertiesFactoryBean 实现。

什么会导致 instanceof 以这种方式失败?我怎样才能找到我的根本原因?

顺便说一句,如果相关的话,这最终是我正在调试的一个 tomcat 实例。另外,beanInstance 一个 instanceof 对象,所以 intanceof 有时确实可以正常工作。

ps。我不得不手动输入,而不是复制/粘贴。请假设任何明显的命名错误都是我的拼写错误。

编辑:修复了 cmets 中提到的括号错字。我想我会那样做。这段代码来自 Spring 未经我修改,因此可以安全地假设代码本身编写得很好且功能齐全,即使我确实打错了

【问题讨论】:

  • 你知道你有!,对吧?
  • 还有放错位置的括号。
  • beanInstance的类加载器和FactoryBean的类加载器一样吗?
  • 您能否检查表达式class.forName("org.springframework.beans.factory.config.PropertiesFactoryBean") 是否返回与beanInstance.getClass() 相同的ID?
  • 我知道有一个!那里。问题是 beanInstance 实现了 FactoryBean,由于 !.但是,它正在返回,因为 instanceof 检查返回的是 false 而不是 true。

标签: java spring classloader instanceof


【解决方案1】:

如果您有多个 webapp(或同一个 webapp 的多个版本,以防您使用 Tomcat 的热部署功能),每个 webapp 都将拥有自己的类加载器,以及另一个加载 Tomcat lib 中所有内容的类加载器文件夹(它是其他类加载器的父级)。

所以,如果您正在检查的接口在您的战争中(或在您的战争部署的库中),并且您部署了多个 web 应用程序(可能其中一些已经取消部署,但对对象的一些引用仍然存在),假设它是一个类加载器问题(特别是当您已经确认实例上的getClass()Class.forName 返回不同的对象时。在两个类对象上调用getClassLoader(Tomcat 的类加载器有很好的toString 方法)并且您可能知道哪个类他们来自的加载器/webapp。

可能的短期修复是将包含接口的 jar 移到 war 之外,并将其放入 tomcat 的 lib 文件夹中。

当然,长期修复是追查根本原因并修复它:)

【讨论】:

  • 我只有一个 webapp。但是,该问题发生在身份验证领域中,该领域在对该特定战争进行身份验证之前运行。我相信这意味着类路径中唯一的东西是 tomcat6/lib 文件。我运行了一个快速脚本来验证该路径中只有一个战争提供了每种相关方法。我还检查了我的战争库,它似乎没有提供任何类。事实上,我的计算机上似乎只有两个 spring-beans 库副本,我的 mvn repo 和 tomcat6/lib 目录。
猜你喜欢
  • 2012-06-11
  • 2013-05-17
  • 1970-01-01
  • 2013-04-01
  • 2012-11-26
  • 1970-01-01
  • 1970-01-01
  • 2019-08-01
  • 2017-05-05
相关资源
最近更新 更多