Veritabanları bu noktada yardımımıza koşuyor fakat verinin değişimi noktasında bize neler sunuyor diye bir soru geçebilir aklınızdan. İşte bu noktada gelişmiş veritabanı sistemlerinde olan yöntemlerden birisi de Log (Kayıt Altına Alma) işlemidir. Basit olarak şöyle bir örnekle düşünebilirsiniz. Bir mağazam var ve bu mağazadaki ürünlerimin bilgilerini tuttuğum bir veritabaı mevcut. Örneğin; ürün adı, marka, ebatlar, renk vs.. bilgilerini tuttuğum bir kağıt düzeni gibi düşünebilirsiniz.
İşleyiş olarak gelen bir ürünün rengi "beyaz" olarak işlenmiştir fakat sonrasında ise bir hata yapıp bunu mavi olarak sisteme işlediğimizi varsayalım. Peki son olarak bu ürün mavi olduğu için geriye yönelik olarak ben bu ürünün yanlış girilmeden önceki rengini nasıl bileceğim?
Diğer bir örnek ise, veritabanında bulunan bir ürünü keza yanlışlıkla tamamen sildik diyelim. Peki bu tamamen silinen ürünün bilgilerine nasıl ulaşacağım. İşte bu sorulara cevap almak için bu örneğimizi şekillendirelim.
Ürünler Tablosu
CREATE TABLE tblUrunler ( urun_ID INT PRIMARY KEY NOT NULL IDENTITY(1,1), urun_adi VARCHAR(100), urun_kodu VARCHAR(100), renk VARCHAR(10), marka VARCHAR(100), mensei VARCHAR(100), model VARCHAR(100), eklenme_tarihi DATETIME NOT NULL DEFAULT (getdate()), durum TINYINT DEFAULT 0 )tblUrunler Tablosu
Tablomuz oluştu. Şimdi bir tane daha kopya tablo oluşturalım. Onu da tblUrunler_Log olarak isimlendirelim. Fakat birkaç ayrıntı var ki o da tablomuza bir kaç tane daha sütun ekleyeceğiz. Onun nedeni ise log (kayıt altına işlemi) altına aldığımızda o işlemin ne zaman kimin tarafından yapıldığı verisini de kaydetmiş olalım.
Ürünler Log Tablosu
CREATE TABLE tblUrunler_Log ( ID INT PRIMARY KEY NOT NULL IDENTITY(1,1), urun_ID INT, urun_adi VARCHAR(100), urun_kodu VARCHAR(100), renk VARCHAR(10), marka VARCHAR(100), mensei VARCHAR(100), model VARCHAR(100), eklenme_tarihi DATETIME, durum TINYINT DEFAULT 0, log_islem VARCHAR(10), log_tarih DATETIME NOT NULL DEFAULT (getdate()), log_olusturan VARCHAR(100), log_ip VARCHAR(20) )tblUrunler_Log Tablosu
Insert Durumunda
Şimdi ise kurgumuzu oluşturalım. Mesela, tblUrunler tablosuna yapılan her insert (ekleme) işlemi için aynı kaydı tblUrunler_Log tablosuna da yazsın. Böylece kayıtların ilk değerlerini de saklamış olacağız.Ürünler Tablosunda Insert İşleminin Log Tablosuna İşlenmesi
CREATE TRIGGER trgUrunler_Insert ON tblUrunler AFTER INSERT AS BEGIN INSERT INTO tblUrunler_Log SELECT urun_ID, urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum, 'Insert', GETDATE(), CAST(SERVERPROPERTY('MachineName') AS VARCHAR(50)), CAST(CONNECTIONPROPERTY('local_net_address') AS VARCHAR(50)) FROM INSERTED ENDOluşan Trigger'ı görsel olarak paylaşalım.
trgUrunler_Insert Trigger'ı
Oluşan bu Trigger'ı test etmek için tblUrunler tablosuna birkaç veri girelim.
tblUrunler Tablosu Insert
INSERT INTO tblUrunler (urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum) VALUES ('Samsung 42 OLED TV', 'SMSNG42OLD', 'Siyah', 'Samsung', 'Güney Kore', 'SM42OL', GETDATE(), 1) INSERT INTO tblUrunler (urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum) VALUES ('LG 42 LED TV', 'LG42OLD', 'Gri', 'LG', 'Güney Kore', 'LG42LD', GETDATE(), 1) INSERT INTO tblUrunler (urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum) VALUES ('PIONEER 5 HIFI', 'PNR5HF', 'Füme', 'Pioneer', 'Japonya', 'PNR5HIFI', GETDATE(), 1) INSERT INTO tblUrunler (urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum) VALUES ('BOSCH 30 Bulaşık Makinesi', 'BSCHW30', 'Mavi', 'Bosch', 'Almanya', 'BSCH30W', GETDATE(), 1)tblUrunler Tablosuna Girilen Değerler
Bu tabloya Insert işlemi yapılırken hazırladığımız Trigger'ın diğer log tablosuna ekleme yaptığına bakalım. tblUrunler_Log Tablosuna Girilen Değerler
Update Durumunda
Şimdi ise diğer bir senaryo üzerinden ilerleyelim. Mesela varolan kayıtların herhangi bir sütunu güncellenirse onun önceki kayıtlarına erişmek için trigger hazırlayalım.tblUrunler Tablosu Update
CREATE TRIGGER trgUrunler_Update ON tblUrunler AFTER UPDATE AS BEGIN INSERT INTO tblUrunler_Log (urun_ID, urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum, log_islem, log_tarih, log_olusturan, log_ip) SELECT urun_ID, urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum, 'Update', GETDATE(), CAST(SERVERPROPERTY('MachineName') AS VARCHAR(50)), CAST(CONNECTIONPROPERTY('local_net_address') AS VARCHAR(50)) FROM deleted END
Oluşan Trigger'ı görsel olarak paylaşalım.
trgUrunler_Update Trigger'ı
Güncelleme işlemi için şöyle bir örnek üzerinden ilerleyelim. urun_ID değeri 2 olan kaydın ürün kodunu önce "LG42OLEDTV" sonra ise "LG42OLEDTV2020" olarak; sonrasında rengini önce "Kahverengi" sonra ise "Turuncu" olarak güncelleyelim.
tblUrunler Tablosu Update
UPDATE tblUrunler SET urun_kodu = 'LG42OLEDTV', renk = 'Kahverengi' WHERE urun_ID = 2 UPDATE tblUrunler SET urun_kodu = 'LG42OLEDTV2020', renk = 'Turuncu' WHERE urun_ID = 2Güncelleme işlemi yaptık peki güncelleme sonrası tblUrunler_Log tablosunda nasıl bir değişim oldu. Şimdi ise onun görselini paylaşalım.
Update Sonrası tblUrunler_Log Tablo Kayıtları
Delete Durumunda
Bu durumdaki senaryo için şöyle bir şey yapalım. urun_ID = 4 olan olan ürünü delete yapıp tblUrunler tablosundan tamamen kaldıralım.tblUrunler Tablosu Delete
CREATE TRIGGER trgUrunler_Delete on tblUrunler FOR DELETE AS INSERT INTO tblUrunler_Log (urun_ID, urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum, log_islem, log_tarih, log_olusturan, log_ip) SELECT urun_ID, urun_adi, urun_kodu, renk, marka, mensei, model, eklenme_tarihi, durum, 'Delete', GETDATE(), CAST(SERVERPROPERTY('MachineName') AS VARCHAR(50)), CAST(SERVERPROPERTY('ServerName') AS VARCHAR(50)) FROM DELETED
Oluşan Trigger'ı görsel olarak paylaşalım.
trgUrunler_Delete Trigger'ı
urun_ID = 4 olan ürün için silme işlemi gerçekleştirelim.
tblUrunler Tablosu Delete
DELETE FROM tblUrunler WHERE urun_ID = 4Sorgu sonucunda tblUrunler_Log tablosunda oluşan kaydı inceleyelim.
Delete Sonrası tblUrunler_Log Tablo Kayıtları