/*
 * Copyright (c) 1998, 2021 Oracle and/or its affiliates. All rights reserved.
 *
 * This program and the accompanying materials are made available under the
 * terms of the Eclipse Public License v. 2.0 which is available at
 * http://www.eclipse.org/legal/epl-2.0,
 * or the Eclipse Distribution License v. 1.0 which is available at
 * http://www.eclipse.org/org/documents/edl-v10.php.
 *
 * SPDX-License-Identifier: EPL-2.0 OR BSD-3-Clause
 */

// Contributors:
//     Oracle - initial API and implementation from Oracle TopLink
package org.eclipse.persistence.testing.tests.forceupdate;

import org.eclipse.persistence.sessions.*;
import org.eclipse.persistence.exceptions.*;
import org.eclipse.persistence.expressions.*;
import org.eclipse.persistence.testing.framework.*;
import org.eclipse.persistence.testing.models.forceupdate.*;

/**
    Scenario:
    Two threads(here we use two UOWs to simulate two threads) read in the same emplyee
    object. The first thread updates employee's address(relationship) and commits. The
    second thread updates the emplyee's salary(non-relationship attribute based on
    where the emplyee lives)and commits. No exception is thrown but the updated salary
    is invalid. If the first thread forces update the version value of the employee, an
    optimistic lock exception is thrown in the second thread.

    (Version locking stores in the Cache)
    Test 1: (Correctly use method forceUpdateToVersionField())
    UOW1 updates employee's address,
    calls forceUpdateToVersionField(Object cloneFromUOW1,true) and commits.
    UOW2 updates the employee's salary and commits.
    The test verified an optimistic lock exception is thrown in UOW2.

    Test 2: (forceUpdateToVersionField() doesn't effect read-only UOW)
    UOW1 updates employee's address,
    calls forceUpdateToVersionField(Object cloneFromUOW1,true) and commits.
    UOW2 has only read-operation and commits.
    The test verified no optimistic lock exception is thrown in UOW2.

    Test 3: (Test method removeForceUpdateToVersionField())
    UOW1 updates employee's address,
    calls forceUpdateToVersionField(cloneFromUOW1,true),COMMIT&RESUMEs.
    It calls removeForceUpdateToVersionField(cloneFromUOW1),
    updates employee's address again and commits.
    UOW2 reads employee after the first commit of UOW1,updates the emplyee's salary
    and commits.
    The test verified no optimistic lock exception is thrown in UOW2.

    Test 4: (Demonstrate the result when no using forceUpdateToVersionField())
    UOW1 updates employee's address, commits.
    UOW2 updates the employee's salary and commits.
    The test verified no optimistic lock exception is thrown in UOW2.
*/
public class FUVLVersionLockInCacheTest extends TransactionalTestCase {
    boolean exceptionCaught = false;
    int testnumber;

    public FUVLVersionLockInCacheTest(int anInt) {
        testnumber = anInt;
        setName(getName() + "(Test" + anInt + ")");
        switch (testnumber) {
        case 1:
            setDescription("Correctly use method forceUpdateToVersionField()");
            break;
        case 2:
            setDescription("forceUpdateToVersionField() doesn't effect read-only UOW");
            break;
        case 3:
            setDescription("Test method removeForceUpdateToVersionField()");
            break;
        case 4:
            setDescription("Demonstrate the result when no using forceUpdateToVersionField()");
            break;
        default:
            break;
        }
    }

    @Override
    public void test() {
        switch (testnumber) {
        case 1:
            test1();
            break;
        case 2:
            test2();
            break;
        case 3:
            test3();
            break;
        case 4:
            test4();
            break;
        default:
            break;
        }
    }

    public void test1() {
        UnitOfWork uow1, uow2;

        ExpressionBuilder bldr = new ExpressionBuilder();
        Expression exp1 = bldr.get("firstName").equal("Bob");
        Expression exp2 = bldr.get("lastName").equal("Smith");
        Expression exp = exp1.and(exp2);

        EmployeeVLIC emp = (EmployeeVLIC)getSession().readObject(EmployeeVLIC.class, exp);

        uow1 = getSession().acquireUnitOfWork();
        uow2 = getSession().acquireUnitOfWork();
        EmployeeVLIC clone1 = (EmployeeVLIC)uow1.registerObject(emp);
        EmployeeVLIC clone2 = (EmployeeVLIC)uow2.registerObject(emp);

        uow1.forceUpdateToVersionField(clone1, true);
        clone1.getAddress().setStreet("4 Hutton Centre,Suite 900");
        clone1.getAddress().setCity("Santa Ana");
        clone1.getAddress().setProvince("CA");
        clone1.getAddress().setCountry("USA");
        clone1.getAddress().setPostalCode("92797");
        uow1.commit();

        clone2.setSalary(clone2.getSalary() + 200);
        try {
            uow2.commit();
        } catch (OptimisticLockException exception) {
            exceptionCaught = true;
        }
    }

    public void test2() {
        UnitOfWork uow1, uow2;

        ExpressionBuilder bldr = new ExpressionBuilder();
        Expression exp1 = bldr.get("firstName").equal("Bob");
        Expression exp2 = bldr.get("lastName").equal("Smith");
        Expression exp = exp1.and(exp2);

        EmployeeVLIC emp = (EmployeeVLIC)getSession().readObject(EmployeeVLIC.class, exp);

        uow1 = getSession().acquireUnitOfWork();
        uow2 = getSession().acquireUnitOfWork();
        EmployeeVLIC clone1 = (EmployeeVLIC)uow1.registerObject(emp);
        EmployeeVLIC clone2 = (EmployeeVLIC)uow2.registerObject(emp);

        uow1.forceUpdateToVersionField(clone1, true);
        clone1.getAddress().setStreet("4 Hutton Centre,Suite 900");
        clone1.getAddress().setCity("Santa Ana");
        clone1.getAddress().setProvince("CA");
        clone1.getAddress().setCountry("USA");
        clone1.getAddress().setPostalCode("92797");
        uow1.commit();

        // uow2 has only read-operation here
        //...
        try {
            uow2.commit();
        } catch (OptimisticLockException exception) {
            exceptionCaught = true;
        }
    }

    public void test3() {
        UnitOfWork uow1, uow2;

        ExpressionBuilder bldr = new ExpressionBuilder();
        Expression exp1 = bldr.get("firstName").equal("Bob");
        Expression exp2 = bldr.get("lastName").equal("Smith");
        Expression exp = exp1.and(exp2);

        EmployeeVLIC emp = (EmployeeVLIC)getSession().readObject(EmployeeVLIC.class, exp);

        uow1 = getSession().acquireUnitOfWork();
        EmployeeVLIC clone1 = (EmployeeVLIC)uow1.registerObject(emp);

        uow1.forceUpdateToVersionField(clone1, true);
        clone1.getAddress().setStreet("100 Young Street");
        clone1.getAddress().setCity("Toronto");
        clone1.getAddress().setProvince("ON");
        clone1.getAddress().setCountry("CANADA");
        clone1.getAddress().setPostalCode("K489Y7");
        uow1.commitAndResume();
        uow1.removeForceUpdateToVersionField(clone1);

        uow2 = getSession().acquireUnitOfWork();
        EmployeeVLIC clone2 = (EmployeeVLIC)uow2.registerObject(emp);

        clone1.getAddress().setStreet("4 Hutton Centre,Suite 900");
        clone1.getAddress().setCity("Santa Ana");
        clone1.getAddress().setProvince("CA");
        clone1.getAddress().setCountry("USA");
        clone1.getAddress().setPostalCode("92797");
        uow1.commit();

        clone2.setSalary(clone2.getSalary() + 200);
        try {
            uow2.commit();
        } catch (OptimisticLockException exception) {
            exceptionCaught = true;
        }
    }

    public void test4() {
        UnitOfWork uow1, uow2;

        ExpressionBuilder bldr = new ExpressionBuilder();
        Expression exp1 = bldr.get("firstName").equal("Bob");
        Expression exp2 = bldr.get("lastName").equal("Smith");
        Expression exp = exp1.and(exp2);

        EmployeeVLIC emp = (EmployeeVLIC)getSession().readObject(EmployeeVLIC.class, exp);

        uow1 = getSession().acquireUnitOfWork();
        uow2 = getSession().acquireUnitOfWork();
        EmployeeVLIC clone1 = (EmployeeVLIC)uow1.registerObject(emp);
        EmployeeVLIC clone2 = (EmployeeVLIC)uow2.registerObject(emp);

        clone1.getAddress().setStreet("4 Hutton Centre,Suite 900");
        clone1.getAddress().setCity("Santa Ana");
        clone1.getAddress().setProvince("CA");
        clone1.getAddress().setCountry("USA");
        clone1.getAddress().setPostalCode("92797");
        uow1.commit();

        clone2.setSalary(clone2.getSalary() + 200);
        try {
            uow2.commit();
        } catch (OptimisticLockException exception) {
            exceptionCaught = true;
        }
    }

    @Override
    protected void verify() {
        switch (testnumber) {
        case 1:
            if (!exceptionCaught)
                throw new TestErrorException("No Optimistic Lock exception was thrown");
            break;
        case 2:
        case 3:
        case 4:
            if (exceptionCaught)
                throw new TestErrorException("Optimistic Lock exception should not have been thrown");
            break;
        default:
            break;
        }
    }
}
