Может быть. Обычно да, но есть ряд случаев, когда это ненадежно.
Драйвер MySQL JDBC предполагает, что пакет сгенерированных значений автоинкремента является последовательным при выполнении пакетной вставки.
См. Код в java.com.mysql.cj.jdbc.StatementImpl.getGeneratedKeysInternal ()
Упрощая логику, соответствующие биты:
long beginAt = getLastInsertID();
for (int i = 0; i < numKeys; i++) {
row[0] = StringUtils.getBytes(Long.toString(beginAt));
beginAt += this.connection.getAutoIncrementIncrement();
}
Таким образом, он начинается с идентификатора первой вставленной строки и предполагает, что последующие сгенерированные значения идентификатора - это просто следующие numKeys
значения, увеличивающиеся на значение конфигурации auto_increment_increment
(по умолчанию 1).
Может ли это пойти не так? Да, в нескольких случаях. Например:
Если вы делаете многорядную INSERT
, указав NULL для некоторых строк и действительное целочисленное значение для других строк в том же операторе INSERT
, предположение драйвера JDBC о том, что все значения будут последовательными значения после значения, возвращенного LAST_INSERT_ID()
, неверны.
Если вы сделаете многорядную INSERT...ON DUPLICATE KEY UPDATE
или REPLACE
, где некоторые строки существуют, а другие нет, он будет неверно сообщать набор последовательно сгенерированных ключей.
Если вы установите innodb_autoinc_lock_mode = 2
(«чередующийся» режим блокировки), то многострочные операторы INSERT, которые выполняются одновременно, могут не быть последовательными. Каждый из них будет генерировать значения идентификаторов всякий раз, когда это возможно, и это будет непредсказуемо чередоваться, как перетасовывание двух половинок колоды карт. См https://dev.mysql.com/doc/refman/8.0/en/innodb-auto-increment-handling.html