<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    vince

    Lazy Initialization and the DAO pattern with Hibernate and Spring -------轉(zhuǎn)自:Karl Baum's Weblog

    Thursday July 08, 2004
    Lazy Initialization and the DAO pattern with Hibernate and Spring

    Hibernate and Lazy Initialization

    Hibernate object relational mapping offers both lazy and non-lazy modes of object initialization. Non-lazy initialization retrieves an object and all of its related objects at load time. This can result in hundreds if not thousands of select statements when retrieving one entity. The problem is compounded when bi-directional relationships are used, often causing entire databases to be loaded during the initial request. Of course one could tediously examine each object relationship and manually remove those most costly, but in the end, we may be losing the ease of use benefit sought in using the ORM tool.

    The obvious solution is to employ the lazy loading mechanism provided by hibernate. This initialization strategy only loads an object's one-to-many and many-to-many relationships when these fields are accessed. The scenario is practically transparent to the developer and a minimum amount of database requests are made, resulting in major performance gains. One drawback to this technique is that lazy loading requires the Hibernate session to remain open while the data object is in use. This causes a major problem when trying to abstract the persistence layer via the Data Access Object pattern. In order to fully abstract the persistence mechanism, all database logic, including opening and closing sessions, must not be performed in the application layer. Most often, this logic is concealed behind the DAO implementation classes which implement interface stubs. The quick and dirty solution is to forget the DAO pattern and include database connection logic in the application layer. This works for small applications but in large systems this can prove to be a major design flaw, hindering application extensibility.

    Being Lazy in the Web Layer

    Fortunately for us, the Spring Framework has developed an out of box web solution for using the DAO pattern in combination with Hibernate lazy loading. For anyone not familiar with using the Spring Framework in combination with Hibernate, I will not go into the details here, but I encourage you to read Hibernate Data Access with the Spring Framework. In the case of a web application, Spring comes with both the OpenSessionInViewFilter and the OpenSessionInViewInterceptor. One can use either one interchangeably as both serve the same function. The only difference between the two is the interceptor runs within the Spring container and is configured within the web application context while the Filter runs in front of Spring and is configured within the web.xml. Regardless of which one is used, they both open the hibernate session during the request binding this session to the current thread. Once bound to the thread, the open hibernate session can transparently be used within the DAO implementation classes. The session will remain open for the view allowing lazy access the database value objects. Once the view logic is complete, the hibernate session is closed either in the Filter doFilter method or the Interceptor postHandle method. Below is an example of the configuration of each component:

    Interceptor Configuration

    <beans>
    <bean id="urlMapping"
    class="org.springframework.web.servlet.handler.SimpleUrlHandlerMapping">
    <property name="interceptors">
    <list>
    <ref bean="openSessionInViewInterceptor"/>
    </list>
    </property>
    <property name="mappings">
    ...
    </bean>
    ...
    <bean name="openSessionInViewInterceptor"
    class="org.springframework.orm.hibernate.support.OpenSessionInViewInterceptor">
    <property name="sessionFactory"><ref bean="sessionFactory"/></property>
    </bean>
    </beans>
    Filter Configuration

    <web-app>
    ...
    <filter>
    <filter-name>hibernateFilter</filter-name>
    <filter-class>
    org.springframework.orm.hibernate.support.OpenSessionInViewFilter
    </filter-class>
    </filter>
    ...
    <filter-mapping>
    <filter-name>hibernateFilter</filter-name>
    <url-pattern>*.spring</url-pattern>
    </filter-mapping>
    ...
    </web-app>
    Implementing the Hibernate DAO's to use the open session is simple. In fact, if you are already using the Spring Framework to implement your Hibernate DAO's, most likely you will not have to change a thing. The DAO's must access Hibernate through the convenient HibernateTemplate utility, which makes database access a piece of cake. Below is an example DAO.

    Example DAO

    public class HibernateProductDAO extends HibernateDaoSupport implements ProductDAO {

    public Product getProduct(Integer productId) {
    return (Product)getHibernateTemplate().load(Product.class, productId);
    }

    public Integer saveProduct(Product product) {
    return (Integer) getHibernateTemplate().save(product);
    }

    public void updateProduct(Product product) {
    getHibernateTemplate().update(product);
    }
    }
    Being Lazy in the Business Layer

    Even outside the view, the Spring Framework makes it easy to use lazy load initialization, through the AOP interceptor HibernateInterceptor. The hibernate interceptor transparently intercepts calls to any business object configured in the Spring application context, opening a hibernate session before the call, and closing the session afterward. Let's run through a quick example. Suppose we have an interface BusinessObject:

    public interface BusinessObject {
    public void doSomethingThatInvolvesDaos();
    }
    The class BusinessObjectImpl implements BusinessObject:


    public class BusinessObjectImpl implements BusinessObject {
    public void doSomethingThatInvolvesDaos() {
    // lots of logic that calls
    // DAO classes Which access
    // data objects lazily
    }
    }
    Through some configurations in the Spring application context, we can instruct the HibernateInterceptor to intercept calls to the BusinessObjectImpl allowing it's methods to lazily access data objects. Take a look at the fragment below:

    <beans>
    <bean id="hibernateInterceptor" class="org.springframework.orm.hibernate.HibernateInterceptor">
    <property name="sessionFactory">
    <ref bean="sessionFactory"/>
    </property>
    </bean>
    <bean id="businessObjectTarget" class="com.acompany.BusinessObjectImpl">
    <property name="someDAO"><ref bean="someDAO"/></property>
    </bean>
    <bean id="businessObject" class="org.springframework.aop.framework.ProxyFactoryBean">
    <property name="target"><ref bean="businessObjectTarget"/></property>
    <property name="proxyInterfaces">
    <value>com.acompany.BusinessObject</value>
    </property>
    <property name="interceptorNames">
    <list>
    <value>hibernateInterceptor</value>
    </list>
    </property>
    </bean>
    </beans>

    When the businessObject bean is referenced, the HibernateInterceptor opens a hibernate session and passes the call onto the BusinessObjectImpl. When the BusinessObjectImpl has finished executing, the HibernateInterceptor transparently closes the session. The application code has no knowledge of any persistence logic, yet it is still able to lazily access data objects.

    Being Lazy in your Unit Tests

    Last but not least, we'll need the ability to test our lazy application from J-Unit. This is easily done by overriding the setUp and tearDown methods of the TestCase class. I prefer to keep this code in a convenient abstract TestCase class for all of my tests to extend.

    public abstract class MyLazyTestCase extends TestCase {

    private SessionFactory sessionFactory;
    private Session session;

    public void setUp() throws Exception {
    super.setUp();
    SessionFactory sessionFactory = (SessionFactory) getBean("sessionFactory");
    session = SessionFactoryUtils.getSession(sessionFactory, true);
    Session s = sessionFactory.openSession();
    TransactionSynchronizationManager.bindResource(sessionFactory, new SessionHolder(s));

    }

    protected Object getBean(String beanName) {
    //Code to get objects from Spring application context
    }

    public void tearDown() throws Exception {
    super.tearDown();
    SessionHolder holder = (SessionHolder) TransactionSynchronizationManager.getResource(sessionFactory);
    Session s = holder.getSession();
    s.flush();
    TransactionSynchronizationManager.unbindResource(sessionFactory);
    SessionFactoryUtils.closeSessionIfNecessary(s, sessionFactory);
    }
    }

    posted on 2006-11-27 18:10 vince 閱讀(25481) 評論(3)  編輯  收藏

    Feedback

    # re: Lazy Initialization and the DAO pattern with Hibernate and Spring -------轉(zhuǎn)自:Karl Baum's Weblog 2007-12-09 14:35 Hairinwind

    Very Good!

    Thanks!  回復(fù)  更多評論   

    # re: Lazy Initialization and the DAO pattern with Hibernate and Spring -------轉(zhuǎn)自:Karl Baum's Weblog 2007-12-13 00:00 Hamid

    Thank you very much for this article.  回復(fù)  更多評論   

    # re: Lazy Initialization and the DAO pattern with Hibernate and Spring -------轉(zhuǎn)自:Karl Baum's Weblog 2009-05-10 05:35 Great Post.

    Thanks! This fixed my lazy-loading issue.. now on to getting the readOnly flag removed when using the OSIVI.  回復(fù)  更多評論   



    只有注冊用戶登錄后才能發(fā)表評論。


    網(wǎng)站導(dǎo)航:
     

    My Links

    Blog Stats

    常用鏈接

    留言簿(1)

    我參與的團(tuán)隊(duì)

    隨筆檔案

    文章檔案

    搜索

    最新評論

    主站蜘蛛池模板: 日韩电影免费观看| 一级毛片a免费播放王色| 国产啪精品视频网站免费尤物| 午夜亚洲av永久无码精品| 亚洲av日韩aⅴ无码色老头| 永久免费的网站在线观看| 亚洲AV成人噜噜无码网站| 日韩不卡免费视频| 成人亚洲国产va天堂| 日本高清色本免费现在观看| 亚洲国产精品久久久久秋霞小| 黑人粗长大战亚洲女2021国产精品成人免费视频 | 中文字幕不卡免费高清视频| 亚洲av无码成人精品区一本二本| 毛色毛片免费观看| 亚洲精品国产suv一区88 | 18禁免费无码无遮挡不卡网站 | 国产综合激情在线亚洲第一页| 好爽好紧好大的免费视频国产| 国产亚洲视频在线| 亚洲伊人久久精品影院| 免费国产黄网站在线观看| 亚洲AV无码乱码麻豆精品国产| 免费观看的a级毛片的网站| 一级做a爰片性色毛片免费网站| 久久亚洲精品无码播放| 久久久久久影院久久久久免费精品国产小说 | 亚洲AV永久精品爱情岛论坛| 18女人毛片水真多免费| 亚洲人成电影网站色| 中文字幕第一页亚洲| 亚洲免费在线观看视频| 欧美激情综合亚洲一二区| 亚洲综合国产一区二区三区| 3d成人免费动漫在线观看| 亚洲av无码专区亚洲av不卡| 亚洲一级片免费看| 无码区日韩特区永久免费系列| 特黄特色大片免费| 久久久婷婷五月亚洲97号色 | 一级毛片免费视频|