Spring boot test using @Sql scripts keep fails after last test method execution

Viewed 46

I test this code

@SpringBootTest
@TestInstance(TestInstance.Lifecycle.PER_CLASS)
@Sql(scripts = {"/sql/create-member.sql"})
@Transactional
class MemberServiceTest {

    @Autowired
    private MemberRepository memberRepository;

    @ParameterizedTest
    @ValueSource(longs = 1L)
    public void SelectMemberTest_A(Long id) {

        Member member = memberRepository.findById(id).get();

        assertEquals(1L, member.getId());
    }

    @ParameterizedTest
    @ValueSource(longs = 2L)
    public void SelectMemberTest_B(Long id) {

        Member member = memberRepository.findById(id).get();

        assertEquals(2L, member.getId());
    }
}

create-member.sql

CREATE TABLE Member
(
    id       int auto_increment
        primary key,
    username varchar(45),
    phone    varchar(45),
    address  varchar(45),
);

INSERT INTO Member (username, phone, address)
VALUES ('John', '111-1111-1111', null);
INSERT INTO Member (username, phone, address)
VALUES ('Jane', '111-1111-1111', null);
INSERT INTO Member (username, phone, address)
VALUES ('emily', '111-1111-1111', null);
INSERT INTO Member (username, phone, address)
VALUES ('chris', '111-1111-1111', null);
INSERT INTO Member (username, phone, address)
VALUES ('peter', '111-1111-1111', null);
INSERT INTO Member (username, phone, address)
VALUES ('sarah', '111-1111-1111', null);
INSERT INTO Member (username, phone, address)
VALUES ('kate', '111-1111-1111', null);

I keep fail the last test method which is SelectMemberTest_B(Long id) with exception Table "MEMBER" already exists; SQL statement: ...

I know if I put @TestInstance(TestInstance.Lifecycle.PER_CALSS) annotation on top of class, test Data would be created once and all test methods would share data.

But the last test still keep fail.

test result image

1 Answers

@Sql declared at a class level is run for each test method (default setting is to be run before method execution). You should add another @Sql script that drops the table and specify it to run after method:

@Sql(scripts = "cleanup.sql", executionPhase = AFTER_TEST_METHOD)
Related