Hibernate.Генераторы улучшенных идентификаторов - PullRequest
4 голосов
/ 08 декабря 2011

Я решил использовать генератор идентификаторов Hibernate, который удовлетворяет следующим требованиям: - безопасная генерация идентификаторов при доступе к домену из разных приложений (разных JVM) - использовать интервалы идентификаторов (не запрашивать базу данных каждый раз, когданужен новый идентификатор)

После некоторых исследований я выбираю один из 2-х генераторов расширенных идентификаторов hibernate, это

org.hibernate.id.enhanced.TableGenerator

Проблема в том, что этот алгоритм хранит в базе данных не следующее доступное значение, а конец следующего доступного интервала, поэтому, скажем, у меня есть генератор идентификатора с increment_size 10, когда я делаю запрос на идентификатор, я получаюинтервал 1 - 10, но в базе данных теперь хранится не значение 11, а 21. При таком поведении мне приходится сохранять increment_size одинаковым для всех классов, которые отображаются на конкретную таблицу.Почему у него такое поведение?Есть ли способ это исправить?

Ответы [ 2 ]

4 голосов
/ 09 июля 2012

org.hibernate.id.enhanced.TableGenerator определяет таблицу, которая может генерировать несколько значений одновременно.Похоже, вы пытаетесь заставить его генерировать идентификаторы из одного значения для нескольких сущностей.Это контролируется настройкой конфигурации TableGenerator для сегмента'gment_value ', если вы хотите воспользоваться этим преимуществом.

А что касается значений, то здесь нечего "исправлять".Это не сломано.Если вы хотите другое поведение, настройте другое поведение.Это контролируется так называемым оптимизатором, определяемым настройкой конфигурации «оптимизатора» TableGenerator.Все это рассматривается в руководстве: http://docs.jboss.org/hibernate/orm/4.1/manual/en-US/html_single/#mapping-declaration-id См., В частности, раздел «5.1.2.3. Усовершенствованные генераторы идентификаторов» и «5.1.2.3.1. Оптимизация генератора идентификаторов».В руководстве не рассказывается обо всех доступных оптимизаторах.Похоже на то, что вы хотите, называется "pooled-lo", который похож на "pooled", но хранит значение lo, а не высокое значение.

1 голос
/ 22 января 2017

Этот пост старый, но для тех, у кого могут быть такие же проблемы.

Как указал Стив Эберсол, вы должны использовать оптимизатор "pooled-lo" в вашем случае. Проверьте также свою версию гибернации, она должна быть> = 4.3.11, потому что в предыдущих версиях была проблема .

Чтобы пояснить это с помощью оптимизатора pooled-lo, значение, хранимое в базе данных, является нижним значением следующего доступного интервала.

Таким образом, если идентификатор последней сохраненной сущности находится в [1; 10], следующий доступный интервал будет [11,20], а значение, хранящееся в базе данных, будет 11, как вы и ожидали.

Таким образом, если у вас есть другая программа, которая не использует hibernate и даже не знает о размере приращения, определенном в конфигурации hibernate, она все равно сможет вставлять объекты без прерывания последовательности.

Все, что ему нужно будет сделать - это атомарно получить значение последовательности и увеличить его, а затем использовать извлечение значения (до «приращения») в качестве нового идентификатора сущности, который он хочет вставить. В нашем примере для вставки одной строки будет обновлено значение последовательности до 12 и добавлена ​​новая сущность с идентификатором 11. Таким образом, когда hibernate достигнет последнего идентификатора своего текущего интервала в памяти (10), он запросит базу данных и сохранит значение 22, чтобы сохранить для себя новый интервал id [12; 21].

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...