Гость
Целевая тема:
Создать новую тему:
Автор:
Форумы / Oracle [игнор отключен] [закрыт для гостей] / TRIGER или JOB? / 19 сообщений из 19, страница 1 из 1
18.04.2003, 08:31
    #32143721
Sergey M. Medvedev
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Здраствуйте!

Есть такая задача:
Внешнее приложение добавляет в некую таблицу записи.
После добавления записи необходимо без задержек ее обработать, т.е. запустить процедуру.

Вопрос: как это правильнее реализовать?

Пробовал JOB с перодом 1 раз в секунду (проверяет наличие записей и запускает процедуру), но получается задержка ~3-4 сек.

Если поставить тригер на insert то увеличивается время добавления записи в таблицу, т.к. процедура долго обрабатывает соотв. записи. В процедуре используются commit и rollback, и это вызывает исключение в тригере.

Внешнее приложение должно быстро добавить запись и забыть про нее. Дальнейшая обработка должна осуществляться Oracle.

Нужно, что-то типа "triger after commit" на таблицу.

Заранее спасибо за ответы.
...
Рейтинг: 0 / 0
18.04.2003, 09:01
    #32143747
AI
AI
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
dbms_alert - извещает ждущую сигнала процедуру при commit.
...
Рейтинг: 0 / 0
18.04.2003, 09:12
    #32143761
Mergen
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
А почему бы неиспользовать trigger after insert с автономными транзакциями.
...
Рейтинг: 0 / 0
18.04.2003, 12:24
    #32143828
Denis Popov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
У тебя получаются два взаимно противоречивых условия:

- После добавления записи необходимо без задержек ее обработать, т.е. запустить процедуру.
- Внешнее приложение должно быстро добавить запись и забыть про нее.

Ланчей даром не бывает: либо ты выполняешь все действия в одной транзакции, увеличивая ее время, либо выполняешь те же самые действия по заданию. во втором случае ты можешь, к примеру, job создавать прямо в триггере с nextdate=>sysdate, interval=>null. Но надо быть уверенным, что процесс, который будет его выполнять, "увидит" все требуемые данные, т.е. оти будут зафиксированы в сессии, их изменяющей.
...
Рейтинг: 0 / 0
18.04.2003, 12:32
    #32143843
AI
AI
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
2 Denis Popov.

dbms_alert как раз и решает такую задачу. Одна из сессий готовит данные и сигнал, который посылается ждущей сессии при commit'е. Ждущая сессия при получении сигнала просыпается и делает необходимую обработку.

Но я бы все-таки использовал AQ или dbms_job для более гибкой работы. В данном случае, триггер неприемлем.
...
Рейтинг: 0 / 0
18.04.2003, 12:35
    #32143844
softy
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Насколько я знаю, для этого можно использовать так называемые очереди.
Об этом в книге Тома Кайта например пишется.
Он приводит пример готового чужого проекта, что пользователь вводит данные, потом идёт транзакция длинная для обработки, при этом естественно блокируется интерфейс в ожидании(на 45 сек. кажется). Он переделал это через очередь, при этом юзер спокойно вводит данные не ожидая завершения процедуры обработки.
Я так понимаю, это как раз и нужно?
...
Рейтинг: 0 / 0
18.04.2003, 12:57
    #32143900
Denis Popov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
А кто посылает алерт? Всяко не триггер (иначе он же бы полылал commit), а, я думаю, процедура, совершающая обработку? И еще: другая сессия должна постоянно вызвать dbms_alert.waitany или wainone, т.е. заниматься постояным опросом? Если автор топига говорит о 3-4 секундной задержке как о недопустимой, не слишком ли это большие расходы?
...
Рейтинг: 0 / 0
18.04.2003, 14:00
    #32144001
AI
AI
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
waitany/waitone висят и ждут. Их не надо гонять в цикле (хотя можно задавать таймауты ожиданий).
...
Рейтинг: 0 / 0
18.04.2003, 14:24
    #32144029
Denis Popov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
В любом случае в соседней сессии... Вроде получается 2 подхода:
1. Commit -> Signal Alert.
2. Commit -> Submit Job.
...
Рейтинг: 0 / 0
18.04.2003, 14:39
    #32144061
Sergey M. Medvedev
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
И что лучше на Ваш взгляд?
Alert или Job?
...
Рейтинг: 0 / 0
18.04.2003, 14:40
    #32144066
AI
AI
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
AQ - advanced queuing.
...
Рейтинг: 0 / 0
18.04.2003, 15:13
    #32144124
Denis Popov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Лично я между Alert и Job выбрал вы последнее. Причина- не думаю, что мне бы понравилась сесия, вечно или продолжительное время висящая в ожидании алерта: черт его знает, почему она висит, задание выполняет или просто ждет? Заодно бы читал про AQ.
...
Рейтинг: 0 / 0
21.04.2003, 11:19
    #32144882
Sergey M. Medvedev
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Задержка получается еще больше!!!

Повесил на таблицу тригер:

Код: plaintext
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
DECLARE 
  job_no binary_integer;
  sql_str varchar2( 1024 );
  pragma autonomous_transaction;
BEGIN
    sql_str := 'begin dbms_job.submit(:job_no, :x_what, sysdate, null); commit; end;';
    execute immediate sql_str using out job_no, in 'inbox_routing_job;';

EXCEPTION WHEN others then
  null;
END;


JOB Срабатывает через 9 секунд после выполнения тригера???
...
Рейтинг: 0 / 0
21.04.2003, 13:23
    #32145037
Denis Popov
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
За выполнение JOB'в отвечают соответствующие процессы:
http://download-west.oracle.com/docs/cd/B10501_01/server.920/a96521/jobq.htm

В твоем случае ИМХО можно или поиграться с параметрами JOB_QUEUE_PROCESSES, JOB_QUEUE_INTERVAL, либо делать через алерты. Но учти: для выполнения задания сразу в момент прихода алерта тебе надо обеспечить ситуацию, когда кто-то постоянно его (алерт) ждет. По существу- имитировать работу Job Queues. Заодно представь ситуацию, когда "обработчик" записи- весьма продолжниельна я
процедура:

Код: plaintext
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.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
create table test (
    test_id number( 9 )
  , entry_date date
  , constraint pk_test primary key(test_id)
)
/
create table test2 (
    test_id number( 9 )
  , entry_date date
  , constraint pk_test2 primary key(test_id)
)
/

create or replace procedure insert_test2 (
  p_test_id number
) as
begin
  insert into test2 (test_id, entry_date)
  values (p_test_id, sysdate);
end;
/
create or replace trigger tbir_test
before insert on test
for each row
begin
  :new.entry_date := sysdate;
end;
/

create or replace trigger tair_test
after insert on test
for each row
declare v_job integer;
  pragma autonomous_transaction;
begin
  dbms_job.submit (
      job => v_job
    , what => 'begin insert_test2('||:new.test_id||'); end;'
    , next_date => sysdate -  1 / 24 / 60 / 60 
    , interval => null
  );
  commit;
end;
/
begin
  for i in  1 .. 20  loop
    insert into test(test_id) values (i);
  end loop;
end;
/

select t.test_id
     , t.entry_date t_entry_date
     , t2.entry_date t2_entry_date
from test t
   , test2 t2
where  1 = 1 
  and t.test_id = t2.test_id
/
...
Рейтинг: 0 / 0
28.04.2003, 08:37
    #32149716
Sergey M. Medvedev
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Вы говорите использовать AQ!
т.е. тригер при insert'е помещает задание в очередь с помощью ENQUEUE
а кто это задание считывать будет (DEQUEUE)?
Как узнать, что в очередь что-то добавилось?

И еще, на каждую запись должна запускаться соотв. процедура, и если она ее долго обрабатывает, то остальные записи не должны ждать завершения обработки предыдущей. Т.е. их надо пускать паралельно???

У кого какие мысли по этому поводу???
...
Рейтинг: 0 / 0
28.04.2003, 08:46
    #32149717
Oracle X-pert
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Esli ne ustraivaet ni to, no drugoe, to , moget, nado by izmenit' podhod k resheniu tvoei zadachi??
...
Рейтинг: 0 / 0
28.04.2003, 08:50
    #32149721
Виктор
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
У меня в проекте почти то, о чем ты говоришь, сделано через Alert'ы.
Человек делает проводку товарного документа - при этом в табличку пишется соответств. инфа и посылается алерт. На серваке висит прога, которая ловит этот алерт и запускает нужные процедурины (скорость обработки зависит от многих параметров). И так по циклу. Прога-обработчик выделена отдельно для того, чтобы попутно писать-читать логи, а вообще можно и прям в оракле всё сделать. Т.о. реализована обычная очередь. Параллельности обработки у меня нет, т.к. сложно при одновременной проводке двух док-тов проверять остатки, писать кэши дебиторки и т.п.
Конечно, можно переделать на AQ, но как говорится - работает, не трожь :-)
...
Рейтинг: 0 / 0
28.04.2003, 09:19
    #32149733
Oracle X-pert
Участник
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Alert, AQ, CORBA etc..
But check Your buisiness-logic!
...
Рейтинг: 0 / 0
28.04.2003, 11:36
    #32149902
Sergey M. Medvedev
Гость
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
TRIGER или JOB?
Ура, получилось!!!
Использую AQ. При помещении в очередь проблем нет.
Подскажите как теперь их оттуда корректно забирать.

Вот этот код работает, но мне надо, чтоб он постоянно висел.
(здесь ждет 20 секунд)

Для этого я убрал параметр v_DequeueOptions.wait, но кто должен запустить эту процедуру на выполнение???

Может в триггере на StartUp???

Код: plaintext
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.
DECLARE
  v_Message InboxObj;
  v_DequeueOptions DBMS_AQ.DEQUEUE_OPTIONS_T;
  v_MessageProperties DBMS_AQ.MESSAGE_PROPERTIES_T;
  v_MsgID RAW( 16 );

  e_QTimeOut EXCEPTION;
  PRAGMA EXCEPTION_INIT(e_QTimeOut, - 25228 );
BEGIN

  BEGIN
    LOOP
      v_DequeueOptions.wait :=  20 ;
      DBMS_AQ.DEQUEUE(
        queue_name => 'InboxQ',
        dequeue_options => v_DequeueOptions,
        message_properties => v_MessageProperties,
        payload => v_Message,
        msgid => v_MsgID);

      v_Message.Process;
    END LOOP;
  EXCEPTION
    WHEN e_QTimeOut THEN
      NULL;
  END;

  COMMIT;
END;
...
Рейтинг: 0 / 0
Форумы / Oracle [игнор отключен] [закрыт для гостей] / TRIGER или JOB? / 19 сообщений из 19, страница 1 из 1
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


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