|
|
|
JPA (Hibermate) custom sequence
|
|||
|---|---|---|---|
|
#18+
abc_daivanraЛучше уж сериализацию через синхронизируемый методчто это такое? Когда мы вставляем записи с применением select max() + 1, то возможна ситуация, когда 2 разные транзакции - одновременно получили одно и то же значение select max() + 1. При этом, прочитав значение, они должны обеспечить целостность, поэтому они блокируют вставку из чужой транзакции - если чужая транзакция вставит новое значение, то эта транзакция будет неконсистентна; - теперь они не могут вставить, поскольку заблокировали друг друга - каждая транзакция ждет, когда другая закончится, чтобы самой вставить, либо выдать ошибку о нарушении уникальности - налицо дедлок. Выход - использовать для вставки сериализуемые транзакции, или хотя бы использовать сериализуемую транзакцию для обращения к сохраненной процедуре, генерирующей идентификаторы. Но, поскольку заводить дополнительную транзакцию для вставки хлопотно, проще упорядочить генерацию с помощью synchronized метода (метод можно сделать статическим, либо использовать синглтон). По аналогии с бумажным делопроизводством - каждый по очереди подходит и делает запись в журнале о получении номера. Код: java 1. 2. 3. 4. 5. 6. 7. 8. 9. 10. 11. 12. 13. 14. 15. Конечно, всё это будет работать, если номера получаем только из этого генератора, поэтому, если приложений много, надо организовывать web-сервис, RMI и тому подобное ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 16.12.2013, 16:19:00 |
|
||
|
JPA (Hibermate) custom sequence
|
|||
|---|---|---|---|
|
#18+
конечно же, Код: java 1. 2. 3. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 16.12.2013, 16:23:49 |
|
||
|
JPA (Hibermate) custom sequence
|
|||
|---|---|---|---|
|
#18+
Как вариант - можно сначала прочитать select max() в первой транзакции, закрыть её, затем открыть вторую транзакцию и уже вставлять с новым вычисленным значением, ловить исключение, пробовать по новой и т.д. но insert into XXX... (select max() ... from XXX), или просто select/insert в одной транзакции - 100% дедлок, если не обеспечена последовательность ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 16.12.2013, 16:45:52 |
|
||
|
JPA (Hibermate) custom sequence
|
|||
|---|---|---|---|
|
#18+
ivanraКак вариант - можно сначала прочитать select max() в первой транзакции, закрыть её, затем открыть вторую транзакцию и уже вставлять с новым вычисленным значением, ловить исключение, пробовать по новой и т.д. но insert into XXX... (select max() ... from XXX), или просто select/insert в одной транзакции - 100% дедлок, если не обеспечена последовательностьЕсли СУБД поддерживает конструкцию типа UPDATE ... RETURNING(...), то изменение может быть атомарным. Запрос делать в отдельной транзакции, запрашивать "пачками", т.е. наращивать на большое число, а сущностям потом отдавать по одному, что позволит сократить количество запросов в базе. ... |
|||
|
:
Нравится:
Не нравится:
|
|||
| 16.12.2013, 16:59:18 |
|
||
|
|

start [/forum/topic.php?fid=59&msg=38502387&tid=2127969]: |
0ms |
get settings: |
10ms |
get forum list: |
12ms |
check forum access: |
3ms |
check topic access: |
3ms |
track hit: |
40ms |
get topic data: |
8ms |
get forum data: |
2ms |
get page messages: |
32ms |
get tp. blocked users: |
1ms |
| others: | 242ms |
| total: | 353ms |

| 0 / 0 |
