Announcement Announcement Module
Collapse
No announcement yet.
Transactions in unmanaged objects (servlets) Page Title Module
Move Remove Collapse
X
Conversation Detail Module
Collapse
  • Filter
  • Time
  • Show
Clear All
new posts

  • Transactions in unmanaged objects (servlets)

    Before you ask - I don't have any control over this decision - this is what the higher ups want to do, and I need to find a way to make it work .

    We've got a DAO layer written that uses Hibernate and Spring. The DAO layer is then used directly in servlets. i.e.
    Code:
    doGet(request, response) {
       ...
       dao.load(...);
       dao.load(...);
       dao.update(...);
       ...
    }
    We need to use Hibernate's lazy loading capabilities, which means making sure the Hibernate session stays open - OpenSessionInViewFilter works fine for this.

    Unfortunately, since the DAO's are the highest layer of objects managed by Spring, this is where the transaction demarcation is currently being done. This means that for the code above, 3 transactions are beginning and ending.

    How can transaction demarcation be handled in a way that will cause there to be only one transaction per request (i.e. I'm thinking of a filter similar to OpenSessionInViewFilter but for transactions)?

    Obviously one option is to force the servlets to at least delegate all logic to a service layer, but this would be a major overhaul of existing code - is there an easy way to get one transaction per request with this setup?

    Jon

  • #2
    You could use programmatic transactions using TransactionTemplate. Alternatively, couldn't you use a filter in the same way that OpenSessionInViewFilter works?

    Comment


    • #3
      Thanks for the suggestion - I was thinking of something similar to OSIVF but for transactions, but wasn't sure how to use Spring to do it. Your mention of TransactionTemplate set me in the right direction though.

      Here's the quick 'n dirty solution I came up with. I've written a Filter that wraps the chain.doFilter(req,resp) call with a TransactionTemplate. Not pretty, but it'll do for now.

      Code:
          public PlatformTransactionManager getPlatformTransactionManager(ServletContext servletContext) {
              WebApplicationContext wac = WebApplicationContextUtils
                      .getRequiredWebApplicationContext(servletContext);
              return (PlatformTransactionManager) wac.getBean("transactionManager");
          }
          @Override
          protected void doFilterInternal(final HttpServletRequest request,
                  final HttpServletResponse response, final FilterChain chain) {
      
              TransactionTemplate tt = new TransactionTemplate(
                      getPlatformTransactionManager(getServletContext()));
      
              if (logger.isDebugEnabled()) {
                  logger.debug("Starting a database transaction");
              }
              tt.execute(new TransactionCallback() {
                  public Object doInTransaction(TransactionStatus transactionStatus) {
                      try {
      
                          // TODO: if an exception is caught, make sure to
                          // rethrow a runtimeexception so that the transaction will
                          // be automatically rolled back by TransactionTemplate
      
                          chain.doFilter(request, response);
                      } catch (IOException e) {
                          e.printStackTrace();
                      } catch (ServletException e) {
                          e.printStackTrace();
                      }
                      return null;
                  }
              });
              if (logger.isDebugEnabled()) {
                  logger.debug("database transaction committed");
              }
          }

      Comment


      • #4
        Glad you got it working, seems pretty straight forward. I presume you are using OncePerRequestFilter just like OSIVFilter. Just don't forget to rethrow the exceptions if you want it to rollback .
        http://www.springframework.org/docs/...estFilter.html

        Comment

        Working...
        X