Mungkin ada kalanya perlu untuk menyelidiki perubahan terbaru pada database dan melaporkan apa yang diubah, kapan dan oleh siapa. Selama bertahun-tahun paket DBMS_LOGMNR Oracle telah tersedia untuk tugas-tugas seperti itu tetapi permintaannya belum sepenuhnya tercakup. Metode konvensional menggunakan prosedur ADD_LOGFILE() untuk menyiapkan Penambang Log untuk digunakan dengan panggilan dasar ke prosedur START_LOGMNR. Ini memulai utilitas dengan SCN saat ini sebagai titik awal. Ada cara lain untuk memulai Log Miner, dengan memilih SCN awal yang valid dan memberikannya ke panggilan START_LOGMNR(). Dalam artikel ini, Anda akan melihat bagaimana hal ini dapat dilakukan, dan, dalam prosesnya, mengungkapkan kemungkinan area yang menjadi perhatian dengan alokasi PGA.
Melihat skrip 'plain vanilla' untuk memulai Log Miner, panggilan prosedur biasa dibuat untuk memulai Log Miner dengan SCN saat ini:
---- run_logmnr.sql---- Tambahkan file log dan setel DBMS_LOGMNR ke-- terus menambang archivelogs--set linessize 200 trimspool pada ukuran halaman 0---- Tambahkan file log yang ada---- Abaikan file log standby- -pilih 'exec dbms_logmnr.add_logfile('''||member||''')'dari v$logfilewhere ketik <> 'STANDBY'dan anggota di (pilih min(anggota) dari v$logfile grup per grup#)spool /tmp/add_logfiles.sql/spool off@/tmp/add_logfiles---- Mulai logmnr dalam mode ranjau berkelanjutan--exec dbms_logmnr.start_logmnr(options => DBMS_LOGMNR.DICT_FROM_ONLINE_CATALOG + DBMS_LOGOMS_MINE>NATALOG + DBMS_LOGMNR.)Perhatikan bahwa semua log redo yang tersedia ditambahkan sebelum memulai Log Miner. Ada metode lain yang memasok SCN awal ke panggilan start_logmnr, selama database berjalan dalam mode ARCHIVELOG:
BEGIN DBMS_LOGMNR.START_LOGMNR( startScn =>, endScn => , OPTIONS => DBMS_LOGMNR.DICT_FROM_ONLINE_CATALOG + DBMS_LOGMNR.COMMITTED_DATA_ONLY + DBMS_LOGMNR.CONTINUOUS_pre>);END;/ Menariknya, SCN akhir tidak diperlukan untuk memulai sesi Penambang Log. Basis data harus dalam mode ARCHIVELOG agar opsi CONTINUOUS_MINE dapat ditentukan karena Log Miner akan secara otomatis menambahkan setiap file log arsip yang tersedia saat dijalankan. Menggunakan metode ini memungkinkan SCN tertentu digunakan untuk memulai pencarian apa pun; menentukan pencarian tanda kurung SCN akhir sehingga hanya sebagian data terbatas yang dikembalikan ke tampilan V$LOGMNR_CONTENTS dan menyediakan titik pemberhentian untuk pencarian, sehingga kueri tampilan dapat dihentikan. Ini adalah tugas sederhana untuk memantau kemajuan Penambang Log dengan memeriksa log peringatan basis data saat entri yang ditandai dengan 'LOGMINER' terdaftar. Entri lengkap akan menyertakan baris BEGIN dan END, seperti yang ditunjukkan di bawah ini:
Senin 07 Okt 12:48:22 2019LOGMINER:Akhiri file log penambangan untuk sesi -2147482111 utas 1 urutan 9776, /Oracle/archive/awcis/awcis_0000009776_0001_1008544071.arcMon Okt 07 12:48:22 2019LOGMINER:Mulai menambang file log untuk sesi - 2147482111 utas 1 urutan 9777, /oracle/archive/awcis/awcis_0000009777_0001_1008544071.arcMon 07 Okt 12:48:36 2019LOGMINER:Akhiri file log penambangan untuk sesi -2147482111 utas 1 urutan 9777, /oracle/archive/awcis/awcis_0000009777_00007.ar100854 :48:36 2019LOGMINER:Mulai menambang file log untuk sesi -2147482111 utas 1 urutan 9778, /Oracle/archive/awcis/awcis_0000009778_0001_1008544071.arcMon Okt 07 12:48:49 2019LOGMINER:Akhiri file log penambangan untuk sesi -2147482111 utas 1 urutan 9778, / oracle/archive/awcis/awcis_0000009778_0001_1008544071.arcMon Oct 07 12:48:49 2019LOGMINER:Mulai menambang logfile untuk sesi -2147482111 utas 1 urutan 9779, /oracle/archive/awcis/awcis_0000009779_0001_1008544071.arcUntuk sesi Oracle lokal, jumlahnya adalah bilangan bulat positif; untuk sesi jarak jauh, yang diprakarsai oleh utilitas seperti Perl, Python, C/C++ atau bahasa lain, bilangan bulat negatif akan terlihat (entri yang ditunjukkan di atas dimulai oleh skrip Python). Nama file log akan menggilir log redo online dan salinan arsip yang tersedia.
Memulai Log Miner dengan cara ini juga dapat menimbulkan kesalahan seperti 'missing logfile' ketika rentang SCN atau SCN awal yang dipilih tidak lagi tersedia di aliran redo. Kueri yang berjalan lama dapat mengalami kesalahan seperti itu. Selain itu, jika SCN berada di luar jangkauan sehubungan dengan file log yang tersedia, Penambang Log tidak akan memulai, melempar:
ERROR pada baris 1:ORA-01292:tidak ada file log yang ditentukan untuk sesi LogMiner saat iniORA-06512:pada "SYS.DBMS_LOGMNR", baris 58ORA-06512:pada baris 2Untuk membantu menghilangkan kesalahan seperti itu, memilih FIRST_CHANGE# dari tampilan V$LOG akan memberikan titik awal yang valid untuk sesi Log Miner; menggunakan kueri serupa terhadap V$ARCHIVED_LOG akan mengembalikan semua SCN awal yang tersedia untuk salinan redo yang diarsipkan.
Ini bukan satu-satunya komplikasi menggunakan Log Miner dengan cara ini. Bergantung pada seberapa banyak informasi yang akan dikembalikan, proses Logmminer dapat mengalokasikan sejumlah besar memori PGA yang dapat, jika pga_aggregate_limit kecil, menimbulkan kesalahan berikut:
ORA-04036:Memori PGA yang digunakan oleh instans melebihi PGA_AGGREGATE_LIMITuntungnya ini bukan kesalahan fatal. Karena sumber daya PGA tidak lagi diperlukan, memori dapat dilepaskan kembali ke database untuk digunakan di tempat lain. Namun, mungkin diperlukan waktu sedikit lebih lama dari yang diinginkan untuk melepaskan memori tersebut kembali ke kumpulan memori. Pilihannya adalah mengatur pga_aggregate_limit lebih tinggi dari jumlah sesi Log Miner yang dapat mencegah terjadinya kesalahan. Bagaimana Anda tahu memori apa yang dialokasikan untuk sesi tersebut? Tampilan, V$PROCESS_MEMORY_DETAIL, tersedia di database. Tetapi mencoba menanyakan tampilan ini tanpa persiapan akan kembali:
tidak ada baris yang dipilih.Ini adalah masalah yang relatif kecil, tetapi memerlukan penggunaan utilitas oradebug. Langkah-langkah berikut akan memuat data ke dalam V$PROCESS_MEMORY_DETAIL:
---- Atur pengenal sesi saat ini-- oradebug setmypid---- Menggunakan PID dari proses yang diinginkan-- buang data memori---- Ini mengisi V$PROCESS_MEMORY_DETAIL--oradebug pga_detail_get- --- Permintaan tampilan untuk mendapatkan data yang diinginkan--pilih * Dari v$process_memory_detail;---- Untuk mengisi kembali tampilan dengan data yang lebih baru-- cukup jalankan oradebug pga_detail_get-- pernyataan--oradebug pga_detail_get Sebuah skrip untuk melakukan tindakan ini ditunjukkan di bawah ini:
---- Siapkan lingkungan untuk panggilan oradebug--oradebug setmypidset echo off trimspool onset verifikasi fundefine p_1undefine p_2undefine s1undefine s2variable p1 numbervariable p2 numbercolumn sys_date new_value sysdt noprintpilih ke_char(sysdates'DH), 'RR_MMS'D ganda; -- Dapatkan id proses dari sesi--column pid new_value p_1pilih pid dari v$proses tempat addr masuk (pilih paddr dari v$session di mana nama pengguna =' ' dan sid =(pilih maks(sid) Dari v$session where username =' '));begin :p1 :=&p_1;end;/---- Buang detail proses ke v$process_memory_detail--oradebug dump pga_detail_get &p_1spool &p_1._pga_stats_&sysdt..log--- - Dapatkan informasi sesi untuk --COLUMN alme HEADING FORMAT "Allocated MB" 99999D9COLUMN menggunakan HEADING "Used MB" FORMAT 99999D9COLUMN dari HEADING "Freeable MB" FORMAT 99999D9COLUMN mame HEADING "Max MB" FORMAT 99999D9COLUMN username FORMAT program a FORMAT a22COLUMN sid FORMAT a5COLUMN spid FORMAT a8column format pid_remote a12SET LINESIZE 300SELECT s.username, SUBSTR(s.sid,1,5) sid, p.spid, logon_time, SUBSTR(s.program,1,22) program , s.process pid_remote, s.status, ROUND(pga_used_mem/1024/1024) usme, ROUND(pga_alloc_mem/1024/1024) alme, ROUND(pga_freeable_mem/1024/1024) frme, ROUND(pga_max_mem/1024/1024) mameFROM v$session s, v$process pWHERE p.addr=s.paddrAND s.username =' 'ORDER BY pga_max_mem,logon_time;---- Tidur 30 detik---- Dapatkan informasi sesi lagi--exec dbms_lock.sleep(30) kolom sid new_value s1 noprintSELECT s.username, SUBSTR(s.sid,1,5) sid, p.spid, logon_time, SUBSTR(s.program,1,22) program , s.process pid_remote, s.status, ROUND( pga_used_mem/1024/1024) usme, ROUND(pga_alloc_mem/1024/1024) alme, ROUND(pga_freeable_mem/1024/1024) frme, ROUND(pga_max_mem/1024/1024) mameFROM v$session s,v$process pWHERE p.addr=s.paddrAND s.username =' 'ORDER BY pga_max_mem,logon_time;exec dbms_lock.sleep(10)pilih max(sid) sid dari v$session dimana username =' ';---- Dapatkan info memori proses--kategori KOLOM HEADING "Kategori"KOLOM yang dialokasikan HEADING "Byte yang dialokasikan"COLUMN yang digunakan HEADING "Byte yang digunakan"COLUMN max_allocated HEADING "Byte yang dialokasikan maks"PILIH pid, kategori, dialokasikan, digunakan, max_allocatedFROM v$process_memoryWHERE pid in (SELECT pid FROM v$process WHERE addr in (pilih paddr FROM v$session WHERE sid =&&s1));exec dbms_lock.sleep(10)SELECT pid, kategori, dialokasikan, digunakan, max_allocatedFROM v$process_memoryWHERE pid in (PILIH pid FROM v$process WHERE addr in (pilih paddr FROM v$session WHERE sid =&&s1));exec dbms_lock.sleep(10)pilih pid dari v$process whe re addr in (pilih paddr dari v$session where username =' ' and sid =(pilih max(sid) from v$session where username =' '));---- Simpan pass pertama pga stats--CREATE TABLE tab1 ASSELECT pid, kategori, nama, heap_name, byte, alokasi_hitung, heap_descriptor, parent_heap_descriptorFROM v$process_memory_detailWHERE pid =&p_1DAN kategori ='Lainnya';---- Dapatkan pass kedua pga stats--detail_oradebugget dump &p_1exec dbms_lock.sleep(120)---- Simpan pass kedua dari pga stats--CREATE TABLE tab2 ASSELECT pid, kategori, nama, heap_name, byte, alokasi_hitung, heap_descriptor, parent_heap_descriptorFROM v$process_memory_detailWHERE pid =&p_1DAN'; ---- Mulai laporan akhir---- PGA heap info--kategori KOLOM HEADING "Kategori"nama KOLOM HEADING "Nama"COLUMN heap_name HEADING "Nama heap"KOLOM q1 HEADING "Memory 1st" Format 999,999,999,999COLUMN q2 HEADING "Memory 2nd " Format 999.999.999,9 99COLUMN diff HEADING "Difference" Format S999.999.999.999SET LINES 150PILIH tab2.pid, tab2.category, tab2.name, tab2.heap_name, tab1.bytes q1, tab2.bytes q2, tab2.bytes-tab1.bytes diffFROM tab1, tab2WHERE tab1.category =tab2.categoryAND tab1.name =tab2.nameAND tab1.heap_name =tab2.heap_nameand tab1.pid =tab2.pidAND tab1.bytes <> tab2.bytesORDER BY 1, 7 DESC;--- Logminer PGA info- -COLUMN heap_name HEADING "heap name"COLUMN name HEADING "Type"COLUMN alokasi_count HEADING "Count"COLUMN bytes HEADING "Sum"COLUMN avg HEADING "Rata-rata" FORMAT 99999D99SELECT pid, heap_name, name, allocation_count, byte, byte/allocation_count avHEFROM_name tab seperti 'Logminer%';spool offdrop table tab1 purge;drop table tab2 purge; Simpan kode ini sebagai skrip dan edit teks untuk mengganti string
dengan akun pengguna yang menjalankan Log Miner. Script secara khusus menargetkan memori Logminer sehingga dapat dipantau untuk peningkatan. Itu juga dapat dimodifikasi untuk mencari area memori bermasalah lainnya. Komentari perintah 'jatuhkan tabel' untuk mempertahankan tab1 dan tab2 untuk penelitian lebih lanjut, jika diinginkan karena area memori lain mungkin menarik. Periksa juga dukungan Oracle untuk masalah terkait PGA yang diketahui. Laporan tersebut kemungkinan akan memiliki kueri untuk digunakan untuk menyelidiki area masalah tertentu menggunakan V$PROCESS_MEMORY_DETAIL. Untuk kemanfaatan, kueri tambahan tersebut dapat ditambahkan ke kode yang ditunjukkan di atas untuk melaporkan semua area yang dicurigai dari memori proses. Data ini akan berperan dalam membuktikan perlunya penerapan patch khusus satu kali ke database. Log Miner bisa menjadi alat yang sangat berguna dalam menyelidiki tindakan saat ini dan yang relatif baru-baru ini ke database. Mungkin perlu untuk memantau alokasi PGA saat sesi Log Miner aktif sehingga tindakan pencegahan seperti meningkatkan pga_aggregate_limit dapat dijalankan, dan sesi tidak akan dihentikan secara tiba-tiba. “Diperingatkan sebelumnya adalah dipersenjatai”, seperti kata pepatah, dan meskipun DBA tidak memiliki empat tangan, mengetahui apa yang ada di depan selalu merupakan pengetahuan yang berharga.
Lihat semua artikel oleh David Fitzjarrell