问题描述
我有一个名为Record ID的数据库列。这是一个主键,其值是使用具有以下属性的oracle序列生成的 序列细节 最低价值:1 最大值:9999999999999999999999999999 增加:10
在我的Java应用程序中,我在应用一些业务逻辑后将记录插入表中。字段Record ID的值是从序列生成器获取的
在插入记录之前,我先在Java代码中使用以下代码(从序列生成器获取)在Java Long变量中设置其ID
public static final String recordSequencesql= "SELECT RECORD_ID_SEQ.NEXTVAL FROM DUAL"
Long recordID = jdbcTemplate.queryForObject(SELECT_EVENT_LOG_SEQUENCE_sql,Long.class);
recordDao.save(recordID,record_name,age);
recordID的值显示为-8742538778(在我从序列生成器收到此值之后),其前面带有减号。
我需要确保没有收到负值。我不确定根本原因,也需要解决相同的问题
解决方法
要排除故障,请尝试以下步骤
检查序列
与您的应用程序用户连接并运行以下查询:
select SEQUENCE_OWNER,SEQUENCE_NAME,MIN_VALUE,MAX_VALUE,INCREMENT_BY,CACHE_SIZE,LAST_NUMBER
from all_sequences
where SEQUENCE_NAME = 'RECORD_ID_SEQ';
SEQUENCE_OWNER SEQUENCE_NAME MIN_VALUE MAX_VALUE INCREMENT_BY CACHE_SIZE LAST_NUMBER
------------------------------ ------------------------------ ---------- ---------------------------- ------------ ---------- -----------
<owner> RECORD_ID_SEQ 1 9999999999999999999999999999 10 20 1202020
重要值在LAST_NUMBER
列中,大约是您通过调用NEXTVAL
获得的值。
您将看不到一个负号(如果如此,则立即获得Oracle支持)。
您应该看到的是一个适中的数字,如示例中所示。
一个潜在的问题是,如果您看到一个大于9223372036854775807
的数字,该数字是Long
的最大值,但在 sequence {{1 }}。
但是即使在这种情况下,您也不会从MAX_VALUE
查询中得到负数-而是会得到JdbcTemplate
异常
Numeric Overflow
摘要
负值问题很可能是在Caught: org.springframework.jdbc.UncategorizedSQLException:
StatementCallback; uncategorized SQLException for SQL [SELECT RECORD_ID_SEQ.NEXTVAL FROM DUAL];
SQLstate [99999];
error code [17026];
Numeric Overflow;
nested exception is java.sql.SQLException: Numeric Overflow
查询中(您未显示)。
其他建议
在SELECT_EVENT_LOG_SEQUENCE_SQL
列中使用Long
类型的同时,将序列的MAX_VALUE调整为ID
的最大值,请参见here进行进一步的讨论
如果您希望使用频繁的序列,请不要使用LONG
10,而要使用INCREMENT_BY
在Marmite Bomber指出问题可能出在SQL之后。进行了以下更正
之前 public void saveRecordData(Long RecordId,RecordLog RecordLog) { Object[] parameters = {recordID,RecordLog.getRouteId(),RecordLog.getRecordType().getRecordTypeId(),RecordLog.getOrderId(),RecordLog.getIncomingRecordTimestamp(),RecordLog.getOutgoingRecordTimestamp(),RecordLog.getStatus()}; int[] types = {Types.INTEGER,Types.INTEGER,Types.VARCHAR,Types.TIMESTAMP,Types.VARCHAR}; int rowsAffected = jdbcTemplate.update(INSERT_Record_LOG_SQL,parameters,types); }
之后(将SQL类型从TYPES.INTEGER更改为TYPES.BIGINT) public void saveRecordData(Long RecordId,RecordLog.getStatus()}; int[] types = {Types.BIGINT,types); }