How do you handle a Hibernate session in a web application to ensure that it is properly closed, avoiding memory leaks?

In a web application, Hibernate sessions are typically managed with the "open session per request" pattern, where a session is opened at the start of each request, bound to the current thread, and reliably closed at the end, preventing leaked sessions and stale connections.

Key Points: • CurrentSessionContext (e.g. ThreadLocalSessionContext) binds a Session to the current thread so getCurrentSession() returns the same instance throughout a request. • A servlet filter or interceptor is a natural place to open the session at request start and close it in a finally block at request end. • This guarantees the session is closed exactly once per request, even if an exception occurs partway through. • Modern Spring applications typically delegate this to Spring's OpenSessionInViewFilter or, more often, avoid it in favor of explicit transactional service boundaries. • Failing to close sessions reliably leads to connection pool exhaustion and eventually application-wide failures under load.

Example: A custom OncePerRequestFilter opens a Hibernate session and starts a transaction before calling filterChain.doFilter(), then commits (or rolls back on exception) and always closes the session in a finally block, so every request is guaranteed a clean session lifecycle.

Code Example:

public class HibernateSessionFilter extends OncePerRequestFilter {
    protected void doFilterInternal(HttpServletRequest req, HttpServletResponse res,
                                     FilterChain chain) throws IOException, ServletException {
        Session session = sessionFactory.openSession();
        TransactionSynchronizationManager.bindResource(sessionFactory, session);
        try {
            chain.doFilter(req, res);
        } finally {
            TransactionSynchronizationManager.unbindResource(sessionFactory);
            session.close();
        }
    }
}

Interview Tip: A concise interview answer is:

"I bind a session to the current thread using CurrentSessionContext and manage its lifecycle in a servlet filter or interceptor — opening it at the start of the request and closing it in a finally block — so every request gets exactly one clean session and nothing leaks even when an exception occurs."