![]() |
Модераторы: LSD, AntonSaburov |
![]() ![]() ![]() |
|
Samotnik |
|
|||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
Привет
![]() Есть приложение работающее с БД через хибер. Нужно, при удалении записей не удалять их физически из БД, а помечать как удаленные, для того чтобы в последующем, можно было делать запросы на удалённые записи. Сделал это так: добавил в таблицы поле boolean deleted, по дефолту оно false, как только запись удаляется, я сеччу в это поле null, таким образом я избегаю unique constraint violated эксепшена, выглядит это так:
Всё отлично работало с MySQL, в БД спокойно ложились записи вида: ('test1', null) ('test1', null) ('test1', null) ('test1', null) и т.д. Но вот беда, перешёл на Oracle, а там это не прокатывает, получается что там null == null если этот null в состовном ключе находится, и как следствие вылетает constraint violated эксепшен. Вопрос, что можно придумать в данной не простой ситуации, что можете подсказать или посоветовать ![]() ![]() Как вариант, можно попробовать использовать envers, но может другие решения есть ? Это сообщение отредактировал(а) Samotnik - 30.4.2011, 15:54 |
|||
|
||||
Старовъръ |
|
|||
![]() Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 491 Регистрация: 8.5.2008 Репутация: 1 Всего: 10 |
Зачем нужны Unique constraints на deleted?
-------------------- |
|||
|
||||
carper |
|
|||
Бывалый ![]() Профиль Группа: Участник Сообщений: 227 Регистрация: 2.3.2005 Репутация: 2 Всего: 8 |
Null, строго говоря, не следует использовать как флаг, т.к. null - означает неопределенное состояние. Поле - метка удаленной записи не должно нести на себе каких-то уникальных констрейнов, как вам сказал Старовъръ. В сухом остатке - создайте boolean field named as DELETED default false, при удалении заносите туда true, а не null. И поле не должно быть частью первичного ключа! |
|||
|
||||
Samotnik |
|
|||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
Да, но как быть с уникальностью поля name в таком случае ? Их не должно быть более одного одинакового, если оно не помечено как deleted. Добавлено через 12 минут и 30 секунд потому что в БД, не может быть создано более одного имени Nikolai, но удалено их может быть сколько угодно. Если не создать uniqueConstraints на поля "name", "deleted", то как по-другому уникальность реализовать ? Это сообщение отредактировал(а) Samotnik - 3.5.2011, 18:48 |
|||
|
||||
Старовъръ |
|
|||
![]() Опытный ![]() ![]() Профиль Группа: Участник Сообщений: 491 Регистрация: 8.5.2008 Репутация: 1 Всего: 10 |
Ну тогда располагай хотя бы true/false, а не true/null. Ну или в таком случае введи понятие версии, а не флажка. Если мы удалили или что-то изменили, то создается новая версия объекта с таким же ID и с инкременченной версией. Или может имеет смысл это хранить в каком-то архивном хранилище дабы не снижать производительность БД.
Это сообщение отредактировал(а) Старовъръ - 3.5.2011, 22:03 -------------------- |
|||
|
||||
Samotnik |
|
|||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
||||
|
||||
carper |
|
|||
Бывалый ![]() Профиль Группа: Участник Сообщений: 227 Регистрация: 2.3.2005 Репутация: 2 Всего: 8 |
Введите ограничение на то, что поле name просто должно быть уникальным, независимо от того есть ли такое поле помеченное как "удаленное" или нет. Т.к. иначе вы получаете сразу два Васи, отличающихся только тем, что один из них помечен как удаленный - спрашивается и какой из 2-х Васей в таком случае помечен? Более того, поскольку у вас запись только помечена как удаленная, это автоматически предполагает, что вы можете передумать, тогда совсем уж глупо иметь двух Васей, отличающихся только признаком удаленной записи. Я, кстати, вообще подозреваю, что вы на самом деле хотите запись помечать не как удаленную, а как скрытую, или неактуальную, предполагая, что с прежним Васей что-то связано. У вас 100% проблемы не с пометкой полей, а с архитектурой. В частности с первичными ключами. P.S. И причем тут envers? Вам таки нужна версионность и куча записей в архиве на каждого удаленного Васю? Во-первых, это просто делается и без envers - просто введите соотв. поле, во-вторых, версионность для одного и того же Васи, скажем для адресов его проживания, совсем не одно и тоже, что и версионность для ряда совсем разных Вась, в последнем случае, это вообще чушь какая-то получится. ![]() P.P.S. И наличие синтетического первичного ключа по ID в большинстве случаев совсем не освобождает от необходимости "человекопонимаемого" АК. |
|||
|
||||
MisterCleric |
|
|||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1043 Регистрация: 16.2.2006 Где: Харьков, Украина Репутация: 33 Всего: 38 |
Привет всем.
Я делаю так: При пометке записи как удаленная в те поля, которые должны быть уникальны, к существующему значению добавляю метку времени, а также проставляю статус как удаленная. Таким образом поле всегда уникально, избавляемся от композитный констрейнтов и ключей. А также такие записи всегда можно отфильтровать по like. Естественно, что у меня заведомо длина поля больше чем, я предоставляю для ввода пользователем... -------------------- ПРИШЕЛ, УВИДЕЛ - ПЕРЕПИСАЛ... |
|||
|
||||
Samotnik |
|
|||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
не понимаю, как это можно сделать без композитных ключей ? Ведь поле name должно быть само по себе уникально, т.е. что бы пользователь не смог вставить запись Dima дважды ![]() Поясни плиз. И вот это я совсем не понял:
|
|||
|
||||
MisterCleric |
|
|||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1043 Регистрация: 16.2.2006 Где: Харьков, Украина Репутация: 33 Всего: 38 |
Поясню на примере:
1. Было у нас в записи значение поля name Вася. 2. Я помечаю эту запись как удаленную. 3. Апдейчу поле name приблизительно так:
Благодаря тому, что время всегда идет вперед, пользователь никогда не сможет нарушить уникальность Добавлено через 2 минуты и 10 секунд И насчет композитный ключей: у тебя должно быть поле ID с генерируемым числовым значением - автоинкремент, сиквенс, или что там у тебя поддерживает БД -------------------- ПРИШЕЛ, УВИДЕЛ - ПЕРЕПИСАЛ... |
|||
|
||||
Samotnik |
|
||||||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
MisterCleric, прикольно, эванокак
![]() А чем хуже, если объединить name и deleteTimeStamp в UniqueConstraint ? Вроде ж тоже уникальность будет.
С Id тут вообще целая история, он у меня вот так генерится:
где
Вроде так работает и для MySQL и для Oracle |
||||||
|
|||||||
MisterCleric |
|
|||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1043 Регистрация: 16.2.2006 Где: Харьков, Украина Репутация: 33 Всего: 38 |
Можно и так, но какое тогда у тебя будет там значение у "неудаленных" записей? Ведь уже обсудили, что NULL не нормально использовать в уникальных констрейнтах Добавлено через 1 минуту и 10 секунд И по твоему генератору. Какая тогда проблема? Ведь поле name у тебя не участвует в PK записи. -------------------- ПРИШЕЛ, УВИДЕЛ - ПЕРЕПИСАЛ... |
|||
|
||||
Samotnik |
|
|||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
MisterCleric, ясно. А что делать, если есть сущности в которых уже есть композитные ключи, например:
Как в таком случае ее помечать удалённой ? Это сообщение отредактировал(а) Samotnik - 4.5.2011, 13:10 |
|||
|
||||
MisterCleric |
|
|||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Завсегдатай Сообщений: 1043 Регистрация: 16.2.2006 Где: Харьков, Украина Репутация: 33 Всего: 38 |
Но у тебя же здесь композитный ключ состоит из внешних ключей.
На что у тебя здесь идет уникальность? Где то бизнес-поле, которое требует уникальности? У тебя же такая конкретна сущность относится к конкретным внешним сущностям. Если ты их помечаешь как удаленные эта тоже должна быть таковой. Или у тебя эти внешние ключи неуникальны? -------------------- ПРИШЕЛ, УВИДЕЛ - ПЕРЕПИСАЛ... |
|||
|
||||
Samotnik |
|
|||
![]() Super star ! ![]() ![]() ![]() ![]() Профиль Группа: Awaiting Authorisation Сообщений: 7192 Регистрация: 4.11.2006 Где: Минск City Репутация: 5 Всего: 191 |
MisterCleric, да, всё верно, спасибо, должно работать.
Еще вопрос, генерить hashCode() и equals() лучше всего по id или uniqueConstraints или id + uniqueConstraints ![]() |
|||
|
||||
![]() ![]() ![]() |
Правила форума "Java" | |
|
Если Вам помогли, и атмосфера форума Вам понравилась, то заходите к нам чаще! С уважением, LSD, AntonSaburov, powerOn, tux. |
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей) | |
0 Пользователей: | |
« Предыдущая тема | Java EE (J2EE) и Spring | Следующая тема » |
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |