有没有办法使用NamedParameterJdbcTemplate和GeneratedKeyHolder提取主键(或ROWID)?

dar*_*isa 6 java spring ojdbc

我试图使用Spring的NamedParameterJdbcTemplate和GeneratedKeyHolder提取ROWID或主键.

我想做这样的事情.

MapSqlParameterSource parameters = new MapSqlParameterSource()
                .addValue("param1", value1)
                .addValue("param2", value2);
KeyHolder keyHolder = new GeneratedKeyHolder();
namedParameterJdbcTemplate.update("INSERT INTO TABLE(ID, col1, col2)"
                + "VALUES(TABLE.TABLE_SEQ.NEXTVAL, :param1, :param2)",
                parameters, keyHolder);
Run Code Online (Sandbox Code Playgroud)

执行上面的查询后,当我尝试这样做keyHolder.getKey().longValue()时抛出异常.

HTTP Status 500 - Request processing failed; nested exception is org.springframework.dao.DataRetrievalFailureException: The generated key is not of a supported numeric type. Unable to cast [oracle.sql.ROWID] to [java.lang.Number]
Run Code Online (Sandbox Code Playgroud)

当我通过这个http://docs.oracle.com/cd/B28359_01/java.111/b31224/datacc.htm时,我理解(我希望我这样做)ojdbc没有将oracle RowId映射到java RowId.

任何人都可以建议有什么方法可以提取密钥吗?(是的,它可以使用PreparedStatement完成,但它使我的代码在某些条件下阅读和操作有点难看).非常感谢您的建议.

Win*_*ins 14

你必须使用它

namedParameterJdbcTemplate.update("INSERT INTO TABLE(ID, col1, col2)"
            + "VALUES(TABLE.TABLE_SEQ.NEXTVAL, :param1, :param2)",
            parameters, keyHolder, new String[]{"ID"});
Run Code Online (Sandbox Code Playgroud)

  • 它不适用于超过7列的表,你有没有解决这个问题的方法 (2认同)

sup*_*ova 5

这是一个完整的工作示例:假设数据库是 Oracle,并且存储生成的 Id 的列名称是“GENERATED_ID”(可以是任何名称)

       public Integer insertRecordReturnGeneratedId(final MyObject obj)
        {
        final String INSERT_QUERY = "INSERT INTO MY_TABLE  VALUES(GENERATED_ID_SEQ.NEXTVAL, :param1, :param2)";
        try
            {
                MapSqlParameterSource parameters = new MapSqlParameterSource().addValue( "param1", obj.getField1() ).addValue( "param2",  obj.getField1() ) ;
                final KeyHolder holder = new GeneratedKeyHolder();
                this.namedParameterJdbcTemplate.update( INSERT_QUERY, parameters, holder, new String[] {"GENERATED_ID" } );
                Number generatedId = holder.getKey();
               // Note: USING holder.getKey("GENERATED_ID") IS ok TOO.
                return generatedId.intValue();
            }
            catch( DataAccessException dataAccessException )
            {
    }
    }
Run Code Online (Sandbox Code Playgroud)