This forum is now a read-only archive. All commenting, posting, registration services have been turned off. Those needing community support and/or wanting to ask questions should refer to the Tag/Forum map, and to http://spring.io/questions for a curated list of stackoverflow tags that Pivotal engineers, and the community, monitor.

This bit of code is buried in my Web Application and when I have two browsers open and one happens to delete a RecipeList item that has already been deleted by the second browser window a StaleObjectStateException gets thrown.

Would you normally expect to be able to catch the StaleObjectStateException at this point using the HibernateTemplate? Or am I seriously missing a concept?

I attempted to go down a level and get a Hibernate Session using getSession() and manually doing the session.delete(recipe) and session.flush commands myself thinking that at a lower level I'd be able to catch the exception... But no luck.

The StatleObjectStateException is a Hibernate checked exception. Spring catches all HibernateExceptions and wraps them in an unchecked Spring DataAccessException (or subclass of). You should grab this exception and look for the inner cause.

If this is indeed the correct Syntax I am still not able to catch the DataAccessException or the StaleObjectStateException..

Heh... Or it could be an error that's completely unrelated to my code. I'm assuming that you can catch RuntimeExceptions the same way you catch java.lang.Exceptions, yes?

Thanks all again for your help!

Error listing and applicationContext.xml

Code:

2004-10-29 13&#58;32&#58;08,784 WARN StaleObjectStateException - An operation failed due to stale data
net.sf.hibernate.StaleObjectStateException&#58; Row was updated or deleted by another transaction &#40;or unsaved-value mapping was incorrect&#41; for zorolrecipemgmt.hibernate.RecipeList instance with identifier&#58; 80
at net.sf.hibernate.persister.AbstractEntityPersister.check&#40;AbstractEntityPersister.java&#58;506&#41;
at net.sf.hibernate.persister.EntityPersister.delete&#40;EntityPersister.java&#58;596&#41;
at net.sf.hibernate.impl.ScheduledDeletion.execute&#40;ScheduledDeletion.java&#58;29&#41;
at net.sf.hibernate.impl.SessionImpl.executeAll&#40;SessionImpl.java&#58;2418&#41;
at net.sf.hibernate.impl.SessionImpl.execute&#40;SessionImpl.java&#58;2376&#41;
at net.sf.hibernate.impl.SessionImpl.flush&#40;SessionImpl.java&#58;2240&#41;
at org.springframework.orm.hibernate.HibernateAccessor.flushIfNecessary&#40;HibernateAccessor.java&#58;214&#41;
at org.springframework.orm.hibernate.HibernateTemplate.execute&#40;HibernateTemplate.java&#58;201&#41;
at org.springframework.orm.hibernate.HibernateTemplate.delete&#40;HibernateTemplate.java&#58;381&#41;
at recipemgmt.hibernate.dao.RecipeListDAO.deleteRecipeItem&#40;RecipeListDAO.java&#58;58&#41;
at recipemgmt.app.RecipeMgmtScreen.deleteRecipeListItem&#40;RecipeMgmtScreen.java&#58;398&#41;
at recipemgmt.app.RecipeMgmtScreen.actionPerformed&#40;RecipeMgmtScreen.java&#58;189&#41;
at nextapp.echo.AbstractButton.fireActionPerformed&#40;AbstractButton.java&#58;268&#41;
at nextapp.echo.AbstractButton$EventForwarder.actionPerformed&#40;AbstractButton.java&#58;127&#41;
at nextapp.echo.DefaultButtonModel.fireActionPerformed&#40;DefaultButtonModel.java&#58;88&#41;
at nextapp.echo.DefaultButtonModel.doAction&#40;DefaultButtonModel.java&#58;77&#41;
at nextapp.echo.AbstractButton.doAction&#40;AbstractButton.java&#58;238&#41;
at nextapp.echoservlet.ui.AbstractButtonUI.clientAction&#40;AbstractButtonUI.java&#58;76&#41;
at echopoint.ui.PushButtonUI.clientAction&#40;PushButtonUI.java&#58;85&#41;
at nextapp.echoservlet.ControllerInputProcessor.doAction&#40;ControllerInputProcessor.java&#58;144&#41;
at nextapp.echoservlet.ControllerInputProcessor.<init>&#40;ControllerInputProcessor.java&#58;113&#41;
at nextapp.echoservlet.ControllerInputProcessor.process&#40;ControllerInputProcessor.java&#58;44&#41;
at nextapp.echoservlet.Controller.service&#40;Controller.java&#58;604&#41;
at nextapp.echoservlet.Connection.process&#40;Connection.java&#58;441&#41;
at nextapp.echoservlet.EchoServer.process&#40;EchoServer.java&#58;303&#41;
at nextapp.echoservlet.EchoServer.doPost&#40;EchoServer.java&#58;223&#41;
at javax.servlet.http.HttpServlet.service&#40;HttpServlet.java&#58;717&#41;
at javax.servlet.http.HttpServlet.service&#40;HttpServlet.java&#58;810&#41;
at org.apache.catalina.core.ApplicationFilterChain.internalDoFilter&#40;ApplicationFilterChain.java&#58;237&#41;
at org.apache.catalina.core.ApplicationFilterChain.doFilter&#40;ApplicationFilterChain.java&#58;157&#41;
at org.apache.catalina.core.StandardWrapperValve.invoke&#40;StandardWrapperValve.java&#58;214&#41;
at org.apache.catalina.core.StandardValveContext.invokeNext&#40;StandardValveContext.java&#58;104&#41;
at org.apache.catalina.core.StandardPipeline.invoke&#40;StandardPipeline.java&#58;520&#41;
at org.apache.catalina.core.StandardContextValve.invokeInternal&#40;StandardContextValve.java&#58;198&#41;
at org.apache.catalina.core.StandardContextValve.invoke&#40;StandardContextValve.java&#58;152&#41;
at org.apache.catalina.core.StandardValveContext.invokeNext&#40;StandardValveContext.java&#58;104&#41;
at org.apache.catalina.core.StandardPipeline.invoke&#40;StandardPipeline.java&#58;520&#41;
at org.apache.catalina.core.StandardHostValve.invoke&#40;StandardHostValve.java&#58;137&#41;
at org.apache.catalina.core.StandardValveContext.invokeNext&#40;StandardValveContext.java&#58;104&#41;
at org.apache.catalina.valves.ErrorReportValve.invoke&#40;ErrorReportValve.java&#58;117&#41;
at org.apache.catalina.core.StandardValveContext.invokeNext&#40;StandardValveContext.java&#58;102&#41;
at org.apache.catalina.core.StandardPipeline.invoke&#40;StandardPipeline.java&#58;520&#41;
at org.apache.catalina.core.StandardEngineValve.invoke&#40;StandardEngineValve.java&#58;109&#41;
at org.apache.catalina.core.StandardValveContext.invokeNext&#40;StandardValveContext.java&#58;104&#41;
at org.apache.catalina.core.StandardPipeline.invoke&#40;StandardPipeline.java&#58;520&#41;
at org.apache.catalina.core.ContainerBase.invoke&#40;ContainerBase.java&#58;929&#41;
at org.apache.coyote.tomcat5.CoyoteAdapter.service&#40;CoyoteAdapter.java&#58;160&#41;
at org.apache.coyote.http11.Http11Processor.process&#40;Http11Processor.java&#58;793&#41;
at org.apache.coyote.http11.Http11Protocol$Http11ConnectionHandler.processConnection&#40;Http11Protocol.java&#58;702&#41;
at org.apache.tomcat.util.net.TcpWorkerThread.runIt&#40;PoolTcpEndpoint.java&#58;571&#41;
at org.apache.tomcat.util.threads.ThreadPool$ControlRunnable.run&#40;ThreadPool.java&#58;644&#41;
at java.lang.Thread.run&#40;Thread.java&#58;536&#41;

Comment

It appears that my code has properly caught the StaleObjectStateException after all.

The problem was that I had Tomcat configured to run in debug mode under Eclipse.

When Tomcat encountered the StaleObjectStateException, it Suspended the current thread. I assumed that this meant that there was a problem with my code not properly catching the exception... I simply resumed through the exception and all is well.

FYI: you can also configure Eclipse to behave in a certain way when an Exception occurs. In this case, I will be configuring Eclipse to not suspend when it sees a StaleObjectStateException. Very cool.