Проблема отката управления транзакциями в OpenEjb - PullRequest
0 голосов
/ 07 июня 2019

Пожалуйста, помогите решить проблему ниже. Не уверен, что я делаю не так.

Я создаю два компонента сеанса без сохранения состояния BlueBean RedBean

Я хочу реализовать два потока транзакций. Один с REQUIRED и REQUIRES_NEW.

BlueBean

  1. вставляет данные в таблицу Person.
  2. Он вызывает RedBean

RedBean

  1. Вставляет данные в таблицу компаний.

Сценарии

TransacationType.REQUIRED

***Positive case*** : 
   No exception in BlueBean and RedBean.
***Result*** :It inserts the data into two tables. 

***Negative case***: 
    Lets say RedBean has issue while inserting into database. It throws exception. 
***Result*** : It shouldn't insert into two tables. Since the TransactionAttribute is REQUIRED. It shares the same transaction context. 

Для TransacationType.REQUIRES_NEW

Положительный регистр : Не исключение в BlueBean и RedBean. Результат : вставляет данные в две таблицы.

Отрицательный регистр : Допустим, RedBean имеет проблемы при вставке в базу данных. Это исключение. Результат : он должен вставляться только в таблицу Person, но не в таблицу компании. Поскольку атрибут TransactionAttribute равен REQUIRES_NEW Создает новый контекст транзакции.

Но почему-то я не вижу вышеуказанных результатов.

Даже случай Обязательный - Отрицательный случай. Данные вставляются в таблицу Person. Где я кроме этого откатился.

@Resource(name="Test", type=javax.sql.DataSource.class)
@TransactionManagement(TransactionManagementType.CONTAINER)
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public class BlueBean implements Friend {

    @Resource
    private SessionContext sessionContext;

    public String sayHello() {
        return "Blue says, Hello!";
    }

    public String helloFromFriend() {
        try {
            savePerson();
            Friend friend = (Friend) new InitialContext().lookup("java:comp/env/myFriend");
            return "My friend " + friend.sayHello();
        } catch (NamingException e) {
            throw new EJBException(e);
        } catch (CustomRuntimeException e){
           // sessionContext.setRollbackOnly();
            throw e;
        }
    }

    public void savePerson() {
        try {
            DataSource dataSource = (DataSource) new InitialContext().lookup("java:comp/env/Test");
            PersonManager personManager = new PersonManager();
            personManager.save(dataSource);
        } catch (NamingException| SQLException e) {
            throw new EJBException(e);
        }
    }
}



@Resource(name="Test", type=javax.sql.DataSource.class)
@TransactionManagement(TransactionManagementType.CONTAINER)
@TransactionAttribute(TransactionAttributeType.REQUIRED)
public class RedBean implements Friend {


    @Resource
    private SessionContext sessionContext;

    public String sayHello() {

        try {
            save()
        } catch (NamingException| SQLException e) {
            throw new CustomRuntimeException(e);
        }
        return "Red says, Hello!";
    }


    public void save() throws SQLException {

        Connection dbConnection = null;
        Statement statement = null;
        try {
            InitialContext context = new InitialContext();
            DataSource dataSource = (DataSource)context .lookup("java:comp/env/Test");
            dbConnection = ds.getConnection();
            statement = dbConnection.createStatement();

            String insertTableSQL = "INSERT INTO ejb_company"
                    + "(id, name) " + "VALUES"
                    + "(1,'apple')";
           // Just added for testing. 
            if(true) {
                throw new SQLException("test");
            }
            statement.executeUpdate(insertTableSQL);
        } finally {
            if( statement != null )  statement.close();
            if(dbConnection != null) dbConnection.close();
        }
      System.out.println("Company Record is inserted into ejb_company table!");

    }

}


@ApplicationException
public class CustomRuntimeException extends RuntimeException {

    public CustomRuntimeException() {
    }

    public CustomRuntimeException(String s) {
        super(s);
    }

    public CustomRuntimeException(String s, Throwable throwable) {
        super(s, throwable);
    }

    public CustomRuntimeException(Throwable throwable) {
        super(throwable);
    }
}


pom.xml dependencies

<dependency>
      <groupId>org.apache.openejb</groupId>
      <artifactId>javaee-api</artifactId>
      <version>7.0-SNAPSHOT</version>
      <scope>provided</scope>
    </dependency>
 <dependency>
      <groupId>org.apache.openejb</groupId>
      <artifactId>openejb-core</artifactId>
      <version>5.0.0-SNAPSHOT</version>
      <scope>test</scope>
    </dependency>
  </dependencies>

1057 * TestCase *

public class EjbDependencyTest extends TestCase {

    private Context context;

    private EJBContainer ejbContainer;

    protected void setUp() throws Exception {

        Properties p = new Properties();
        p.put(Context.INITIAL_CONTEXT_FACTORY, "org.apache.openejb.core.LocalInitialContextFactory");
        p.put("Test", "new://Resource?type=javax.sql.DataSource");
        p.put("Test.JdbcDriver", "oracle.jdbc.OracleDriver");
        p.put("Test.JdbcUrl", "jdbc:oracle:thin:@test.crop.com:1521/testBlue");
        p.put("Test.UserName", "admin");
        p.put("Test.Password", "######");
        p.put("Test.LogSql", "true");

        ejbContainer = EJBContainer.createEJBContainer(p);
        context = ejbContainer.getContext();
    }

    @Override
    protected void tearDown() throws Exception {
        ejbContainer.close();
    }

    public void testBlue() throws Exception {
        Friend blue = (Friend) context.lookup("java:global/wombat/BlueBean");
        assertNotNull(blue);
        assertEquals("Blue says, Hello!", blue.sayHello());
        assertEquals("My friend Red says, Hello!", blue.helloFromFriend());
    }
}
...