通过 jdbctemplate 在表中插入记录时如何获取自动增量 ID

Posted

技术标签:

【中文标题】通过 jdbctemplate 在表中插入记录时如何获取自动增量 ID【英文标题】:How can I get the autoincremented id when I insert a record in a table via jdbctemplate 【发布时间】:2012-10-04 16:11:05 【问题描述】:
private void insertIntoMyTable (Myclass m) 
    String query = "INSERT INTO MYTABLE (NAME) VALUES (?)";
    jdbcTemplate.update(query, m.getName());

当上述查询插入一条记录时,表中的ID 列会自动递增。

有没有办法在插入时取回这个自动递增的 ID。所以在这个例子中,我的方法的返回值是int

【问题讨论】:

我认为您可能需要在插入事务之后进行选择。 【参考方案1】:
@Component
public class PersonDao 

    private final JdbcTemplate jdbcTemplate;

    @Autowired
    public PersonDao(JdbcTemplate jdbcTemplate) 
        this.jdbcTemplate = jdbcTemplate;
    

    public List<Person> index() 
        return jdbcTemplate.query("SELECT * FROM person", new BeanPropertyRowMapper<>(Person.class));
    

    public Person show(int id)
        return jdbcTemplate.query("SELECT * FROM person WHERE id=?", new Object[]id, new BeanPropertyRowMapper<>(Person.class))
                .stream().findAny().orElse(null);
    

    public void save(Person person)
        jdbcTemplate.update("INSERT INTO person (name, age, email) VALUES (?, ?, ?)", person.getName(), person.getAge(), person.getEmail());
    

    public void edit(Integer id, Person person) 
        jdbcTemplate.update("UPDATE person SET name = ?, age = ?, email = ? WHERE id = ?", person.getName(), person.getAge(), person.getEmail(), id);
    

    public void delete(Integer id) 
        jdbcTemplate.update("DELETE FROM person WHERE id = ?", id);
    

【讨论】:

【参考方案2】:

JdbcTemplate 是 Spring 的核心。另一种选择是使用SimpleJdbcInsert。

SimpleJdbcInsert simpleJdbcInsert = new SimpleJdbcInsert(jdbcTemplate);
simpleJdbcInsert
    .withTableName("TABLENAME")
    .usingGeneratedKeyColumns("ID");
SqlParameterSource params = new MapSqlParameterSource()
    .addValue("COL1", model.getCol1())
    .addValue("COL2", model.getCol2());
Number number = simpleJdbcInsert.executeAndReturnKey(params);   

你仍然可以@Autowire jdbcTemplate。对我来说,这比使用 jdbcTemplate.update() 方法和 KeyHolder 来获取实际 id 更方便。

示例代码 sn-p 使用 Apache Derby 进行了测试,应该可以与常用数据库一起使用。

使用Spring JPA 是另一种选择 - 如果 ORM 适合您。

【讨论】:

【参考方案3】:

插入后我得到数据库(MSSQL)生成的 id,如下所示,导入:

  import org.springframework.jdbc.core.BeanPropertyRowMapper;
  import org.springframework.jdbc.core.JdbcTemplate;
  import org.springframework.jdbc.core.RowMapper;
  import org.springframework.jdbc.core.SqlParameter;
  import org.springframework.jdbc.core.SqlReturnResultSet;
  import org.springframework.jdbc.core.simple.SimpleJdbcCall;

和代码sn-p:

    final String INSERT_SQL = "INSERT INTO [table]\n"
            + " ([column_1]\n"
            + " ,[column_2])\n"
            + " VALUES\n" +
            " (?, ?)";

    Connection connection = jdbcTemplate.getDataSource().getConnection();
    PreparedStatement preparedStatement = connection.prepareStatement(INSERT_INVOICE_SQL, Statement.RETURN_GENERATED_KEYS);
    preparedStatement.setString(1, "test 1");
    preparedStatement.setString(2, "test 2");

    preparedStatement.executeUpdate();
    ResultSet keys = preparedStatement.getGeneratedKeys();

    if (keys.next()) 
        Integer generatedId = keys.getInt(1); //id returned after insert execution
     

【讨论】:

【参考方案4】:

检查this reference.你可以使用jdbcTemplate.update作为:

编辑 按要求添加导入

import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.SQLException;

import org.springframework.jdbc.core.JdbcTemplate;
import org.springframework.jdbc.core.PreparedStatementCreator;
import org.springframework.jdbc.support.GeneratedKeyHolder;
import org.springframework.jdbc.support.KeyHolder;

以下是代码用法:

final String INSERT_SQL = "insert into my_test (name) values(?)";
final String name = "Rob";
KeyHolder keyHolder = new GeneratedKeyHolder();
jdbcTemplate.update(
    new PreparedStatementCreator() 
        public PreparedStatement createPreparedStatement(Connection connection) throws SQLException 
            PreparedStatement ps =
                connection.prepareStatement(INSERT_SQL, new String[] "id");
            ps.setString(1, name);
            return ps;
        
    ,
    keyHolder);
// keyHolder.getKey() now contains the generated key

【讨论】:

请你把进口的? 我们现在还需要将 Statement.RETURN_GENERATED_KEYS 作为另一个参数传递给 prepareStatement

以上是关于通过 jdbctemplate 在表中插入记录时如何获取自动增量 ID的主要内容,如果未能解决你的问题,请参考以下文章

使用while循环在表中插入多条记录[关闭]

在表中插入数据,在一个查询中使用 FK 更新其他表

在表中插入记录之前/之后删除旧记录,记录数> 2

如果存在则插入仅在表中有记录时才有效

无法使用oracle中的游标在表中插入记录

如果它已经在表中,如何不在sqlite中记录[关闭]