Есть ли ограничения в RI

UAP
Дата: 20.09.2012 18:17:17
Господа!

Корректно ли использовать RI в таких двух случаях:

- Таблица с ЧЕТЫРЬМЯ индексами типа REGULAR, ее записи ссылаются на ЧЕТЫРЕ материнские таблицы
- Таблица имеет ТРИ дочерние таблицы

Отмечу, что когда в открытой базе данных запускаю RI, в его таблице присутствуют ВСЕ пары родительских и дочерних таблиц, везде, где нужно я выбираю КАСКАД на удаление, но при тестировании НЕ везде работает каскадное удаление.
Иногда, те записи в дочерних таблицах, которые должны быть удалены, не помечены как удаленные.

Помогите разобраться.
Jonny540
Дата: 21.09.2012 08:09:47
UAP,

Не удалось повторить. :( Все работает. Может, неправильно понял?
"Кабы схемку аль чертеж - мы б затеяли вертеж..." (с)
UAP
Дата: 21.09.2012 12:40:36
Уважаемый Jonny540!

Я тоже на "модели" получаю правильные результаты.

Хотелось бы увидеть ФОРМАЛЬНОЕ описание условий работы RI, чтобы найти проблему в реальной задаче, которая очень закручена.

Вероятно, я нарушаю некоторые требования к состоянию таблиц, участвующих в RI.

Может быть RI может работать на определенную глубину родитель-ребенок, либо ограничение на количество связей с другими таблицами, либо ограничение на количество индексов в таблице и т.д.
ВладимирМ
Дата: 21.09.2012 21:26:23
Откройте хранимые процедуры и изучайте триггера. В чем проблема-то.

У RI как таковой нет специальных ограничений. Это же просто построитель хранимых процедур для организации определенного типа ссылочной целостности. Причем механизм далеко НЕ универсальный. Ограничения есть у собственно FoxPro. Например, запрет на рекурсивный вызов триггера. Если у Вас получилась древовидная структура, то удалить всю иерархию через RI - не получится. Хотя собственный триггер вне рамок RI для этого написать можно

А если задача "закручена", то изучайте как у Вас там обстоят дела с транзакцией и буферизацией. Может, триггера-то срабатывают как надо, да только у Вас либо буфер какой сбрасывается позже, либо откат транзакции происходит. Может Вы просто подавили сообщение об ошибке.

Кстати, если Вы не в курсе, то RI в процессе своей работы создает глобальный массив gaErrors(). Если в результате работы триггера происходит ошибка, то в этот массив записывается причина ошибки. Посмотрите, не записалось ли ту чего в тех случаях, когда у Вас не все удалилось
UAP
Дата: 21.09.2012 23:06:19
Уважаемый ВладимирМ!

Пожалуйста, объясните о какой древовидной структуре, где RI может не работать, Вы говорите.
ВладимирМ
Дата: 22.09.2012 20:39:44
"Классический" способ хранения древовидной иерархии. Одна и та же таблица с двумя полями: ID - код записи, ParentID - ссылка на "родителя" (запись этой же таблицы). Так вот, построить RI между этими полями можно, но каскадное удаление работать будет только для одного уровня. При количестве уровней больше одного произойдет рекурсивный вызов (вызов триггера изнутри самого себя), что запрещено в VFP
UAP
Дата: 23.09.2012 20:19:54
Уважаемый ВладимирМ!

В моем случае, материнские и дочерние записи принадлежат РАЗНЫМ таблицам, САМОССЫЛОЧНОСТИ нет.

Не знаю почему, но сайт sql.ru, в последнее время, часто невозможно открыть.

Когда такое случается я расстаиваюсь, поскольку ощущаю очень большую пользу для себя от форума.
ВладимирМ
Дата: 23.09.2012 21:36:34
Я упомянул классическую древовидную иерархию, только как иллюстрацию того факта, что использование триггеров вообще (и RI как частный случай триггеров) имеет свои ограничения. Что именно накручено в Вашем приложении - не известно. Вы ведь сами не понимаете, что у Вас там творится. Так что, тут Вам никто не поможет. Ищите ошибку сами.

Как я уже говорил, скорее всего, Вы где-то просто подавляете сообщение об ошибке. Т.е. FoxPro Вам говорит, что вот этого он сделать не может, но Вы от его слов "отмахиваетесь".

Кроме того, Вы упомянули только о триггерах на удаление, но ничего не сказали о триггерах на вставку/модификацию. Может, у Вас после удаление просто создаются новые или изменяются существующие записи. Вот Вам и кажется, что не все удалилось.