Connection (Bağlantı) Nesnesi

Veritabanı bağlantı nesnesi hakkında ayrıntılı bir yazı

ADO.NET''in programcıya sunduğu veri erişim mimarisinden .NET''te Veri Erişimi : ADO.NET başlıklı yazımızda bahsetmiştik. Belirttiğimiz gibi, ADO.NET, bağlantısız veri operasyonlarına ve verinin standart XML ifadesine tam destek veriyor.

ADO.NET''in veri kaynağıyla canlı ilişkide olan tarafını .NET Veri Sağlayıcısı oluşturuyor. Bu sağlayıcı, veri kaynağına gönderilecek her türlü komut, ve ondan dönecek her türlü yanıt için bir köprü vazifesi görüyor. Tüm bu operasyonlar için, bu sağlayıcının aktif bir bağlantısı olması gerekiyor. İşte bu bağlantı, Connection nesnesiyle temsil ediliyor. Connection nesnesi, ADO.NET''in en temel nesnesi.

Her veri sağlayıcısı, kendine özgü gerçeklenmiş bir bağlantı nesnesi sunmak durumunda. .NET ile gelen OLE DB .NET sağlayıcısının sunduğu bağlantı nesnesi OleDbConnection. SQL Server .NET veri sağlayıcısının bağlantı nesnesi ise SqlConnection. Her iki nesnenin de kullanımı genel olarak aynı. Yazımızda her iki sağlayıcı için de bağlantı örnekleri vereceğiz.

SqlConnection

Microsoft SQL Server 7.0 ve üst sürüm veritabanlarına erişmek için System.Data.SqlClient aduzayı altındaki SqlConnection nesnesini kullanıyoruz. Bu bağlantı nesnesi (daha doğrusu nesneyi sunan sağlayıcı), sadece SQL Server için tasarlandığı için başka bir veritabanı erişiminde kullanamıyoruz. SQL Server''in daha alt sürümlerine erişim içinse eskiden olduğu gibi yine OLE DB kullanılacak. Peki 7 ve üst versiyonlarında neden ayrı bir sağlayıcı kullanmamız gerekiyor? Aslında böyle bi zorunluluk yok. OLE DB hala bir seçenek. Ancak veritabanı erişimi gibi masraflı bir işte daha yüksek performans arzuluyorsak, tercihimiz SQL Server .NET veri sağlayıcısı olmalıdır. Çünkü bu sağlayıcı, SQL Server ile TDS (Tabular Data Stream) paketleri seviyesinde, yani SQL Server''in anladığı dilde haberleşiyor. Böylece OLE DB gibi bir tercümanı direk saf dışı bırakmış oluyorsunuz. .NET dokumantasyonunda bu durum şöyle çizilmiş:



Uygulamanızı hâlâ veritabanından bağımsız yapmak istiyorsanız, çok katmanlı mimariyi iyi planlamalı ve gerçeklemelisiniz. Veya ilerde konularımız arasında olacak System.Data aduzayı bünyesindeki sağlayıcılar için yazılmış arabirimlerden (IDbConnection, IDbCommand, IDataReader, ..) yararlanmak da bir çözüm olacaktır.

Şimdi SQL Server 2000 üzerindeki ünlü Northwind veritabanına bağlantı kuracağımız, bir konsol uygulaması yazalım:

SqlConnectionOrnegi.cs
// gerekli aduzaylarını bildirelim.
// SQL Provider''i System.Data.SqlClient aduzayı temsil ediyor.
using System;
using System.Data.SqlClient;

namespace Evcil.NET
{
public class CBaglanti
{
public static void Main()
{
// bağlantı cümlesini oluşturalım.
// OLEDB bağlantı cümlelerinden farklı olarak,
// Provider değeri belirtilmediğine dikkat edin
string sBaglantiCumlesi = "Server=(local); User id=sa; Password=; Database=Northwind";

// SqlConnection tipindeki bağlantı nesnemizi,
// SqlConnection sınıfının, bağlantı cümlesini parametre alan
// yapılandırıcısı (constructor) ile oluşturuyoruz.
SqlConnection oConn = new SqlConnection(sBaglantiCumlesi);

// bağlantımızın kurulması
oConn.Open();
Console.WriteLine("Northwind ile baglanti kuruldu");

// .... burda Northwind üzerinde
// istediğiniz operasyonları yaptığınızı varsayalım.

// işimiz bitince bağlantıyı "kesinlikle" kapatmalıyız.
oConn.Close();
Console.WriteLine("Northwind ile baglanti kesildi");
}
}
}

Neler yaptığımıza biraz daha yakından bakalım. Başlangıçta, konsola yazı yazmak için gereken Console sınıfının bulunduğu System aduzayını ve SqlConnection sınıfının bulunduğu System.Data.SqlClient aduzayını kullanacağımızı derleyiciye using ayrılmış kelimesiyle bildirdik. Bu bildirimi yapmasak da olur; ama o zaman bahsedilen sınıfları, her seferinde aduzayı ile birlikte (Fully-Qualified) yazmak zorunda kalırız: System.Data.SqlClient.SqlConnection . Hangisi kolayınıza(!) geliyor?

Kendimize has bir aduzayı ve sınıf tanımı yaptıktan sonra, bağlantı denememizi, bağımsız (stand-alone) uygulamamızın giriş noktası (entry point) olacak Main() rutinimizde yazacağız. Burda "Bağlantı Cümlesi" diye bir kavram görüyoruz. Bağlantı cümlesi, OLE DB''den gelen bi kavramdır. Bir OLE DB sağlayıcısı üzerinden bir veritabanına erişimle ilgili her türlü detay, daha genel bir ifadeyle bir "bağlantı" ile ilgili her detay bağlantı cümlesinde ifade edilir. Bu cümle anahtar/değer çiftlerinin (;) noktalı virgül ile birleştirilmiş halidir. İşte örnek bir bağlantı cümlesi:

Provider=SQLOLEDB.1;Integrated Security=SSPI;Persist Security Info=False;Initial Catalog=Northwind;Data Source=127.0.0.1

Siz de kolayca bir OLE DB bağlantı cümlesi oluşturmak isterseniz boş bir metin dosyasının uzantısını .udl yapın. Dosyanın simgesinin değiştiğini göreceksiniz. Dosyayı çift tıkladığınızda, "Data Link Properties" başlıklı sihirbaza benzer bir Windows uygulaması açılacak. Burdaki seçenekleri kullanarak geçerli bir bağlantı cümlesi oluşturursanız önünüze bir seçenek daha çıkar: OLEDB bağlantısında, parametre olarak bağlantı cümlesi yerine bu dosyanın yolunu verebilirsiniz. Böylece bağlantı detayınızı harici bir dosyada saklamış olursunuz. Ne kadar faydalı olduğu tartışmalıdır.

Şimdi, SqlConnection nesnesi için bağlantı cümlesi oluştururken dikkat etmemiz gereken bir nokta var, ondan bahsedelim. Yukarıda verdiğim bağlantı cümlesi örneği OLE DB içindi. OLE DB bağlantı cümlelerinde Provider anahtarı ile sağlayıcı seçimi yapmamız gerekiyor. Eğer yapmazsak varsayılan sağlayıcı olan "OLE DB Provider for ODBC Drivers" i seçmiş oluyoruz. Bu tür bir seçim yapmamızın nedeni OLE DB API katmanının birbirinden çok farklı veri kaynaklarına erişimi mümkün kılması. Bunun için de, bizden bağlanacağımız veri kaynağına uygun bir Provider (sağlayıcı) seçmemizi bekliyor. Ancak SqlConnection ile kuracağımız bir bağlantı için oluşturacağımız cümlede Provider anahtarını kullanmıyoruz. Çünkü sadece SQL Server''e bağlanacağız ve bir "Provider" seçimi yapma hakkımız yok.

Bağlantı cümlesinde anahtarların sırası önemli değildir. Geleneksel olsun diye ilk önce Server anahtarına bir değer atadık. ( Server yerine Data Source anahtarı da kullanılabilir.) Yerel SQL Server''e bağlanacaksak anahtara "(local)" (veya "localhost", "127.0.0.1", ..) değerini veriyoruz. Buraya uzaktaki bir SQL Server''in IP adresini de yazabiliriz. Daha sonra SQL Server Login bilgilerimizi belirtiyoruz. SQL Server''a iki türlü login olabiliriz. Birincisi SQL Server Doğrulaması ile. İnternet uygulamaları için en uygun olanı budur. Bu tür girişte bir kullanıcı adı ve parola belirtiriz. İkincisi ise Bütünleşik Windows Doğrulaması''dır. Bu seçenekte ise, SQL Server Windows''a giriş yaptığımız login bilgisine göre doğrulama yapar. Bağlantı cümlesinde entegre Windows doğrulamasını kullanmak istersek user id ve password anahtarları yerine "Integrated Security = SSPI; " anahtar/değer çiftini belirtmeliyiz. (veya "Trusted Connection = True;")

Sonra SQL Server üzerindeki veritabanlarından birini seçmek istiyoruz. Bunun için de Database (veya Initial Catalog) anahtarını kullanıyoruz. Böylelikle bağlantı ile ilgili detayları verdiğimiz bir cümleyi oluşturmuş olduk. Bunu bir string değişkene atadık. SqlConnection tipinde deklare ettiğimiz referansı ( oConn), SqlConnection''un bağlantı cümlesini parametre alan yapılandırıcısı ile yarattığımız nesneye bağladık. Bağlantı cümlesini, nesneye daha sonra da atayabilirdik ama kolaylık olsun diye, daha yapılandırıcıda iken bu işi hallettik.

Bir bağlantı cümlesinde kullanılabilecek anahtarlar ve alabilecekleri değerler ile ilgili ayrıntılı açıklamayı lokal .NET Framework SDK dokumantasyonunda veya burada bulabilirsiniz.


Bağlantı nesnemizi oluşturduk. Hafızada (heap''te) bu nesne için bir yer ayrıldı. Ancak tüm bunlar, "bağlantı cümlesinde" bahsini geçtiğimiz SQL Server veritabanı ile fiziksel bir bağlantı kurmuş olduğumuz anlamına gelmiyor. Şimdilik sadece niyetlendik. Bu bağlantının kurulması için bağlantı nesnemizin Open() metodunu işletiyoruz. Eğer hiç bir problem yoksa, bağlantınız kurulacak ve bağlantı nesnemizin State (vaziyet) özelliği ConnectionState.Open (açık) duruma gelecektir. Artık veri kaynağı ile oConn nesnesi üzerinden canlı bir bağlantımız vardır ve sağlayıcının diğer nesneleri ile (SqlCommand, SqlDataReader, SqlDataAdapter) bu canlı bağlantı üzerinden istediğimiz manipulasyon operasyonlarını gerçekleştirebiliriz.

Bu yazımızda sadece bağlantı nesnesi üzerinde odaklanmak istediğimiz için, hiç bir işlem yapmadan bağlantımızı kapatacağız. Bu iş için de parametresiz basit bir metodumuz var: Close(). Veritabanı bağlantısı masraflı (yani sistem için zahmetli) bir iş olduğundan, işimizi en kısa sürede halledip bekletmeden, aktif bağlantıyı kapatmayı unutmamalıyız. Eğer bunu unutursak, bağlantımız belli bir zaman aşımı süresi kadar açık kalacaktır.

Örnek uygulamayı aşağıdaki komutu kullanarak derleyebilirsiniz.

C:>csc /r:System.dll,System.Data.dll SqlConnectionOrnegi.cs

Ve uygulamayı çalıştıralım:



Görüldüğü gibi bir SQL Server veritabanına bağlantıyı kolayca kurabiliyoruz. Burada belki de üzerinde durulması yerinde olacak bir konu var: Bağlantı cümlesinin yeri. Yazdığımız örnekte bağlantı cümlesini hiç bir kaygı duymadan kodumuzun içine gömdük. Bağlantı cümlesinde yapılacak bir değişiklik için (örneğin SQL Server''in adresinin değişmesi durumunda) uygulamayı yeniden derleme ihtiyacı doğacağı açıktır. Bağlantı cümlesini uygulamadan ayrı bir noktada tutmak hem merkezi bir yönetim hem de esneklik sağlayacak. Elbette bunun düz metin dosyası olması, bir güvenlik sıkıntısı da doğuracak. Ancak ASP.NET uygulamalarının yapılandırma dosyaları web.config, bu tür kayıtlar için çok ideal bir yer. Çünkü bu yapılandırma dosyaları düz yazı dosyaları olmalarına rağmen ASP.NET motoru tarafından ziyaretçilere sunulmuyor. Tıpkı .ascx uzantılı dosyalar gibi. Bağlantı cümlesinin ulaşılabilir olması, dosya özellikle SQL Server login bilgisi içeriyorsa çok riskli olacaktır.

OleDbConnection

OleDbConnection nesnesi, System.Data.OleDb aduzayına bağlı, OLE DB .NET veri sağlayıcısı üzerinden bir veri kaynağına bağlantı tesis etmemizi sağlar. Kullanımı aynen yukarıda bahsettiğimiz SqlConnection nesnesi gibidir. O nedenle aynı şeyleri tekrar etmeyeceğiz. Yalnız bu tip bağlantıda, bağlantı cümlesini oluştururken, hedef veri kaynağına uygun bir Provider seçmemiz gerekecektir. OLE DB veri sağlayıcısını kullanarak, sistemde OLE DB sağlayıcısı bulunan her veri kaynağına (SQL Server, Oracle, Access, Indexing Service) bağlanabiliriz. Biz bir Access veritabanına bağlantı örneği verelim:

OleDbConnection.cs
using System;
using System.Data.OleDb;

namespace Evcil.NET
{
public class COleDb
{
public static void Main()
{
string sBagCumle = @"Provider=Microsoft.Jet.OLEDB.4.0; Data Source=C:data.mdb ";
OleDbConnection oConn = new OleDbConnection(sBagCumle);
try
{
oConn.Open();
}
catch ( OleDbException e )
{
Console.WriteLine( e.Message );
}
finally
{
oConn.Close();
}
}
}
}

Yaptığımız her şeyin SqlConnection''la birebir aynı olduğunu görüyorsunuz. Namespace olarak System.Data.OleDb kullandığımıza dikkat edin. Bir kaç nokta daha var. Bağlantı cümlesinde bir Access veritabanının fiziksel yolunu belirtiyoruz. Peki string ifadenin önündeki " @" simgesi de ne işe yarıyor? Biliyorsunuz ki, C''de " " (escape) karakterinin kendinden sonra gelen ilk karakterle beraber özel görevleri var. Bir fiziksel yol yazarken normal " " karakterini doğru olarak ifade etmek için iki adet " " yazmamız gerekecekti: " C:\Data.mdb". İşte string ifadenin önündeki " @" karakteri, o stringdeki tüm " " karakterlerini ayrıcalıklı olmaktan çıkarıyor. Bir kolaylık olarak sunulmuş bize.

Kodda, bağlantıda herhangi bir istisna çıktığı durumda, istisnanın yakalanması ve her hâlukarda bağlantının kapatılması için try/catch/finally yapısının kullanımını da örneklemiş olduk.

Bitirirken...

Bu yazıda, veri kaynağı ile sağlayıcı üzerinden nasıl ilişki kurabileceğimizi gördük. Bu veri tabanı operasyonları için ilk adımdı. Bundan sonra atacağımız tüm adımlar, kurduğumuz bu ilişki üzerinden yürüyecek.

İyi çalışmalar.

, ,

Arşivden

Yorum bulunmuyor.

Yorum yazabilirsiniz


* [b], [i] ve [quote] serbest