在filter里关闭session

来源:互联网 发布:淘宝国际物流订单 编辑:程序博客网 时间:2024/05/01 22:30
package com.upstate.cellculture.om.persist;

import net.sf.hibernate.HibernateException;
import net.sf.hibernate.JDBCException;
import net.sf.hibernate.Session;
import net.sf.hibernate.SessionFactory;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

/**
* This class is used to get Hibernate Sessions and may
* also contain methods (in the future) to get DBConnections
* or Transactions from JNDI.
*/

public class ServiceLocator
{
    //~ Static fields/initializers =============================================
    public final static String SESSION_FACTORY = "hibernate/sessionFactory";
    public static final ThreadLocal session = new ThreadLocal();
    private static SessionFactory sf = null;
    private static ServiceLocator me;
    private static Log log = LogFactory.getLog(ServiceLocator.class);

    static {
        try
        {
            me = new ServiceLocator();
        }
        catch (Exception e)
        {
            log.fatal("Error occurred initializing ServiceLocator");
            e.printStackTrace();
        }
    }

    //~ Constructors ===========================================================

    private ServiceLocator() throws HibernateException, JDBCException
    {}

    //~ Methods ================================================================

    public static Session currentSession() throws PersistenceException
    {
        Session s = (Session) session.get();

        if (s == null)
        {
            s = PersistenceManager.openSession();
            if (log.isDebugEnabled())
            {
                log.debug("Opened hibernate session.");
            }

            session.set(s);
        }

        return s;
    }

    public static void closeSession() throws HibernateException, JDBCException
    {
        Session s = (Session) session.get();
        session.set(null);

        if (s != null)
        {
            if (s.isOpen())
            {
                s.flush();
                s.close();

                if (log.isDebugEnabled())
                {
                    log.debug("Closed hibernate session.");
                }
            }
        }
        else
        {
            log.warn("Hibernate session was inadvertently already closed.");

        }
    }
}



如果你使用对象的lazy loading你需要使用一个servlet filter
java代码: 

package com.upstate.cellculture.filter;

import java.io.IOException;

import javax.servlet.Filter;
import javax.servlet.FilterChain;
import javax.servlet.FilterConfig;
import javax.servlet.ServletException;
import javax.servlet.ServletRequest;
import javax.servlet.ServletResponse;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import javax.servlet.http.HttpSession;

import net.sf.hibernate.Session;

import org.apache.commons.logging.Log;
import org.apache.commons.logging.LogFactory;

import com.upstate.cellculture.om.persist.PersistenceException;
import com.upstate.cellculture.om.persist.ServiceLocator;

public class ActionFilter implements Filter
{
    //~ Static fields/initializers =============================================

    //~ Instance fields ========================================================

    /**
     * The <code>Log</code> instance for this class
     */

    private Log log = LogFactory.getLog(ActionFilter.class);
    private FilterConfig filterConfig = null;

    //~ Methods ================================================================

    public void init(FilterConfig filterConfig) throws ServletException
    {
        this.filterConfig = filterConfig;

    }

    /**
     * Destroys the filter.
     */

    public void destroy()
    {
        filterConfig = null;
    }

    public void doFilter(ServletRequest req, ServletResponse resp, FilterChain chain) throws IOException, ServletException
    {
        // cast to the types I want to use
        HttpServletRequest request = (HttpServletRequest) req;
        HttpServletResponse response = (HttpServletResponse) resp;
        HttpSession session = request.getSession(true);

        Session ses = null;
        boolean sessionCreated = false;

        try
        {
            chain.doFilter(request, response);
        }
        finally
        {
            try
            {
                ServiceLocator.closeSession();
            }
            catch (Exception exc)
            {
                log.error("Error closing hibernate session.", exc);
                exc.printStackTrace();
            }
        }
    }

    public static Session getSession() throws PersistenceException
    {
        try
        {

            return ServiceLocator.currentSession();
        }
        catch (Exception e)
        {
            throw new PersistenceException("Could not find current Hibernate session.", e);
        }

    }
}



此外,为了把数据库访问集中起来,我们会使用一些manager类,也就是DAO
java代码: 

/*
* Created on Apr 28, 2003
*
*/

package com.upstate.cellculture.om.persist;
import java.util.List;

import net.sf.hibernate.Query;
import net.sf.hibernate.Session;

import com.upstate.cellculture.om.Technician;
/**
* @author tmckinney
*
* Centralizes all access to the Technicians table
*/

public class TechnicianManager
{
    private static List allTechnicians;
    public static void save(Technician technician) throws PersistenceException
    {
        try
        {

            ServiceLocator.currentSession().save(technician);

        }
        catch (Exception e)
        {
            throw new PersistenceException("Could not save.", e);
        }
    }

    public static Technician retrieveByPK(long technicianId) throws PersistenceException
       {
           try
             {
                 Technician technician= (Technician) ServiceLocator.currentSession().load(Technician.class, new Long(technicianId));
                 return technician;
             }
             catch (Exception e)
             {
                 throw new PersistenceException("Could not retrieve.", e);
             }
       }


    public static List retrieveAllTechnicians() throws PersistenceException
    {
        if (allTechnicians == null)
        {
            try
            {
                Query q = ServiceLocator.currentSession().createQuery("from technician in class " + Technician.class +" order by upper(technician.name)");
                allTechnicians = q.list();
                session.flush();
            }
            catch (Exception e)
            {
                e.printStackTrace();
                throw new PersistenceException(e);
            }
        }
        return allTechnicians;

    }


}



如果能够使用一个 TechnicianManager接口和一个TechnicianManagerImpl class. 那就更好了。

通过自己定义的一个异常来包装了所有抛出的异常。

java代码: 


package com.upstate.cellculture.om.persist;

import org.apache.commons.lang.exception.NestableException;
/**
* A general PersistenceException that is thrown by all Manager classes.
*
*/

public class PersistenceException extends NestableException
{
    //~ Constructors ===========================================================

    /**
     * Constructor for PersistenceException.
     */

    public PersistenceException()
    {
        super();
    }

    /**
     * Constructor for PersistenceException.
     *
     * @param message
     */

    public PersistenceException(String message)
    {
        super(message);
    }

    /**
     * Constructor for PersistenceException.
     *
     * @param message
     * @param cause
     */

    public PersistenceException(String message, Throwable cause)
    {
        super(message, cause);
    }

    /**
     * Constructor for PersistenceException.
     *
     * @param cause
     */

    public PersistenceException(Throwable cause)
    {
        super(cause);
    }

}
原创粉丝点击