избегать зависаний в оракуле - PullRequest
0 голосов
/ 04 октября 2019

У меня есть процедура в pl / sql, которая отлично работает с небольшим количеством данных. Проблема в том, что когда большой объем данных, cursor6 иногда зависает сессия, и другие пользователи не могут получить доступ к table5. Таблица5 имеет столбец первичного ключа «ocf», который является идентификатором пользователя, поэтому каждый пользователь имеет доступ только к тем строкам, которые соответствуют его идентификатору. Даже в этих условиях курсор 6 блокирует таблицу 5 и создает мертвый сеанс, и я не понимаю, как, но он не позволяет другим пользователям получать к нему доступ, даже если они используют другие строки в таблице 5. Есть ли решение воссоздать этот курсор для обновления или использовать что-то, что может сделать то же самое, избегая таким образом этого зависания сеанса?

cursor cursor6(pf varchar2,PO number, psu varchar2) is select * from table5 where ocf=PO and .. for update;
row1 cursor6%rowtype;
BEGIN
   delete table5 where ocf=PO;
    commit;
    open cursor1;
    fetch cursor1 into wv,wd;
    if cursor1%found then
    open cursor2;
      fetch cursor2 into wf;
      if cursor2%found then
      while cursor2%found loop
          open cursor3;
          fetch cursor3 into wco;
          if cursor3%found then
            while cursor3%found loop
                open cursor5;
                  fetch cursor5 into ws;
                  while cursor5%found loop
                       open cursor4;
                       fetch cursor4 into ..;
                       if cursor4%found then
                            open cursor6(..);
                            fetch cursor6 into row1;
                            if cursor6%notfound then insert into table5 values (..);
                            else update table5 set ... where current of cursor6;    
                            end if;
                            close cursor6;
                       end if;
                       close cursor4;
                   end loop;
                close cursor5;
            end loop;
          end if;
          close cursor3;
        end loop;
       end if;
     close cursor2;
    end if;
    close cursor1;
    commit;
    delete table5 where ocf=PO;
    commit;

1 Ответ

3 голосов
/ 04 октября 2019

Черт возьми, удачи с 6 вложенными циклами.


cursor6 блокирует таблицу5 и создает мертвую сессию, и я не понимаю как, но она не позволяет другим пользователямк доступам

Это происходит, когда столбцы внешнего ключа не проиндексированы. Я предлагаю вам проверить, так ли это, и - если это так - создать индексы.


Вот запрос (автор Том Кайт ) (у меня нет ссылки наоригинал, извините, Google для этого, если хотите), который отображает неиндексированные ограничения внешнего ключа. Я немного изменил его, добавив what для отображения:

  • PAR_WHAT:
    • 0 - показать только отсутствующие
    • 1 - показать действительные
    • NULL - показать все

Я предлагаю сначала запустить его с PAR_WHAT = 0.

WITH forkey
     AS (SELECT DECODE (b.table_name, NULL, '****', 'ok') Status,
                a.table_name,
                a.columns column_1,
                b.columns column_2
           FROM (  SELECT SUBSTR (a.table_name, 1, 30) table_name,
                          SUBSTR (a.constraint_name, 1, 30) constraint_name,
                             MAX (
                                DECODE (position,
                                        1, SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        2, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        3, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        4, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        5, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        6, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        7, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        8, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (position,
                                        9, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   10, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   11, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   12, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   13, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   14, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   15, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   position,
                                   16, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                             columns
                     FROM user_cons_columns a, user_constraints b
                    WHERE     a.constraint_name = b.constraint_name
                          AND b.constraint_type = 'R'
                 GROUP BY SUBSTR (a.table_name, 1, 30),
                          SUBSTR (a.constraint_name, 1, 30)) a,
                (  SELECT SUBSTR (table_name, 1, 30) table_name,
                          SUBSTR (index_name, 1, 30) index_name,
                             MAX (
                                DECODE (column_position,
                                        1, SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        2, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        3, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        4, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        5, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        6, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        7, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        8, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (column_position,
                                        9, ', ' || SUBSTR (column_name, 1, 30),
                                        NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   10, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   11, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   12, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   13, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   14, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   15, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                          || MAX (
                                DECODE (
                                   column_position,
                                   16, ', ' || SUBSTR (column_name, 1, 30),
                                   NULL))
                             columns
                     FROM user_ind_columns
                 GROUP BY SUBSTR (table_name, 1, 30),
                          SUBSTR (index_name, 1, 30)) b
          WHERE     a.table_name = b.table_name(+)
                AND b.columns(+) LIKE a.columns || '%'
                AND a.table_name NOT LIKE 'HEP_DP%')
  SELECT f.status,
         f.table_name,
         f.column_1,
         f.column_2
    FROM forkey f
   WHERE f.status =
            CASE
               WHEN :par_what = 1 THEN 'ok'
               WHEN :par_what = 0 THEN '****'
               ELSE f.status
            END
ORDER BY f.table_name, f.column_1, f.column_2;
...