MySQL не обновляет information_schema, если только я не запускаю ANALYZE TABLE `myTable` - PullRequest
0 голосов
/ 19 декабря 2018

Мне нужно получить последний идентификатор (первичный ключ) таблицы (InnoDB), и для этого я выполняю следующий запрос:

SELECT (SELECT `AUTO_INCREMENT` FROM `information_schema`.`TABLES` WHERE `TABLE_SCHEMA` = 'mySchema' AND `TABLE_NAME` = 'myTable') - 1;

, который возвращает неправильный AUTO_INCREMENT.Проблема в том, что таблица TABLES для information_schema не обновляется с использованием текущего значения, если только я не выполню следующий запрос:

ANALYZE TABLE `myTable`;

Почему MySQL не обновляет information_schema автоматически и как я могу исправить это поведение?
Запуск MySQL Server 8.0.13 X64.

Ответы [ 2 ]

0 голосов
/ 19 декабря 2018
SELECT * FROM tbl ORDER BY insert_datetime DESC LIMIT 1;

получит все данные из «последней» вставленной строки.Нет необходимости иметь дело с AUTO_INCREMENT, нет необходимости использовать подзапросы, нет ANALYZE, нет information_schema, нет дополнительной выборки, если у вас есть идентификатор, нет и т. Д. И т. Д.

Да, вам нужноиндекс столбца, который вы используете, чтобы определить, что является «последним».Да, id можно использовать , но это не должно быть.AUTO_INCREMENT значения гарантированно будут уникальными, но ничто остальное.

0 голосов
/ 19 декабря 2018

Q: Почему MySQL не обновляет информационную_схему автоматически и как я могу исправить это поведение?

A: InnoDB хранит значение auto_increment в памяти,и не сохраняется на диске.

На поведение запросов метаданных (например, SHOW TABLE STATUS) влияет установка innodb_stats_on_metadata и innodb_stats_persistent переменных.

https://dev.mysql.com/doc/refman/8.0/en/innodb-parameters.html#sysvar_innodb_stats_on_metadata

Применение ANALYZE каждый раз, когда мы запрашиваем метаданные, может привести к снижению производительности.

Кроме настроек этих переменных или сбора статистики путем ручного выполнения ANALYZE TABLE, я недумаю, что есть «решение» для этой проблемы.

(я думаю, что в основном потому, что я не думаю, что это проблема, которую нужно исправить.)


Чтобы получить самую высокуюзначение столбца auto_increment в таблице, нормативный шаблон:

 SELECT MAX(`ai_col`) FROM `myschema`.`mytable`

Что меня удивляет, так это то, почему нам нужно извлечь именно этот фрагмент информации.Для чего мы будем его использовать?

Конечно, мы не собираемся использовать это в коде приложения для определения значения, которое было присвоено только что вставленной строке.Нет гарантии, что самое высокое значение не из строки, которая была вставлена ​​каким-либо другим сеансом.И у нас есть механизм LAST_INSERT_ID() для извлечения значения строки, которую только что вставили в нашу сессию.

Если мы воспользуемся ANALYZE TABLE для обновления статистики, между этим и последующим * 1035 еще будет небольшой промежуток времени* ... другой сеанс может проскользнуть в другой INSERT, так что значение, которое мы получим из статистики сбора, может быть "устаревшим" к моменту его получения.

...