DBsetup之后,Spring数据不会增加

时间:2018-09-03 03:59:04

标签: java spring-boot spring-data-jpa dbsetup

我有这样的问题。我正在使用DBsetup进行春季启动测试和postgresql数据库。而且我正在使用DBsetup设置用户,但是当我尝试通过spring数据设置另一个用户时,我遇到下一个例外:

Подробности: Key (id)=(1) already exists.

org.springframework.dao.DataIntegrityViolationException: could not execute statement; SQL [n/a]; constraint [users_pkey];

这是我的测试课:

@RunWith(SpringRunner.class)
@SpringBootTest
@TestPropertySource("/application-test.properties")
public class UserRepositoryTest {

    @Autowired
    private ApplicationContext applicationContext;
    @Autowired
    private UserRepository userRepository;
    @Autowired
    private DataSource dataSource;

    @Before
    public void insertData() throws SQLException {
        Operation operation = sequenceOf(CommonOperations.DELETE_ALL, CommonOperations.INSERT_USER);
        DbSetup dbSetup = new DbSetup(new DataSourceDestination(dataSource), operation);
        dbSetup.launch();
    }

    @After
    public void cleanPK() throws SQLException {
        DBUtil.resetAutoIncrementColumns(applicationContext, "user");
    }

    @Test
    public void registerUser() {
        val user = new User(null, "Glass", "123123", "glass999@mail.ru");
        assertEquals(user, userRepository.saveAndFlush(user));
    }

}

DBsetup的操作:

public class CommonOperations {
    public static final Operation DELETE_ALL = deleteAllFrom("article_tag", "article", "tag", "users");
    public static final Operation INSERT_USER =
            insertInto("users")
                    .columns("id", "email", "password", "username")
                    .values(1, "krikkk998@mail.ru", "123123", "Daimon")
                    .build();
}

要重置序列的类:

@NoArgsConstructor
public final class DBUtil {

    public static void resetAutoIncrementColumns(ApplicationContext applicationContext,
                                                 String... tableNames) throws SQLException {
        DataSource dataSource = applicationContext.getBean(DataSource.class);
        String resetSqlTemplate = "ALTER SEQUENCE %s RESTART WITH 1;";
        try (Connection dbConnection = dataSource.getConnection()) {
            for (String resetSqlArgument: tableNames) {
                try (Statement statement = dbConnection.createStatement()) {
                    String resetSql = String.format(resetSqlTemplate, resetSqlArgument + "_id_seq");
                    statement.execute(resetSql);
                }
            }
        }
    }
}

有人知道如何解决这个问题吗?

2 个答案:

答案 0 :(得分:1)

要看的一件事:

public static final Operation INSERT_USER =
        insertInto("users")
                .columns("id", "email", "password", "username")
                .values(1, "krikkk998@mail.ru", "123123", "Daimon")
                .build();

此处您使用的是硬编码ID,即1

现在,在测试用例中,当您试图创建另一个用户时,您将id传递为null,并假设该id应该从序列中选择。它也将从1开始。因此,您会遇到冲突。

答案 1 :(得分:0)

您有一个与约束违反有关的问题。因此,您可以做的一件事是在表中将'id'列更改为"auto_increment"。数据库将负责自动增加此列的值。

在任何时候,如果要重置此id值,都可以调用"resetAutoIncrementColumns()",然后在INSERT SQL中,根本不必指定'id'列。保存新用户时,它将始终插入一个唯一值。

希望这会对您有所帮助。