Temat: [Oracle] Procedura update na kilku tabelach z obługą...

Mam problem w bazie z duplikatami klientów. Jest tego ok 7 tys.
Do tej pory poprawiłem ręcznie ok. 200 przypadków.
Wygląda to mniej więcej tak: dla CIF'a o numerze '9999' występują dwa rekordy w tabeli klienci.
Często jest tak, że jeden ma pełne dane a drugi w zasadzie oprócz CIF nie posiada żadnych danych.
Część referencji w innych tabelach dotyczy jednego rekordu o kliencie z CIF '9999' (np. cli_id='1545') a pozostałą część dotyczy drugiego rekordu o tym samym CIF (np. cli_id='218').
Spośród dwóch kandydatów na dany CIF wybieram "lepszego" - najczęściej tego niepustego lub z aktualniejszymi danymi (data w polu cli_import_date) i w 10 tabelach podmieniam wystąpienia cli_id "złego" klienta cli_id "dobrego" klienta, u złego poprzedzam nr cif i PESEL literą "x", i obcinam imię, nazwisko do 3 znaków. (Być może z czasem po kolejnym sprawdzeniu referencji po prostu usnę te "błędne" rekordy - istnieje jakiś kod który sprawdza wszystkie ewentualne odwołania do danego rekordu w pozostałych tabelach?).

Chciałbym to zautomatyzować na wejściu dałbym plik z parami cli_id dla danego nr CIF.


dobre_id, zle_id
155414, 1255555
221122, 55245
484514, 15151
...


Czytałem gdzieś że możliwa jest obsługa zewnętrznych plików w PL/SQL.

Dodatkowo zmiany w identyfikatorach w około 1/100 przypadków powodują naruszenie więzów integralności o czym informuje stosowny błąd.
Jak prawidłowo zrobić obsługę tego błędu by w takiej sytuacji wykonywał się rollback?

Do tej pory "wyprostowałem" ok 200 przypadków z pomocą arkusza Excel'a, który po wpisaniu dwóch cli_id, wyrzuca mi 10 updatów dla każdej z tabel.
COMMIT daję dopiero po poprawnym przejściu na wszystkich 10 tabelach.


UPDATE cct_last_contacts SET lct_cli_id=$dobry_id WHERE lct_cli_id=$zly_id;

UPDATE cct_client_communicators SET cco_cli_id=$dobry_id WHERE cco_cli_id=$zly_id;

UPDATE cct_clients_groups SET cco_cgr_id=$dobry_id WHERE cgr_cli_id=$zly_id;

...



W PL/SQL stawiam dopiero pierwsze kroki, dlatego proszę o pomoc.
Wojciech Muszyński

Wojciech Muszyński Tworzenie aplikacji
bazodanowych
(Oracle, APEX,
Access)

Temat: [Oracle] Procedura update na kilku tabelach z obługą...

Najprościej jest utworzyć procedurę, która będzie to robić


create or replace procedure zamien_cif (pv_dobry_cif_id varchar2, pv_zly_cif_id varchar2)
is
begin
-- W procedurze zamieniasz po koleji tabele
Update tabela1 set cli_id = pv_dobry_cif_id where cli_id = pv_zly_cif_id;
Update tabela2 set cli_id = pv_dobry_cif_id where cli_id = pv_zly_cif_id;
-- pozostałe tabele
Update tabela10 set cli_id = pv_dobry_cif_id where cli_id = pv_zly_cif_id;
-- koniec update

-- Wykasowanie złego rekordu z tabeli głownej
delete from CIF where CIF.ID = pv_zly_cif_id
-- opcjonalnie można nie wykasowywa tylko zmienić stan "złego rekordu" na usunięty
-- Update CIF set "ustaw parametry złego rekordu" where CIF.ID = pv_zly_cif_id
end;


Procedurę wywołujesz w następujący sposób:

zamien_cif (155414, 1255555);
commit;

Dla grupy rekordów procedury można wywołać jedna pod drugą:
zamien_cif (155414, 1255555);
zamien_cif (221122, 55245 );
zamien_cif (484514, 15151 );
commit;

Uwaga: pamiętaj o commit - inaczej zmiany się nie zapiszą, a na bazie mogą powstać blokady.
Zwłaszcza po wielokrotnym wywołaniu funkcji.Wojciech Muszyński edytował(a) ten post dnia 29.11.12 o godzinie 07:46
Wojciech Muszyński

Wojciech Muszyński Tworzenie aplikacji
bazodanowych
(Oracle, APEX,
Access)

Temat: [Oracle] Procedura update na kilku tabelach z obługą...

Druga część pytania związana jest ze znalezieniem klucza obcego.

Tutaj odpowiedzi najszybciej udzieli google, tylko trzeba zadać odpowiednie pytanie:

oracle how to find foreign keys reference

Odpowiedź znaleziona przez googla:


select table_name, constraint_name, status, owner
from all_constraints
where r_owner = :r_owner
and constraint_type = 'R'
and r_constraint_name in
(
select constraint_name from all_constraints
where constraint_type in ('P', 'U')
and table_name = :r_table_name
and owner = :r_owner
)
order by table_name, constraint_name

(owner - to schemat na którym znajdują się obiekty bazy danych)

Sprawdziłem - pięknie działa.

Ogólnie google bardzo dobrze sobie radzi z pytaniami w stylu:

Oracle - how to (opis czynności)

Pozdrawiam

Następna dyskusja:

[mySQL] Trigger kopiujacy d...




Wyślij zaproszenie do