Forum
Merhaba arkadaşlar;
Veritabanını SQL Server'da tutan bir yazılım geliştireceğim ve şu anda ön etüdlerimi yapıyorum. Sorum kayıt kilitleme konusu ile ilgili. Yerli ve yabancı dökümanlara göz attım (transaction, isolation level, nolock, rowlock, holdlock bla bla bla) ancak tam olarak istediğim sonucu alamadım. Uygulamamda (C# Windows Application) yapmak istediğim şey şu;
1 - clientA - connA - mevcut kayıtlardan bir kayıt seçecek (SELECT * FROM t1 WITH(rowlock veya nasıl bir kilit komutu ?) WHERE id=1) ve çekilen kaydı form üzerinde ilgili alanlara bind edecek. Buraya kadar sorun yok.
2- clientB - connB - aynı formda aynı kayıt için (WHERE id=1) aynı işlemi yapamayacak. Kaydı çağırmak istediğinde kayıt x kullanıcı veya x idli connection tarafından kilitlenmiş uyarısını (exception oluşacak) verecek. Ne zamanki connA işini bitirecek (formu kapatacak veya gerekli değişiklikleri UPDATE edecek) yada bağlantısını sonlandıracak (bu durumda kilit yine serbest kalacak) connB düzenleme için kaydı alabilecek. Burada şöyle bir soru sorabilirsiniz. "connA kaydı forma aldıktan sonra formu açık unutursa o kayıt asla seçilemeyecek ve kullanıcının update yapması yada formu kapatması gerekecek", evet doğrudur aynen istediğim şey bu. UPDATE amacı ile forma çağırılan satır kilitlenecek ve kilitleyen bağlantı kapatılana kadar kilitli kalacak. Çıkan uyarıda (exception) connection id veya terminal id, ip si vs. gibi herhangi birinin bilgisini istememin sebebide diğer kullanıcılar ilgili kişiyi uyarabilsin diye.
Yardımcı olan arkadaşlara şimdiden teşekkürler...
merhaba arkadaşım. sana önerim direkt olarak bu kontrolü sqlservera brakmaman dır. çünkü lock optimizasyon sql 2008 haricinde 2005 veya 2000 lerde tam anlamıyla çileden çıkma sebebidir. normalde zaten sql aynı anda 1 tablo üzerinde 2 adet transactionı partitionlar yoksa çalıştıramaz. otomatik olarak tabloyu locklar. aynızamanda lock optimizasyonda rowlock konutu o rowu locklamanı sağlasada aslı olay lockı minimuma indirmek ve query timeoutların önüne geçmektir.
sana bir çözüm önerisinde bulunacağım.
öncelikle bu tarz işlemler için transactional spler kullanmalısın ve o tabloda o kayıt için bir flag kontrolü koy. örneğin
SELECT * FROM t1 WITH(nolock) WHERE id=1 and isopen=0 gibi. bunu da transaction blok içinde değerlendir.
begin tran
SELECT @isopen=isopen FROM t1 WITH(nolock) WHERE id=1
if @isopen=1
begin
select 'müsait değil' veya return -1
end
else
begin
update t1 set isopen=1 where id=1
--diğer işlemler
end
if şööyleyse rollback
değilse commit gibi..