2011-07-05 30 views
0

我在Hibernate論壇上問了這個問題一個星期沒有anwser - https://forum.hibernate.org/viewtopic.php?f=1&t=1011634。我很困難,希望能在這裏得到幫助。我從org.hibernate.engine.StatefulPersistenceContext得到了NullPointerException。NullPointerEx在org.hibernate.engine.StatefulPersistenceContext行1401

我休眠依賴性如下: org.hibernate作爲 的Hibernate的EntityManager 3.5.6決賽

異常堆棧低於:

 2011-07-04 07:06:38,691 DEBUG [http-8080-2] mobi.esca.mobile.remoting.HttpInvokerServiceExporter (HttpInvokerServiceExporter.java:168) - java.lang.NullPointerException 
java.lang.NullPointerException 
at org.hibernate.engine.StatefulPersistenceContext.replaceDelayedEntityIdentityInsertKeys(StatefulPersistenceContext.java:1401) 
at org.hibernate.action.EntityIdentityInsertAction.postInsert(EntityIdentityInsertAction.java:117) 
at org.hibernate.action.EntityIdentityInsertAction.execute(EntityIdentityInsertAction.java:89) 
at org.hibernate.engine.ActionQueue.execute(ActionQueue.java:267) 
at org.hibernate.engine.ActionQueue.executeActions(ActionQueue.java:259) 
at org.hibernate.engine.ActionQueue.executeInserts(ActionQueue.java:169) 
at org.hibernate.event.def.AbstractSaveEventListener.performSaveOrReplicate(AbstractSaveEventListener.java:287) 
at org.hibernate.event.def.AbstractSaveEventListener.performSave(AbstractSaveEventListener.java:204) 
at org.hibernate.event.def.AbstractSaveEventListener.saveWithGeneratedId(AbstractSaveEventListener.java:130) 
at org.hibernate.ejb.event.EJB3PersistEventListener.saveWithGeneratedId(EJB3PersistEventListener.java:69) 
at org.hibernate.event.def.DefaultPersistEventListener.entityIsTransient(DefaultPersistEventListener.java:179) 
at org.hibernate.event.def.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:135) 
at org.hibernate.event.def.DefaultPersistEventListener.onPersist(DefaultPersistEventListener.java:61) 
at org.hibernate.impl.SessionImpl.firePersist(SessionImpl.java:800) 
at org.hibernate.impl.SessionImpl.persist(SessionImpl.java:774) 
at org.hibernate.impl.SessionImpl.persist(SessionImpl.java:778) 
at org.hibernate.ejb.AbstractEntityManagerImpl.persist(AbstractEntityManagerImpl.java:668) 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
at java.lang.reflect.Method.invoke(Method.java:597) 
at org.springframework.orm.jpa.ExtendedEntityManagerCreator$ExtendedEntityManagerInvocationHandler.invoke(ExtendedEntityManagerCreator.java:365) 
at $Proxy138.persist(Unknown Source) 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
at java.lang.reflect.Method.invoke(Method.java:597) 
at org.springframework.orm.jpa.SharedEntityManagerCreator$SharedEntityManagerInvocationHandler.invoke(SharedEntityManagerCreator.java:240) 
at $Proxy59.persist(Unknown Source) 
at org.springframework.orm.jpa.JpaTemplate$5.doInJpa(JpaTemplate.java:264) 
at org.springframework.orm.jpa.JpaTemplate.execute(JpaTemplate.java:183) 
at org.springframework.orm.jpa.JpaTemplate.persist(JpaTemplate.java:262) 
at mobi.esca.persistence.GenericJPARepository.persist(GenericJPARepository.java:153) 
at mobi.esca.persistence.GenericJPARepository.persistAll(GenericJPARepository.java:161) 
at mobi.esca.mars.application.UsageManager.logUsageStats(UsageManager.java:43) 
at mobi.esca.mars.interfaces.mobile.EndUserController.reportStats(EndUserController.java:259) 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
at java.lang.reflect.Method.invoke(Method.java:597) 
at org.springframework.aop.support.AopUtils.invokeJoinpointUsingReflection(AopUtils.java:309) 
at org.springframework.aop.framework.JdkDynamicAopProxy.invoke(JdkDynamicAopProxy.java:196) 
at $Proxy137.reportStats(Unknown Source) 
at sun.reflect.NativeMethodAccessorImpl.invoke0(Native Method) 
at sun.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:39) 
at sun.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:25) 
at java.lang.reflect.Method.invoke(Method.java:597) 
at mobi.esca.mobile.remoting.RemoteInvocationAdaptor.invoke(RemoteInvocationAdaptor.java:89) 
at mobi.esca.mobile.remoting.RemoteInvocationAdaptor.proceed(RemoteInvocationAdaptor.java:54) 
at mobi.esca.mobile.remoting.FilterChain.doFilter(FilterChain.java:59) 
at mobi.esca.mobile.remoting.MethodInvocationRateFromUserProtection.doFilter(MethodInvocationRateFromUserProtection.java:56) 
at mobi.esca.mobile.remoting.FilterChain.doFilter(FilterChain.java:56) 
at mobi.esca.mobile.remoting.MethodInvocationRateFromIpProtection.doFilter(MethodInvocationRateFromIpProtection.java:57) 
at mobi.esca.mobile.remoting.FilterChain.doFilter(FilterChain.java:56) 
at mobi.esca.mars.interfaces.mobile.ClientVersionChecker.doFilter(ClientVersionChecker.java:41) 
at mobi.esca.mobile.remoting.FilterChain.doFilter(FilterChain.java:56) 
at mobi.esca.mobile.remoting.AuthenticationFilter.doFilter(AuthenticationFilter.java:37) 
at mobi.esca.mobile.remoting.FilterChain.doFilter(FilterChain.java:56) 
at mobi.esca.mobile.remoting.HttpInvokerServiceExporter.invokeAndCreateResult(HttpInvokerServiceExporter.java:201) 
at mobi.esca.mobile.remoting.HttpInvokerServiceExporter.handleRequestInternal(HttpInvokerServiceExporter.java:128) 
at mobi.esca.mobile.remoting.HttpInvokerServiceExporter.handleRequest(HttpInvokerServiceExporter.java:102) 
at org.springframework.web.servlet.mvc.HttpRequestHandlerAdapter.handle(HttpRequestHandlerAdapter.java:49) 
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:790) 
at org.springframework.web.servlet.DispatcherServlet.doService(DispatcherServlet.java:719) 
at org.springframework.web.servlet.FrameworkServlet.processRequest(FrameworkServlet.java:644) 
at org.springframework.web.servlet.FrameworkServlet.doPost(FrameworkServlet.java:560) 
at javax.servlet.http.HttpServlet.service(HttpServlet.java:637) 
at javax.servlet.http.HttpServlet.service(HttpServlet.java:717) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:290) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.springframework.web.filter.CharacterEncodingFilter.doFilterInternal(CharacterEncodingFilter.java:88) 
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:76) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.springframework.orm.jpa.support.OpenEntityManagerInViewFilter.doFilterInternal(OpenEntityManagerInViewFilter.java:113) 
at org.springframework.web.filter.OncePerRequestFilter.doFilter(OncePerRequestFilter.java:76) 
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter(ApplicationFilterChain.java:235) 
at org.apache.catalina.core.ApplicationFilterChain.doFilter(ApplicationFilterChain.java:206) 
at org.apache.catalina.core.StandardWrapperValve.invoke(StandardWrapperValve.java:219) 
at org.apache.catalina.core.StandardContextValve.invoke(StandardContextValve.java:191) 
at org.apache.catalina.core.StandardHostValve.invoke(StandardHostValve.java:127) 
at org.apache.catalina.valves.ErrorReportValve.invoke(ErrorReportValve.java:102) 
at org.apache.catalina.core.StandardEngineValve.invoke(StandardEngineValve.java:109) 
at org.apache.catalina.connector.CoyoteAdapter.service(CoyoteAdapter.java:298) 
at org.apache.coyote.http11.Http11Processor.process(Http11Processor.java:852) 
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.process(Http11Protocol.java:588) 
at org.apache.tomcat.util.net.JIoEndpoint$Worker.run(JIoEndpoint.java:489) 

我看行1401 of StatefulPersistenceContext.java文件:

1396 public void replaceDelayedEntityIdentityInsertKeys(EntityKey oldKey, Serializable generatedId) { 
1397  Object entity = entitiesByKey.remove(oldKey); 
1398  EntityEntry oldEntry = (EntityEntry) entityEntries.remove(entity); 
1399  parentsByChild.clear(); 
1400 
1401  EntityKey newKey = new EntityKey(generatedId, oldEntry.getPersister(), getSession().getEntityMode()); 
1402  addEntity(newKey, entity); 

所以這裏可能的null對象可能是oldEntry,對吧?有誰能告訴我什麼時候oldEntry可以變爲空?我能做些什麼來解決這個問題?

我們將非常感謝您的幫助。

非常感謝, 程偉


萌嗨,

感謝您的答覆。現在我們的系統中的各種方法都會隨機發生異常,我不能通過單元測試重新創建它。我會從一個方法給出一個最簡單的代碼。

@Controller 
public class EndUserController implements EndUserService, InvocationContextRequired 
{ 
    @Override 
    public void reportStats(UsageStatsDTO usageStatsDTO) throws ClientVersionOutOfDateException 
    { 
     log.debug("enter UsageReportController.reportStats()"); 
     UsageStats usageStats = usageStatsDTO.asUsageStats(getEndUser()); 
     usageManager.logUsageStats(usageStats); 
     if(usageStats.hasAppStartEvent()) 
     { 
      endUserManager.updateClientVersion(getEndUser(), getClientVersion()); 
     } 
     log.debug("exit UsageReportController.reportStats()"); 
    } 
    ...... 
} 

@Service 
public class UsageManager 
{ 
    @Autowired 
    private CallEventRepository callEventRepository; 
    @Autowired 
    private AppStartEventRepository appStartEventRepository; 
    @Autowired 
    private InviteEventRepository inviteEventRepository; 

    @Transactional 
    public void logUsageStats(UsageStats usageStats) 
    { 
     if (usageStats.hasCallEvent()) 
     { 
      callEventRepository.persistAll(usageStats.getCallEvents()); 
     } 
     if (usageStats.hasAppStartEvent()) 
     { 
      appStartEventRepository.persistAll(usageStats.getAppStartEvents()); 
     } 
     if (usageStats.hasInviteEvent()) 
     { 
      inviteEventRepository.persistAll(usageStats.getInviteEvents()); 
     } 
    } 
    ...... 
} 

public class GenericJPARepository<T, ID extends Serializable> 
    implements GenericRepository<T, ID> 
{ 
    @Override 
    public T persist(T entity) 
    { 
     getJpaTemplate().persist(entity); 
     return entity; 
    } 
    @Override 
    public void persistAll(Collection<T> entities) 
    { 
     for(T entity : entities) 
     { 
      persist(entity); 
     } 
    } 
    ...... 
} 

而且所有RepositoryImpl類是子類GenericJPARepository的(CallEventRepository,AppStartEventRepository,InviteEventRepository)。

非常感謝, 程偉


燦問題由我引起的分離的實體? endUserRepository.detach(detatchedEndUser);但UsageStats(即要持久保存的對象)不引用detatchedEndUser。


感謝Moe和Maurice,感謝您的幫助。我終於找到了問題。下面的代碼導致了這個問題:

EndUser toBePersistedEndUser = endUserRepository.persist(new EndUser(remoteEndUser)); 
endUserRepository.detach(toBePersistedEndUser); 
return toBePersistedEndUser; 

此外,我想我揭示了一個在這裏休眠的bug。

問題解決了,非常感謝, 程偉

回答

0

好,無論是oldEntry爲空,或者的getSession()返回null。 顯然,如果entityEntries不包含從entitiesByKey中移除的條目,則oldEntry將爲null。如果EntityEntry的equals()方法執行不正確,也會發生這種情況。

+0

感謝您的回覆。我解決了上述問題。 – Cheng

+0

該代碼的問題是什麼? –