/*
 * Copyright 2004-2009 the original author or authors.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *      http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package org.compass.gps.device.hibernate.transaction;

import junit.framework.TestCase;
import org.compass.core.Compass;
import org.compass.core.CompassSession;
import org.compass.core.config.CompassConfiguration;
import org.compass.core.impl.ExistingCompassSession;
import org.compass.gps.device.hibernate.HibernateSyncTransactionFactory;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.hibernate.Transaction;
import org.hibernate.cfg.Configuration;
import org.hibernate.cfg.Environment;

/**
 * Hibernate transaction tests that use session#close instead of session#commit with no explicit
 * usage of CompassTransaction.
 *
 * @author kimchy
 */
public class HibernateJustCloseTransactionTests extends TestCase {

    private Compass compass;

    private SessionFactory sessionFactory;

    protected void setUp() throws Exception {

        Configuration conf = new Configuration().configure("/org/compass/gps/device/hibernate/transaction/hibernate.cfg.xml")
                .setProperty(Environment.HBM2DDL_AUTO, "create");
        sessionFactory = conf.buildSessionFactory();

        // set the session factory for the Hibernate transcation factory BEFORE we construct the compass instnace
        HibernateSyncTransactionFactory.setSessionFactory(sessionFactory);

        CompassConfiguration cpConf = new CompassConfiguration()
                .configure("/org/compass/gps/device/hibernate/transaction/compass.cfg.xml");
        compass = cpConf.buildCompass();
        compass.getSearchEngineIndexManager().deleteIndex();
        compass.getSearchEngineIndexManager().verifyIndex();

    }

    protected void tearDown() throws Exception {
        compass.close();
        sessionFactory.close();
    }

    public void testInnerHibernateManagement() throws Exception {
        CompassSession session = compass.openSession();

        // save a new instance of A
        long id = 1;
        A a = new A();
        a.id = id;
        session.save(a);

        a = session.get(A.class, id);
        assertNotNull(a);

        // check that if we open a new transaction within the current one it
        // will still work
        CompassSession newSession = compass.openSession();
        assertTrue(newSession instanceof ExistingCompassSession);
        assertTrue(session == ((ExistingCompassSession) newSession).getActualSession());
        a = session.get(A.class, id);
        assertNotNull(a);
        // this one should not commit the hibernate transaction since the out
        // controlls it
        newSession.close();
        session.close();

        // verify that the instance was saved
        session = compass.openSession();
        a = session.get(A.class, id);
        assertNotNull(a);

        session.close();
    }

    public void testOuterHibernteManagementWithCommit() throws Exception {
        Session hibernateSession = sessionFactory.getCurrentSession();
        Transaction hibernateTr = hibernateSession.beginTransaction();

        CompassSession session = compass.openSession();
        long id = 1;
        A a = new A();
        a.id = id;
        session.save(a);
        a = session.get(A.class, id);
        assertNotNull(a);
        session.close();

        CompassSession oldSession = session;
        session = compass.openSession();
        assertTrue(session instanceof ExistingCompassSession);
        assertTrue(oldSession == ((ExistingCompassSession) session).getActualSession());
        a = session.get(A.class, id);
        assertNotNull(a);
        session.close();

        hibernateTr.commit();

        session = compass.openSession();
        a = session.get(A.class, id);
        assertNotNull(a);
        session.close();
    }

    public void testOuterUTManagementWithCommitAndNoSessionOrTransactionManagement() throws Exception {
        Session hibernateSession = sessionFactory.getCurrentSession();
        Transaction hibernateTr = hibernateSession.beginTransaction();

        CompassSession session = compass.openSession();
        long id = 1;
        A a = new A();
        a.id = id;
        session.save(a);
        a = session.get(A.class, id);
        assertNotNull(a);

        CompassSession oldSession = session;
        session = compass.openSession();
        assertTrue(session instanceof ExistingCompassSession);
        assertTrue(oldSession == ((ExistingCompassSession) session).getActualSession());
        a = session.get(A.class, id);
        assertNotNull(a);

        hibernateTr.commit();

        // now check that things were committed
        // here we do need explicit session/transaciton mangement
        // just cause we are lazy and want to let Comapss to manage JTA
        session = compass.openSession();
        a = session.get(A.class, id);
        assertNotNull(a);
        session.close();
    }

    public void testOuterUTManagementWithRollback() throws Exception {
        Session hibernateSession = sessionFactory.getCurrentSession();
        Transaction hibernateTr = hibernateSession.beginTransaction();

        CompassSession session = compass.openSession();
        long id = 1;
        A a = new A();
        a.id = id;
        session.save(a);
        a = session.get(A.class, id);
        assertNotNull(a);
        session.close();
        session = compass.openSession();
        a = session.get(A.class, id);
        assertNotNull(a);
        session.close();

        hibernateTr.rollback();

        session = compass.openSession();
        a = session.get(A.class, id);
        assertNull(a);
        session.close();
    }
}
@@ -874,32 +874,81 @@
 CompassSession;%0A
+import org.compass.core.util.FileHandlerMonitor;%0A
 import org.compa
@@ -996,32 +996,32 @@
 sactionFactory;%0A
-
 import org.hiber
@@ -1440,16 +1440,68 @@
 mpass;%0A%0A
+    private FileHandlerMonitor fileHandlerMonitor;%0A%0A
     priv
@@ -2214,24 +2214,153 @@
 dCompass();%0A
+%0A        fileHandlerMonitor = FileHandlerMonitor.getFileHandlerMonitor(compass);%0A        fileHandlerMonitor.verifyNoHandlers();%0A%0A
         comp
@@ -2518,32 +2518,32 @@
 ows Exception %7B%0A
-
         compass.
@@ -2543,32 +2543,79 @@
 ompass.close();%0A
+        fileHandlerMonitor.verifyNoHandlers();%0A
         sessionF

test file handlers for hibernate tests