sobota, 22 października 2011

Tryb flashback

We wcześniejszycj postach pisałem juz o zapytaniach typu as of timestamp. Teraz robimy level up i  będziemy widzieć całą bazę z określonego punktu w czasie. Dane które będziemy widzieć pochodzą z przestrzeni UNDO , więc musimy pamiętać o właściwym ustawieniu parametru undo_retention.
Do tej sztuczki-magiczki wykrzystujemy pakiet dbms_flashback, więc jeśli chcemy z niego korzystać z innego użytkownika niż sys musimy temu użytkownikowi nadać odpowiednie uprawnienia:

grant execute on dbms_flashback to hr;


Następnie dokonujemy kilku zmian po których odróżnimy aktualny stan od stanu po zmianach. Dobrze jest sobie zapisać kiedy zmiany miały miejsce:



update employees set salary=3000;
commit;
update departments set manager_id=100;
commit; --13:37

Kolejnym krokiem jest włączenie trybu flashback. Musimy podać czas, z którego stan chcemy oglądać. Czas musi być podany jako timestamp:


begin
dbms_flashback.enable_at_time(to_timestamp('13:30:00 22-10-2011','hh24:mi:ss dd-mm-yyyy' ));
end;


Możesz teraz zajrzeć do tabel które zmieniałeś:


select * from employees;
select * from departments;




Zauważ że widzisz te tabele w stanie z czasu który podałeś w enable_at_time, nie trzeba dorzucać as of timestamp - bo to jest tutaj jakby parametrem domyślnym.  Minus jest taki, że mając włączony ten tryb nie możemy zmieniać nic w bazie. Baza działa w trybie flashback i jest tylko do odczytu. Nie możemy też wykonać żadnej operacji DDL. Oczywiście ograniczenie to dotyczy tylko aktualnej sesji.
 
Aby wyłączyć tryb flashback stosujemy to:

begin
dbms_flashback.disable;
end;

niedziela, 9 października 2011

Tuning generowania statystyk

Zapewne często spotykacie się z koniecznością odtwarzania statystyk dla obiektów. Powstaje pytanie - dla ktorych tabel i których indeksów odświeżać statystyki? Dla wszystkich może okazac się zbyt kosztowne.
Mamy możliwość włączenia specjalnego monitoringu dla kilku tabel i odtwarzać statystyki tylko dla tych obiektów które tego wymagają. To czy tego wymagają czy nie określamy my, poprzez wskazanie wartości procentowej danych w obiekcie które zostały zmienione. Określamy np. że jeżeli zmieniło się 14% danych w tabeli employees to dla tej tabeli mają zostać wygenerowane statystyki.
Pierwsze co czynimy to ustawienia dla tabel:


alter table employees monitoring;

Następnie co jakiś czas otwarzamy statystyki dla schematu, ale w sposób  nieco zmieniony:

execute dbms_stats.gather_schema_stats(ownname=>'hr',estimate_percent=>14,options=>'GATHER STALE');

Powyżej wywołałem odtwarzanie statystyk w schemacie hr dla tabel które zmieniły sie w 14 lub więcej procentach. Objęte tym będą tylko tabele dla których włączyliśmy monitoring.
Teraz wystarczy to wrzucić w jakiegoś joba, by statystyki odtwarzały nam się cyklicznie.

Indeksy wirtualne

Fajny stuff dla tunerów.
Jeśli zastanawiasz się nad założeniem jakiegoś indeksu, musisz idee odłożyć czasem na  bok i skonfrontować się z rzeczywistoscią. Na dużych tabelach zakładanie indeksu będzie trwałoooooo.... Teraz przetestowanie różnych kombinacji zajmie nam zbyt dużo czasu. Możemy założyć wirtualny indeks na kolumnie, tylko po to by sprawdzić jak zachowa się optymalizator kosztowy mając taki indeks.  W rzeczywistości "prawdziwy" indeks nie będzie nakładany.

create index mojanazwa on tabela(kolumna) nosegment;

żeby to zadziałało musimy jeszcze włączyć specjalną opcję dla sesji (czyli przy ponownym połączeniu to juz nie bedzie dzialalo):

alter session set "_use_nosegment_indexes"=true;


Tego indeksu nie będziecie widzieli w user_indexes jak normalne indeksy, za to zobaczycie go w slowniku USER_OBJECTS.

PS. Pozdrowienia dla uczestników szkolenia ORAA w Gdyni w Altkomie w zeszłym tygodniu dla super załogi z BPH!  Obyśmy jeszcze mięli okazję się spotkać. I ćwiczyć tam! Ćwiczyć! :)

Przenoszenie tabeli do innego tablespace

alter table przykladowa move tablespace dane;

przykładowa - nazwa tabeli
dane - nazwa tablespace'a

Towrzenie tablespace'a

Jak szybko stworzyć tablespace? Masa jest w dokumentacji Oracle metod z dziesiątkami przełączników, znaczników a my tymczasem potrzebujemy zwykłego nowego tablespace'a który się automagicznie rozszerza pod wdrożenie jakiegoś CRMa.

create tablespace dane datafile 'c:\oraclexe\oradata\xe\dane.dbf' size 100M autoextend on next 10M;

Z oraclowego na nasze:
dane - nazwa tablespace
datafile 'c:.......'  - określa gdzie ma leżeć nasz plik danych tego tablespace'a . Najlepiej by leżał tam gdzie inne pliki danych. To możemy sprawdzić zaglądając do słownika v$datafile
size 100M  - początkowa wielkośc tablespace'a. Określa jaka przestrzeń ma zostać zaalokowana na potrzeby pliku danych tego tablespace'a
autoextend on - czyli że ma się automatycznie rozszerzać.
next 10M - czyli że jak skończy się początkowo zaalokowana przestrzeń (w tym przypadku 100M) to tablespace ma zostać rozszerzony o kolejne 10M.

Monitorowanie blokad







W praktyce administratora zdarzy się Wam nie raz, że jakiś user zmieni dane a nie zatwierdzi albo nie wycofa zmian i w ten sposób zablokuje zasób. Polecenia innych użytkowników którzy zechcą zmienić te same dane, będą czekać na zdjęcie blokady (a tymczasem użytkownik wyszedł, lub system który założył blokadę zawiesił się). Możemy sprawdzić kto i co nam blokuje w ten sposób:

select sid,serial#,lmode,l.request,status,osuser,machine,terminal,program,schemaname, o.name
from v$lock l join obj$ o on (l.id1=o.obj#)
join v$session s on (s.sid=l.sid);



W razie potrzeby możemy ubić sesję która blokuje nam zasób:

alter system kill session 'sid,serial';

SID i SERIAL podstawiamy odpowiedni z wyniku pierwszego zapytania.

Tryb Serializable

Opcja przydatna przy wszelkiego rodzaju analizach, Mamy taką możliwość by w ramach jednej sesji widzieć dane z momentu jej rozpoczęcia. Dzięki temu nie zachodzi niebezpieczeństwo, że dane zostaną zmienione w trakcie analizy.

alter system set isolation_level=serializable