powered by simpleCommunicator - 2.0.51     © 2025 Programmizd 02
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Чтение таблицы из триггера (after-insert)
25 сообщений из 178, страница 2 из 8
Чтение таблицы из триггера (after-insert)
    #40009697
Фотография Stax
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL

Для одиночного insert существует, но запрещен инженерами оракла.

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

сравните с before
Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
SQL> select * from t;

        ID N
---------- ----------
         1 One
         2 Two
         3 Three

SQL> CREATE OR REPLACE TRIGGER
  2  t$tri
  3  BEFORE INSERT ON T FOR EACH ROW
  4  begin
  5   dbms_output.put_line('AFTER INSERT '||:new.id);
  6   for r in (select *  from t) loop --чтение из таблицы триггера
  7    dbms_output.put_line(r.id||' '||r.n);
  8   end loop;
  9  end;
 10  /

Trigger created.

SQL> set serveroutput on
SQL> insert into t values(4,'НеофитSQL');
AFTER INSERT 4
1 One
2 Two
3 Three

1 row created.

SQL> select * from t;

        ID N
---------- ----------
         1 One
         2 Two
         3 Three
         4 НеофитSQL

SQL>



так конечно делать нельзя , пример для понимания мутации

разве что как защита от непонятно чего


ps
я не считаю триггера всемирным злом

.....
stax
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009699
Фотография Stax
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL

Для протоколирования действий у меня отдельная таблица, где действительно работает откат .


прочитайте об автономных транзакциях,
или пишите в файл (в алерт лог например)

.....
stax
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009803
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
boobyЧитать у него времени нет. Триггера писать надо.

Проблема не в совсем в этом, а в том, что ему лень при вызове процедуры перечислять все
поля из new явно. Это же можно пальцы стереть до самых ягодиц.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009840
graycode
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
НеофитSQL
Как это принято делать?

Инкапсулировать логику работы с данными в пакетах.

Dimitry Sibiryakov
Проблема не в совсем в этом, а в том, что ему лень при вызове процедуры перечислять все
поля из new явно. Это же можно пальцы стереть до самых ягодиц.

Думаете, если он научится формировать перечисление полей запросом и узнает, что кроме позиционного указания параметров существует именованное, то проблема исчезнет?
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009881
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Stax
НеофитSQL

Для протоколирования действий у меня отдельная таблица, где действительно работает откат .


прочитайте об автономных транзакциях,
или пишите в файл (в алерт лог например)

.....
stax


Спасибо, я так и делаю. Моя процедура LogError() объявлена автономной через прагму, что позволяет ей быть безоткатной.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009896
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
>Инкапсулировать логику работы с данными в пакетах.
Это я и сделал в начале темы. Возник вопрос: как передать :new в этот пакет, кроме перечисления всех полей?
Динамический SQL для копирования одной строки внутри триггера не рассматривается, это извращение.

Было много рассуждений на все темы, ответа пока нет (я скоро напишу, там две строчки).
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009904
Фотография env
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL,

Под инкапсуляцией логики в пакетах подразумевается управление добавлением/изменением содержимого таблиц через вызов процедур, а не прикручивание пакетов к триггерам. Или у вас в базу может лазить кто угодно и править данные в любой таблице в любое время?
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009917
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Stax
НеофитSQL

Для одиночного insert существует, но запрещен инженерами оракла.

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

сравните с before
Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
SQL> select * from t;

        ID N
---------- ----------
         1 One
         2 Two
         3 Three

SQL> CREATE OR REPLACE TRIGGER
  2  t$tri
  3  BEFORE INSERT ON T FOR EACH ROW
  4  begin
  5   dbms_output.put_line('AFTER INSERT '||:new.id);
  6   for r in (select *  from t) loop --чтение из таблицы триггера
  7    dbms_output.put_line(r.id||' '||r.n);
  8   end loop;
  9  end;
 10  /

Trigger created.

SQL> set serveroutput on
SQL> insert into t values(4,'НеофитSQL');
AFTER INSERT 4
1 One
2 Two
3 Three

1 row created.

SQL> select * from t;

        ID N
---------- ----------
         1 One
         2 Two
         3 Three
         4 НеофитSQL

SQL>



так конечно делать нельзя , пример для понимания мутации

разве что как защита от непонятно чего


ps
я не считаю триггера всемирным злом

.....
stax


Я вижу вы человек обстоятельный, и потратили время написать код.

Я поменял одну строчку, и все заработало:

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
SQL> select * from tst;
                                     ID N
--------------------------------------- --------------------------------------------------------------------------------
                                      1 one
                                      2 two
                                      3 three

SQL> insert into tst values(4,'НеофитSQL');
4 НеофитSQL
1 one
2 two
3 three
1 row inserted

SQL> select * from tst;
                                     ID N
--------------------------------------- --------------------------------------------------------------------------------
                                      4 НеофитSQL
                                      1 one
                                      2 two
                                      3 three

SQL> 



Сам триггер:

Код: plsql
1.
2.
3.
4.
5.
6.
7.
create or replace trigger TR_TST_AFTER_INSERT
  after insert on tst  
begin
  for r in (select *  from tst) loop --чтение из таблицы триггера
    dbms_output.put_line(r.id||' '||r.n);
  end loop;  
end TR_TST_AFTER_INSERT;



О мутации говорило сообщение об ошибке, "нельзя потому что мутация". Меня как человека думающего занимал вопрос - а почему, собственно, таблица мутирует, ведь все уже вставлено?
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009927
dmdmdm
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL
почему, собственно, таблица мутирует, ведь все уже вставлено?


Все уже вставлено after insert.

Не все уж вставлено after insert for each row.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009930
dmdmdm
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
dmdmdm


Все уже вставлено after insert.



Дополнение. Анализировать "все, что вставлено", можно в рамках транзакции. Т.е. не учитывая действия других сессий. Если, как часто бывает, важна очередность действий, вам уже было разъяснено про блокировки и прочие методы обеспечения очередности.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009938
Фотография кит северных морей
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
раз уж пошла такая пьянка, гуглите сразу про микрооткаты и statement restart, чтобы не было сюрпризов, когда до update и delete доберетесь.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009942
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
dmdmdm
dmdmdm


Все уже вставлено after insert.



Дополнение. Анализировать "все, что вставлено", можно в рамках транзакции. Т.е. не учитывая действия других сессий. Если, как часто бывает, важна очередность действий, вам уже было разъяснено про блокировки и прочие методы обеспечения очередности.


Да, я так и понимаю. Очередность действий не важна, если insert вставляет более одной строки, это ожидается.

Я пну еще раз эту довольно-таки мертвую лошадь:

> Не все уж вставлено after insert for each row.

Так решили инженеры Оракл, и в этом наверное есть глубокий смысл, который пока от меня ускользает.

Вместо этого, Оракл мог решить что ВСЕ построчные после-триггеры будут вызваны после того, как все строчки уже вставлены, и таблица не мутирует. Это было бы симметрично поведению до-триггеров, которые ВСЕ вызываются до изменений.

Это умеет делать MSSQL, т.е. это возможно, только не в имплементации оракла. (код ниже).

Почему так сделано в Оракле, мне неизвестно. Запрет существует даже при вставлении одной строки, когда преград нет.

Оракл не позволяет доступиться только к вставленным данным из statemen-level триггера, у MSSQL есть "inserted" псевдотаблица, которая легко бы решила мою задачу:

Код: plsql
1.
2.
3.
4.
5.
6.
7.
8.
9.
CREATE OR REPLACE TRIGGER TR_REACTOR_EVENTS
  after insert on REACTOR_EVENTS -- в таблицу пишутся данные снаружи
--   for each row 
begin
  for rnew in (select * from INSERTED) -- INSERTED не поддерживается в Оракле
  loop
    PROCESS_REACTOR_EVENT( rnew, '-verbose -journal' );
  end loop;
end;



Поэтому у меня так и не получилось передать :new из триггера в процедуру без копирования индивидуальных колонок.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009943
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQLПочему так сделано в Оракле, мне неизвестно.

Ты поймёшь это если попытаешься написать свою собственную СУБД.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009944
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Кстати, в statement-level триггерах у Оракла похоже (я пока не нашел) вообще нет информации о том, что было вставлено или изменено.
Даже количество вовлеченных строчек неизвестно.
Т.е. блочный триггер на удаление вызывается когда было удалено "0 или более" строк.

а что тогда может "instead of insert" блочный триггер делать? Отметить факт пропажи строчек которые не вставились?
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009947
Фотография Stax
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL


Я поменял одну строчку, и все заработало:

...

ведь все уже вставлено?


не одну строчку, а "тип" триггера

в операторных триггерах нет мутации

не все вставлено
напр вставляете сразу три строки, "все вставлено" поcле вставки третьей строки

так и обходят мутацию, накапливают инфу в строчном, и обрабатывают уровня оператора

.....
stax
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009948
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Dimitry Sibiryakov

НеофитSQLПочему так сделано в Оракле, мне неизвестно.

Ты поймёшь это если попытаешься написать свою собственную СУБД.


Возможно, возможно нет. У майкрософта это работает, преграда похоже в голове, а не в принципах СУБД.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009949
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Stax
НеофитSQL


Я поменял одну строчку, и все заработало:

...

ведь все уже вставлено?


не одну строчку, а "тип" триггера

в операторных триггерах нет мутации

не все вставлено
напр вставляете сразу три строки, "все вставлено" поcле вставки третьей строки

так и обходят мутацию, накапливают инфу в строчном, и обрабатывают уровня оператора

.....
stax


Если я правильно понял, я в строчном могу собрать, к примеру, ID вставленных строчек, а на уровне оператора пройтись по списку?
Это чтобы обойти отсутствие "INSERTED" псевдотаблицы в Оракле. Да, так наверное можно, но это уже превращается в тройной прыжок из-за неспособности PL/SQL передать :new как параметр.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009950
Фотография Stax
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL
Кстати, в statement-level триггерах у Оракла похоже (я пока не нашел) вообще нет информации о том, что было вставлено или изменено.
Даже количество вовлеченных строчек неизвестно.
Т.е. блочный триггер на удаление вызывается когда было удалено "0 или более" строк.

а что тогда может "instead of insert" блочный триггер делать? Отметить факт пропажи строчек которые не вставились?


считайте в FOR EACH ROW и используйте в statement-level

ps
"Отметить факт пропажи строчек" - непонятно что пропало
.....
stax
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009951
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQLУ майкрософта это работает, преграда похоже в голове, а не в принципах СУБД.

Да. И мы все знаем чья это голова.

У MS нет триггеров уровня строки.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009954
Фотография env
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL
Это умеет делать MSSQL

Который в отличие от оракла изначально шёл от блокировочной модели, а не от версионной. И в котором есть понятие "грязные чтения".

К тому же, сравнение некорректно как минимум потому, что в mssql нет row level триггеров, о чём явно говорит официальная документация.

авторЗначение FOR или AFTER указывает, что триггер DML срабатывает только после успешного запуска всех операций в инструкции SQL, по которой срабатывает триггер. Кроме того, до запуска триггера должны успешно завершиться все каскадные действия и проверки ограничений , на которые есть ссылки.

НеофитSQL
Запрет существует даже при вставлении одной строки, когда преград нет.

Потому, что row level триггер не знает о существовании других строк. Он срабатывает на действие с конкретной строкой.

А таблицы inserted/deleted, да, полезная штука. Увы, не завезли.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009955
Фотография Stax
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL

Если я правильно понял, я в строчном могу собрать, к примеру, ID вставленных строчек, а на уровне оператора пройтись по списку?
Это чтобы обойти отсутствие "INSERTED" псевдотаблицы в Оракле. Да, так наверное можно, но это уже превращается в тройной прыжок из-за неспособности PL/SQL передать :new как параметр.


можно ид, можно ровиды дело вкуса

зы
насчет :new, смеритесь нет (возможно пока) в оракля new типа "record"

.....
stax
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009957
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQLЕсли я правильно понял, я в строчном могу собрать, к примеру, ID вставленных строчек, а на
уровне оператора пройтись по списку?
Это чтобы обойти отсутствие "INSERTED" псевдотаблицы в Оракле. Да, так наверное можно, но
это уже превращается в тройной прыжок из-за неспособности PL/SQL передать :new как параметр.

Назовите таблицу, в которую будете вставлять вставленные строки, INSERTED и внезапно паззл
сложится.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009958
Фотография env
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
НеофитSQL
Даже количество вовлеченных строчек неизвестно

А зачем оно в триггере?

Вне его есть sql%rowcount.
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009959
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Staxнасчет :new, смеритесь нет (возможно пока) в оракля new типа "record"

А параметр процедуры этого типа есть? Я честно не в курсе...
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
Чтение таблицы из триггера (after-insert)
    #40009961
НеофитSQL
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Stax
НеофитSQL

Если я правильно понял, я в строчном могу собрать, к примеру, ID вставленных строчек, а на уровне оператора пройтись по списку?
Это чтобы обойти отсутствие "INSERTED" псевдотаблицы в Оракле. Да, так наверное можно, но это уже превращается в тройной прыжок из-за неспособности PL/SQL передать :new как параметр.


можно ид, можно ровиды дело вкуса

зы
насчет :new, смеритесь нет (возможно пока) в оракля new типа "record"

.....
stax


Спасибо, смирился. Посмотрел как другие в интернете с этим справляются - копируют по одной колонке, лучше ничего не придумали.
...
Рейтинг: 0 / 0
25 сообщений из 178, страница 2 из 8
Форумы / Oracle [игнор отключен] [закрыт для гостей] / Чтение таблицы из триггера (after-insert)
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]