JPA Inheritance entitymanager.find produces ClassCastException
我有一个像这样的类层次结构:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 | @Entity @Table (name="call_distribution_policies") @Inheritance (strategy=InheritanceType.JOINED) public class CallDistributionPolicy implements Serializable, Cloneable{ ---------------- } @Entity @Table(name="skill_based_call_distribution_policies") public class SkillBasedCallDistributionPolicy extends CallDistributionPolicy { -------------- } public class CallDistributionPolicyDAOJPAImpl extends AbstractJPADAOImpl<CallDistributionPolicy> implements CallDistributionPolicyDAO { } public CallDistributionPolicy get(long id) { try { Query query = entityManager .createQuery("from CallDistributionPolicy where id = :id"); query.setParameter("id", id); List<CallDistributionPolicy> resultList = query.getResultList(); if (!CollectionUtils.isEmpty(resultList)) { return resultList.get(0); } return null; } catch (EntityNotFoundException e) { return null; } } } |
当我这样做时:
log.debug("已加载:" callDistributionPolicyDao.get(10).toString())
它显示SkillsBasedCallDistributionPolicy
的toString()
但是当我尝试像这样投射它时:
1 | SkillsBasedCallDistributionPolicy scdp = (SkillsBasedCallDistributionPolicy) callDistributionPolicyDao.get(10) |
我收到类强制转换异常。
1 | com.vantage.callcenter.core.entity.acd.CallDistributionPolicy$$EnhancerByCGLIB$$334f3d1b cannot be cast to com.vantage.callcenter.core.entity.acd.SkillBasedCallDistributionPolicy |
instanceof检查也失败了!
当我在Eclipse中检查对象时,我看到了CGLIB代理,但是据我了解,CGLIB代理应该扩展SkillsBasedCallDistributionPolicy类吗?在CGLIB $ CALLBACK_0属性中,我可以看到实体类是" CallDistributionPolicy ",但目标是" SkillsBasedCallDistributionPolicy "。
加载子类的正确过程应该是什么?我可以看到hibernate正在生成所有正确的SQL并加载正确的子类,但是如何检查instanceof并将其转换为子类呢?
我正在使用hibernate 3.2.1,Spring 2.5.5,cglib2.1_3。有什么建议吗?
我知道很长一段时间以来这在Hibernate中都是一个问题,例如:
- ClassCastException cglib延迟加载
- JPA:instanceof与hibernate代理:什么时候安全?
- 使用Hibernate代理对象时如何避免ClassCastExceptions)
问题是,我的意思是错误,
但是我无法重现Hibernate 3.3.0.SP1的问题。
1 2 3 4 5 | <dependency> <groupId>org.hibernate</groupId> hibernate-cglib-repack</artifactId> <version>2.1_3</version> </dependency> |
和
1 2 3 4 5 | <dependency> <groupId>javassist</groupId> javassist</artifactId> <version>3.8.0.GA</version> </dependency> |
我很确定这是一个Jira问题,但找不到它。
The problem(bug) is consistent across my application. Can you post your working pom.xml here so I can see exactly what hibernate dependencies are you using?
在我使用的依赖项下面:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | <project> ... <dependencyManagement> <dependencies> <dependency> <groupId>org.slf4j</groupId> slf4j-api</artifactId> <version>1.5.10</version> </dependency> </dependencies> </dependencyManagement> ... <dependencies> <dependency> <groupId>org.hibernate</groupId> hibernate-entitymanager</artifactId> <version>3.4.0.GA</version> <exclusions> <exclusion> <groupId>javassist</groupId> javassist</artifactId> </exclusion> </exclusions> </dependency> <dependency> <groupId>org.hibernate</groupId> hibernate-cglib-repack</artifactId> <version>2.1_3</version> </dependency> ... </dependencies> </project> |
这是依赖关系树:
1 2 3 4 5 6 7 8 9 10 11 12 13 | [INFO] +- org.hibernate:hibernate-entitymanager:jar:3.4.0.GA:compile [INFO] | +- org.hibernate:ejb3-persistence:jar:1.0.2.GA:compile [INFO] | +- org.hibernate:hibernate-commons-annotations:jar:3.1.0.GA:compile [INFO] | +- org.hibernate:hibernate-annotations:jar:3.4.0.GA:compile [INFO] | +- org.hibernate:hibernate-core:jar:3.3.0.SP1:compile [INFO] | | +- antlr:antlr:jar:2.7.6:compile [INFO] | | \\- commons-collections:commons-collections:jar:3.1:compile [INFO] | +- org.slf4j:slf4j-api:jar:1.5.10:compile [INFO] | +- dom4j:dom4j:jar:1.6.1:compile [INFO] | | \\- xml-apis:xml-apis:jar:1.0.b2:compile [INFO] | \\- javax.transaction:jta:jar:1.1:compile ... [INFO] \\- org.hibernate:hibernate-cglib-repack:jar:2.1_3:compile |