Reputation: 850
I'm trying to create a Junit test case. I have a create method which is called from my processor method which creates and saves the entity in the new transaction. The problem is the data that I'm loading in my sql is not available for the new transaction.
Processor method:
public void updateFoo(final Test test) throws ProcessingException {
//Business logics
Foo foo = this.fooHelper.createAndSaveFoo(test);
//other business logics
foo.setName ("Name");
...
...
}
Helper method:
@Transactional(propagation = Propagation.REQUIRES_NEW)
public Foo createAndSaveFoo(final Test test) throws NotFoundException, BadRequestException {
if (this.isFooPresent(test)) {
throw new BadRequestException(LOGGER, "CANNOT_CREATE_FOO", "Foo already created for the test");
}
final Foo foo = this.fooDAO.save(this.fooFactory.createFoo(test));
LOGGER.debug("Foo is saved successfully!, Entity@@ {}", foo);
return foo;
}
Factory method:
public Foo createFoo(final Test test) throws NotFoundException {
return Foo.FooBuilder.aFoo().
withId(test.getId()).
withDate((test.getDate()).
withSize(test.getSize()).
withType(getType(test.getTypeId()).
build();
}
private Type getType(final int id) throws NotFoundException {
return this.typeDAO.findById(id).orElseThrow(() -> new NotFoundException(LOGGER, TYPE_NOT_FOUND, "Invalid type id"));
}
Entity:
@Entity
@Table(name = "foo")
public class Foo {
@Column(name = "id")
private Long id;
@Column(name = "date")
private Date date;
@Column(name = "size")
private Long size;
@ManyToOne
@JoinColumn(name = "type", foreignKey = @ForeignKey(name = "fk__foo__type_id"))
private Type type;
//getters, setters and builders
}
@Entity
@Table(name = "type")
public class Type {
@Column(name = "id")
private Long id;
@Column(name = "date")
private String name;
//getters and setters
}
Test method:
@Test
@Transactional
@Sql(value = {"classpath:sql/create_foo_data.sql"}, executionPhase = Sql.ExecutionPhase.BEFORE_TEST_METHOD)
@Sql(value = {"classpath:sql/clean_everything.sql"}, executionPhase = Sql.ExecutionPhase.AFTER_TEST_METHOD)
public void foo_test() throws ProcessingException {
//GIVEN
Test test = new Test();
test.setId(12);
test.setDate(new Date());
test.setSize(20);
test.setTypeId(1);
// WHEN
this.fooProcessor.updateFoo(test);
// THEN
final List<Foo> foo = this.fooDAO.findAll();
assertEquals(1, foo.size());
assertEquals(20, foo.get(0).getSize());
assertEquals("Test2", foo.get(0).getType().getName());
}
foo_data.sql
INSERT INTO `type` (`id`, `name`) VALUES (0, 'Test1'), (1, 'Test2');
Logs:
com.deep.common.core.exception.NotFoundException: errorCode: 'TYPE_NOT_FOUND' - errorMessage : 'Invalid type id'
at com.deep.process.factory.entity.FooFactory.lambda$createFoo$0(FooFactory.java:55)
at java.util.Optional.orElseThrow(Optional.java:290)
Even though I have inserted type in my sql its not retrived as the createAndSaveFoo() has created new transaction. How can I get my sql data available for new transaction?
Upvotes: 0
Views: 58
Reputation: 754
Have you tried explicitly setting the transactionMode
to ISOLATED
within your @sql
annotation? That may help to ensure that the inserts are committed before your test method is executed. I.E.
@Sql(value = {"classpath:sql/create_foo_data.sql"},
executionPhase = Sql.ExecutionPhase.BEFORE_TEST_METHOD,
config = @SqlConfig(transactionMode = SqlConfig.TransactionMode.ISOLATED))
Upvotes: 1