/**
 *  Licensed to the Apache Software Foundation (ASF) under one or more
 *  contributor license agreements.  See the NOTICE file distributed with
 *  this work for additional information regarding copyright ownership.
 *  The ASF licenses this file to You 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.apache.geronimo.transaction.manager;

import javax.transaction.xa.Xid;
import javax.transaction.xa.XAResource;
import javax.transaction.xa.XAException;
import javax.transaction.Transaction;
import javax.transaction.Status;

import junit.framework.TestCase;

/**
 *
 *
 * @version $Rev$ $Date$
 *
 * */
public class XidImporterTest extends TestCase{

    MockResourceManager rm1 = new MockResourceManager(true);
    MockResource r1_1 = new MockResource(rm1, "rm1");
    MockResource r1_2 = new MockResource(rm1, "rm1");
    MockResourceManager rm2 = new MockResourceManager(true);
    MockResource r2_1 = new MockResource(rm2, "rm2");
    MockResource r2_2 = new MockResource(rm2, "rm2");

    XidImporter tm;
    XidFactory xidFactory = new XidFactoryImpl();

    protected void setUp() throws Exception {
        tm = new TransactionManagerImpl();
    }

    public void testImportXid() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        assertNotNull(tx);
        assertEquals(Status.STATUS_ACTIVE, tx.getStatus());
    }

    public void testNoResourcesCommitOnePhase() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        tm.commit(tx, true);
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
    }

    public void testNoResourcesCommitTwoPhase() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        assertEquals(XAResource.XA_RDONLY, tm.prepare(tx));
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
    }

    public void testNoResourcesMarkRollback() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        tx.setRollbackOnly();
        try {
            tm.prepare(tx);
            fail("should throw rollback exception in an XAException");
        } catch (XAException e) {
        }
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
    }

    public void testNoResourcesRollback() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        tm.rollback(tx);
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
    }

    public void testOneResourceOnePhaseCommit() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        tx.enlistResource(r1_1);
        tx.delistResource(r1_1, XAResource.TMSUCCESS);
        tm.commit(tx, true);
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
    }

    public void testOneResourceTwoPhaseCommit() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        tx.enlistResource(r1_1);
        tx.delistResource(r1_1, XAResource.TMSUCCESS);
        assertEquals(XAResource.XA_OK, tm.prepare(tx));
        assertTrue(!r1_1.isCommitted());
        assertTrue(r1_1.isPrepared());
        assertTrue(!r1_1.isRolledback());
        tm.commit(tx, false);
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
        assertTrue(r1_1.isCommitted());
        assertTrue(r1_1.isPrepared());
        assertTrue(!r1_1.isRolledback());
    }

    public void testFourResourceTwoPhaseCommit() throws Exception {
        Xid externalXid = xidFactory.createXid();
        Transaction tx = tm.importXid(externalXid, 0);
        tx.enlistResource(r1_1);
        tx.enlistResource(r1_2);
        tx.enlistResource(r2_1);
        tx.enlistResource(r2_2);
        tx.delistResource(r1_1, XAResource.TMSUCCESS);
        tx.delistResource(r1_2, XAResource.TMSUCCESS);
        tx.delistResource(r2_1, XAResource.TMSUCCESS);
        tx.delistResource(r2_2, XAResource.TMSUCCESS);
        assertEquals(XAResource.XA_OK, tm.prepare(tx));
        assertTrue(!r1_1.isCommitted() & !r1_2.isCommitted());
        assertTrue(r1_1.isPrepared() ^ r1_2.isPrepared());
        assertTrue(!r1_1.isRolledback() & !r1_2.isRolledback());
        assertTrue(!r2_1.isCommitted() & !r2_2.isCommitted());
        assertTrue(r2_1.isPrepared() ^ r2_2.isPrepared());
        assertTrue(!r2_1.isRolledback() & !r2_2.isRolledback());
        tm.commit(tx, false);
        assertEquals(Status.STATUS_NO_TRANSACTION, tx.getStatus());
        assertTrue((r1_1.isCommitted() & r1_1.isPrepared()) ^ (r1_2.isCommitted() & r1_2.isPrepared()));
        assertTrue(!r1_1.isRolledback() & !r1_2.isRolledback());
        assertTrue((r2_1.isCommitted() & r2_1.isPrepared()) ^ (r2_2.isCommitted() & r2_2.isPrepared()));
        assertTrue(!r2_1.isRolledback() & !r2_2.isRolledback());
    }

}
