Проверка соответствия значений, найденных курсором, новому условию - PullRequest
0 голосов
/ 11 октября 2018

Итак, я вернулся к процедуре поиска ключей / идентификаторов в схеме.

вот готовая процедура:

CREATE OR REPLACE PROCEDURE SIEROT(i_table_name VARCHAR2) IS
  strSelect      VARCHAR2(32767);
  c                  SYS_REFCURSOR;

  vTYPEPKSTRING  PRODUCTS.TYPEPKSTRING%TYPE;

  TYPE c_list IS TABLE of PRODUCTS.TYPEPKSTRING%type INDEX BY binary_integer; 
  TYPEPK_list c_list; 
  counter integer := 0; 
BEGIN 
  strSelect := 'SELECT DISTINCT i.TYPEPKSTRING ' ||
               '  FROM ' || i_table_name || ' i ' ||
               '  LEFT OUTER JOIN COMPOSEDTYPES c ' ||
               '    ON i.TYPEPKSTRING = c.PK ' ||
               '  WHERE c.PK IS NULL';

    OPEN c FOR strSelect;


  FETCH c INTO vTYPEPKSTRING;

  WHILE c%FOUND LOOP
    counter := counter + 1; 
    TYPEPK_list(counter) := vTYPEPKSTRING; 

    dbms_output.put_line('TABLE: '||i_table_name||'('||counter||'):'||TYPEPK_list(counter)); 

    FETCH c INTO vTYPEPKSTRING;
  END LOOP; 

  CLOSE c;
EXCEPTION
  WHEN OTHERS THEN
    IF c%ISOPEN THEN
      CLOSE c;
    END IF;
END SIEROT;

А вот вызов:

set serveroutput on
DECLARE
    ind integer := 0;
BEGIN
FOR ind IN (select table_name from all_tab_columns where column_name='TYPEPKSTRING' AND table_name!='COMPOSEDTYPES')
  LOOP
    BEGIN
        SIEROT(ind.table_name);
    EXCEPTION 
        WHEN NO_DATA_FOUND THEN
        null;
    END; 
  END LOOP;
END;

Эта процедура ищет все значения для 'typepkstring' в схеме.Это значения ключей, которые можно найти в таблице «mixedtypes» в столбце PK.Более конкретно, в рамках этой процедуры мы находим идентификаторы, которые появляются на схеме и не включаются в это коллективное представление в столбце pk.В моей конкретной бутылке их три.Процедура сообщает мне, в какой таблице был найден ключ.Все отлично работает.Тем не менее, я должен добавить еще один к этой функциональности.У меня есть около 132 таблиц на этой схеме, которые содержат столбцы 'sourcepk' и 'targetpk'.Эти столбцы также содержат цифровые клавиши.Теперь я хочу убедиться в одном: оба этих столбца, т.е. и «sourcepk», и «targetpk», должны быть пустыми для найденных в моих «typepkstrings».

Я знаю, как найти таблицы с интереснымистолбцы:

select distinct  table_name from all_tab_columns where column_name='SOURCEPK' OR column_name ='TARGETPK';

Как правило, я хотел преобразовать эту часть процедуры:

FETCH c INTO vTYPEPKSTRING;

  WHILE c%FOUND LOOP
    counter := counter + 1; 
    TYPEPK_list(counter) := vTYPEPKSTRING; 

    dbms_output.put_line('TABLE: '||i_table_name||'('||counter||'):'||TYPEPK_list(counter)); 

    FETCH c INTO vTYPEPKSTRING;
  END LOOP; 

Я попытался добавить здесь в цикле for вышеприведенный выбор для таблиц, содержащих sourcepk и targetpk.а затем условие if для переменной vTYPEPKSTRING.после операции выборки в данном проходе найденная 'typepkstring' имеет некоторые значения для этих столбцов или нет.Однако из этого ничего не вышло. В общем, я сталкиваюсь с новыми проблемами без перерыва.И мне действительно нужна помощь, по крайней мере, в нацеливании, хотя я бы не презирал код.Заранее благодарю за любые подсказки. :)

1 Ответ

0 голосов
/ 16 октября 2018

Я сложил, соединил и понял.Я отказался от предыдущей конструкции процедуры и решил сделать все заново.

Я использовал 4 вложенных курсора, из которых 2 являются рефрассорами.Все работает в соответствии с предположениями.Спасибо за совет по предыдущему сообщению.

CREATE OR REPLACE PROCEDURE SIEROTKA
IS
    t_name           VARCHAR2(30);
    od_typePK      PRODUCTS.TYPEPKSTRING%TYPE;
    t_nameST       VARCHAR(30);
    od_Source  cat2prodrel.SOURCEPK%TYPE;
    od_Target  cat2prodrel.TARGETPK%TYPE;

    sv_tname VARCHAR2(32767);
    Get_typePK      SYS_REFCURSOR;

    sv_tnameST      VARCHAR2(32767);
    Get_Sierotki         SYS_REFCURSOR;

    CURSOR Get_PK_TN
    IS
        SELECT table_name FROM all_tab_columns
        WHERE column_name='TYPEPKSTRING' AND
        table_name!='COMPOSEDTYPES';

    CURSOR Get_ST_TN
    IS
        SELECT DISTINCT table_name from all_tab_columns
        WHERE column_name='SOURCEPK' OR 
        column_name='TARGETPK';

BEGIN

    OPEN Get_PK_TN;
    LOOP
        FETCH Get_PK_TN INTO t_name;
        EXIT WHEN Get_PK_TN%NOTFOUND;

        sv_tname := 'SELECT DISTINCT i.TYPEPKSTRING FROM ' || t_name || ' i LEFT OUTER JOIN COMPOSEDTYPES c ON i.TYPEPKSTRING=c.PK WHERE c.PK IS NULL';

        OPEN Get_typePK FOR sv_tname;
        LOOP
            FETCH Get_typePK INTO od_typePK;
            IF Get_typePK%FOUND THEN
                    dbms_output.put_line('Znalezione Sirotka to: ' || t_name || ' --------- ' || od_typePK);
            ELSE
                    EXIT WHEN Get_typePK%NOTFOUND;
            END IF;

            OPEN Get_ST_TN;
            LOOP
                FETCH Get_ST_TN INTO t_nameST;
                EXIT WHEN Get_ST_TN%NOTFOUND;

                sv_tnameST := 'SELECT SOURCEPK, TARGETPK FROM ' || t_nameST || ' WHERE PK=' || od_typePK || '';

                OPEN Get_Sierotki FOR sv_tnameST;
                LOOP
                    FETCH Get_Sierotki INTO od_Source, od_Target;
                    IF Get_Sierotki%FOUND THEN
                            dbms_output.put_line('Jednak to nie sierotka, bo posiada wpis: ' || t_name || ' --------- ' || od_typePK || ' ____________ ' || t_namest || ' --------- ' || od_Source || ' --------- ' || od_Target);
                    ELSE
                            EXIT WHEN Get_Sierotki%NOTFOUND;
                    END IF;    
                END LOOP;
                CLOSE Get_Sierotki;

            END LOOP;
            CLOSE Get_ST_TN;

        END LOOP;
        CLOSE Get_typePK;

    END LOOP;
    CLOSE Get_PK_TN;

END;

Для этого простой однострочный вызов в начале и конце блока:

set serveroutput on
BEGIN
    SIEROTKA;
END;
/

До следующего, скоро увидимся.

...