Как проверить откат на исключение с помощью Junit? - PullRequest
0 голосов
/ 06 апреля 2020

У меня есть класс с некоторыми бизнес-логиками c и сохраняется в БД после проверки. Сохранение в БД происходит в новом методе с новой транзакцией, и если есть исключение, он будет откатан.

Класс FooProcessor:

public void process(Map<String, List> fooMap, String name) {
        final List<FooList> fooList = fooMap.get("fooList");
        int successRecordCount = 0;
        int errorRecordCount = 0;
        for (Foo foo : fooList) {
            try {
                //Validation logics
                saveToDB(foo);
            } catch (Exception e) {
                this.fooErrorProcessor.insertIntoError(foo);
            }
        }
    }

Класс FooUpdateProcessor:

@Transactional(propagation = Propagation.REQUIRES_NEW, rollbackFor = Exception.class)
public void saveToDB(Foo foo) {
        BarEntity barEntity = foo.getBarEntity;
        FooEntity fooEntity = foo.getFooEntity;
        BazEntity bazEntity = foo.getBazEntity;

        //Business logic
        //insert Bar and Baz entities to the table

        barDao.save(barEntity);
        bazEntity.save(bazEntity);
        updateFooEntity(fooEntity);

}

public void updateFooEntity(fooEntity) {
        int retryAttempt = 0;
        while (true) {
            try {
                final Optional<QuxEntity> quxOptional = quxDao.findFooByNameAndTypeAndPartId(foo.getName, foo.getType, foo.getPartId);
                if (quxOptional.isPresent()) {
                    QuxEntity quxEntity = quxOptional.get;
                    quxEntity.setState("Success");
                } else {
                    quxDao.insertintoQux(foo.getName, foo.getType, foo.getPartId, "Success"); 
                }
                fooEntity.setStatus("Completed");
                fooDao.save(fooEntity);

            } catch (Exception e) {
                retryAttempt++;
                LOGGER.warn("Exception occurred while updating data");
                if (retryAttempt >= 2) {
                    LOGGER.debug("Threshold reached");
                    throw e;
                }
                Thread.sleep(500);
            }
        }

}

Тестовый класс:

@RunWith(SpringJUnit4ClassRunner.class)
@SpringBootTest(classes = ApplicationTest.class)
@TestPropertySource(locations = "classpath:application-test.properties")
@Sql(value = {"classpath:sql/processor/foo_processor_test.sql"}, config = @SqlConfig(transactionMode = SqlConfig.TransactionMode.ISOLATED))
public class FooProcessorTest {
    private FooProcessor fooProcessor;
    private FooUpdateProcessor fooUpdateProcessor;

    @Autowired
    private FooDao fooDao;
    @Autowired
    private BarDao barDao;
    @Mock
    private QuxDao quxDao;
    @Autowired
    private BazDao bazDao;



    @Before
    public void setUp() {
        fooUpdateProcessor = new FooUpdateProcessor(quxDao, fooDao);
        fooProcessor = new FooProcessor(fooUpdateProcessor, fooDao, barDao, quxDao, bazDao);
    }

    @Test
    @Transactional(isolation = Isolation.READ_COMMITTED)
    public void validateRollBack() {
        List<FooList> fooList = new ArrayList<>();
        FooDato fooDto = new FooDto(1212, null, 1L, 2877, 100L, 17502L, 20801L, null, null, 1000L, 2L, LocalDateTime.of(2019, 5, 15, 10, 20, 30));
        fooList.add(fooDto);
        String fileName = "fooList";        

        Map<String, List> fooMap = new HashMap<>();
        fooMap.put(fileName, fooList);

        Mockito.when(this.quxDao.findFooByNameAndTypeAndPartId(any(),any(),any()))
                .thenThrow(new RuntimeException("DB Error"))
                .thenThrow(new RuntimeException("DB Error"));

        this.fooProcessor.process(fooMap, fileName);
        TestTransaction.flagForCommit();
        TestTransaction.end();

        //Verify
        long insertedRecordCount = this.barDao.countBarById(1);
        long insertedRecordCount = this.fooError.countFooError();
        Assert.assertEquals(0L, insertedRecordCount);
        Assert.assertEquals(1L, errorRecordCount);
    }  
}

Откат не работает. Утверждение BarEntity терпит неудачу в junit. Однако при запуске программы откат работает нормально. Как заставить откат работать в тестовом примере junit? Я что-то здесь упускаю?

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...