Oracle
 sql >> Teknologi Basis Data >  >> RDS >> Oracle

Menggunakan IF EXISTS (SELECT ...) dalam pemicu BEFORE INSERT (Oracle)

Pertama, jika Anda menggunakan SQL*Plus, saat Anda membuat objek dan diberitahu bahwa ada kesalahan kompilasi, perintah show errors akan menunjukkan kesalahannya.

Jika Anda menjalankan show errors , Anda akan diberi tahu bahwa IF EXISTS bukan sintaks yang valid. Anda dapat melakukan sesuatu seperti

SELECT COUNT(*)
  INTO l_cnt
  FROM <<rest of query>>

IF( l_cnt > 0 )
THEN
  RAISE_APPLICATION_ERROR ...
END IF;

Namun, setelah Anda memperbaiki kesalahan kompilasi, Anda akan berakhir dengan kesalahan runtime. Dalam pemicu tingkat baris pada surveillance , Anda biasanya tidak dapat menanyakan surveillance (Anda bisa jika yang Anda lakukan hanyalah INSERT VALUES yang dijamin hanya menyisipkan satu baris). Jika Anda melakukannya, Anda akan mendapatkan kesalahan pemicu bermutasi saat runtime.

Dari perspektif model data, ketika Anda menemukan diri Anda mendesain tabel di mana data yang valid untuk baris tertentu bergantung pada data yang disimpan di baris lain dari tabel yang sama, Anda biasanya telah melanggar prinsip normalisasi dan Anda biasanya lebih baik memperbaiki model data yang mendasarinya.

Jika Anda benar-benar bertekad untuk mempertahankan model data, saya lebih suka membuat tampilan terwujud yang menyegarkan pada komit yang memiliki data hanya untuk baris yang melanggar kriteria Anda. Anda kemudian dapat menempatkan batasan pada tampilan terwujud yang menimbulkan kesalahan pada waktu komit ketika kriteria Anda dilanggar. Ini akan membutuhkan log tampilan yang terwujud di meja Anda.

Jika Anda benar-benar ingin mempertahankan model data dan Anda ingin menerapkan logika dengan pemicu, Anda memerlukan solusi tiga pemicu klasik (atau pemicu gabungan dengan tiga bagian jika Anda menggunakan 11.2 atau lebih baru). Anda akan membuat paket dengan kumpulan nilai kunci utama. Pemicu pernyataan sebelumnya akan menginisialisasi koleksi. Pemicu tingkat baris akan menyisipkan kunci utama dari baris yang disisipkan dan/atau diperbarui ke dalam koleksi ini. Dan kemudian pemicu pernyataan setelah akan mengulangi koleksi ini dan menerapkan pemeriksaan apa pun yang Anda inginkan. Itu banyak bagian yang bergerak, itulah sebabnya saya biasanya menyarankan untuk tidak melakukannya.

Plus, bahkan jika Anda membuat semua bagian ini berfungsi, logika Anda tidak akan melindungi Anda di lingkungan multi-pengguna. Ketika Anda memiliki beberapa pengguna yang menekan sistem secara bersamaan, sangat mungkin bahwa satu pengguna akan menyisipkan baris, pengguna kedua akan memasukkan baris lain dengan rentang yang tumpang tindih, dan kemudian setiap sesi akan dikomit. Dalam hal ini, kedua rangkaian pemicu akan mengizinkan perubahan, tetapi Anda akan tetap memiliki data dalam tabel yang melanggar persyaratan Anda. Tampilan terwujud, karena diberlakukan pada waktu komit daripada pada saat penyisipan, akan bekerja dengan baik di lingkungan multi-pengguna. Jika Anda ingin pemicu bekerja di lingkungan multi-pengguna, Anda harus memperumitnya lebih lanjut dengan menambahkan logika tambahan yang memberlakukan serialisasi yang akan memblokir insert sesi kedua dari menjalankan hingga sesi pertama baik dilakukan atau dibatalkan. Hal itu menambah kerumitan, mengurangi skalabilitas, dan bergantung pada cara penerapannya, dapat membuat dukungan menjadi mimpi buruk.




  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Perbedaan Minus vs Kecuali di ORACLE/SQL Server

  2. Pernyataan dan ketentuan kueri Oracle SQL dengan stempel waktu dan tanggal ISO

  3. Menghubungkan ke Oracle DB berkemampuan SSL melalui Java (JDBC)

  4. Bagaimana cara menghapus nilai kolom berulang dari laporan?

  5. Oracle Order dengan tidak bekerja untuk Subquery dari DUAL