Makale Özeti

Kayıt işlemi gerçekleştirdiğiniz bir sayfa var; bir komutta önce ana tabloya kayıt sonra dönen Id değeri ile ana tabloya bağlı alt tablolara birden fazla kayıt yaptırıyorsunuz. Bu örnek sanırım her yazılım geliştiricinin hemen hemen karşılaştığı bir durum. Peki, bu işlemleri nasıl yapıyorsunuz; iki stored procedure kullanarak mı? Eğer evetse bu makaleyi okumanızı öneririm.

Makale

Stored Procedure DataSet Gönderme
Kayıt işlemi gerçekleştirdiğiniz bir sayfa var; bir komutta önce ana tabloya kayıt sonra dönen Id değeri ile ana tabloya bağlı alt tablolara birden fazla kayıt yaptırıyorsunuz. Bu örnek sanırım her yazılım geliştiricinin hemen hemen karşılaştığı bir durum. Peki, bu işlemleri nasıl yapıyorsunuz; iki stored procedure kullanarak mı? Eğer evetse bu makaleyi okumanızı öneririm.
Bu makalede, bir biri ile bire çok ilişkili iki tabloya tek bir stored procedure ile kayıt işlemini gerçekleştireceğiz. Internetten sipariş verilen basit bir uygulama yapacağız.
Uygulamamızda ana tablomuz tbl_Siparis bu tabloya sadece tek bir kayıt gönderilebilir. Ana tabloya bağlı olan tbl_SiparisAlt tablosu, bir ya da birden çok kayıt gönderilebilir.
Sayfa tasarımı aşağıdaki gibidir;
Page Source için Tıklayınız
Siparişe Ürün ekle düğmesine tıklanıldığında alttaki ürün kayıt penceresi açılmaktadır. Böylece kullanıcı bir siparişe birden fazla ürün ekleyebilir.
Siparişe eklenen ürünleri veritabanından önce (siparisId bilmiyoruz ve henüz sipariş kesin değil) datasete aktarmak için sayfa açılışına dataset üreten prosedürü yazmamız gerekiyor. Burada dikkat edilmesi gereken nokta datasetin içerisinde oluşturulacak her alanın string olmasıdır. Çünkü stored prosedure oluşturduğumuz dataseti gönderirken string dönüşümü yapılacaktır. Ayrıca dataset içerisinde oluşturulan tabloya mutlaka bir ad verilmelidir.

    Sub DatasetOlustur()

        Me.ViewState("dtUrunler") = Nothing

        Dim dtUrunler As New DataTable

        dtUrunler.TableName = "siparisAlt"

        dtUrunler.Columns.Add(New DataColumn("Urun", GetType(String)))

        dtUrunler.Columns.Add(New DataColumn("Adet", GetType(String)))

        Me.ViewState("dtUrunler") = dtUrunler

    End Sub

Ürün Ekle düğmesine tıklanıldığında ürün kayıt penceresindeki bilgileri datasete aktarmak için aşağıdaki kod satırını kullanıyoruz.

    Protected Sub btnUrunEkle_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnUrunEkle.Click

        Try

            Dim dt As DataTable = Me.ViewState("dtUrunler")

            Dim dr As DataRow

            dr = dt.NewRow

            dr("Urun") = txtUrun.Text

            dr("Adet") = txtAdet.Text

            dt.Rows.Add(dr)

            Me.ViewState("dtUrunler") = dt

            pnlUrunEkle.Visible = False

            grdUrunler.DataSource = dt

            grdUrunler.DataBind()

        Catch ex As Exception

            lblHata.Visible = True

            lblHata.Text = "HATA : " & ex.Message

        End Try

    End Sub

Stored procedure atayacağımız dataseti tamamladıktan sonra, stored procedure yazımını yapabiliriz. Stored procedurede istenen parametre değerlerine bakarsanız alt tablo kaydı için xml veri türünde bir değer istenmekte. Kod sayfasında oluşturduğumuz dataseti xml türündeki parametreye atayacağız.
Öncelikle  ana tabloya kayıt yapıyor ve oluşan SiparisId (Identity) değerini okuyoruz. Böylelikle alt tabloya atayacağımız ilişkili Idyi elde ediyoruz. Xml ’in içerisindeki (kod sayfasında datatable verdiğimiz ad) her bir değeri okuyarak template tablosuna kayıt ediyoruz. Burada dikkat edersiniz ki; string olarak yarattığımız datasetin içerisindeki alanları, kendi türlerine dönüştürebiliyoruz. Ve template dosyasına node ‘un içerisindeki alanlar dışında da yeni üretilen Id değerini atayabiliyoruz. Son olarak da template tablosundaki kayıtları SiparisAlt tablosuna kayıt ediyoruz.
Bu işlemin bir diğer özelliği de, tüm kayıt kodları aynı begin tran da olduğu için commit ve rollback işlemleri çok daha basit gerçekleştirilir.

CREATE PROCEDURE [dbo].[proc_SiparisKayit]

@SiparisAdresi nvarchar(Max),

@SiparisTel nvarchar(50),

@siparisAlt xml

AS

BEGIN

 

Begin Tran

 

INSERT INTO tbl_Siparis

                      (SiparisAdresi, SiparisTel, SiparisTarihi)

VALUES     (@SiparisAdresi,@SiparisTel, GETDATE())

 

Declare @SiparisId int

Select @SiparisId = @@Identity

 

 

SELECT

      Cast(convert(varchar(36), @SiparisId ) as integer )   as SiparisId,

      Cast(colx.query('data(Urun) ') as varchar) as Urun,

      Cast(convert(varchar(36), colx.query('data(Adet) ') ) as integer ) as Adet

INTo #TMP FROM @siparisAlt.nodes('DocumentElement/siparisAlt') AS Tabx(Colx)

 

INSERT INTO tbl_SiparisAlt

 (SiparisId, Urun, Adet)

SELECT * FROM #TMP

 

 

if @@error = 0

      Commit Tran

Else

      Rollback Tran

 

END

Siparişi Kapat düğmesine tıklanıldığında, datatable içersindeki verileri, string veri türündeki siparisAltTablosu adındaki değişkene WriteXml metodunu kullanarak aktarıyoruz. Veritabanı ve stored procedure bağlantılarını yaptıktan sonra prosedurun xml veri türündeki parametresine, siparisAltTablosu değişkenini atıyoruz.

Protected Sub btnSiparisiKapat_Click(ByVal sender As Object, ByVal e As EventArgs) Handles btnSiparisiKapat.Click

        Try

            Dim connSTR As String = "data source=.;initial Catalog=Siparis;uId=sa;pwd=1234"

            Dim dt As DataTable = Me.ViewState("dtUrunler")

            Dim siparisAltTablosu As String

 

            Using sw As New StringWriter()

                dt.WriteXml(sw)

                siparisAltTablosu = sw.ToString()

            End Using

 

            Using conn As New SqlConnection(connSTR)

                conn.Open()

                Dim cmd As New SqlCommand()

                cmd.Connection = conn

                cmd.CommandType = CommandType.StoredProcedure

                cmd.CommandText = "proc_SiparisKayit"

 

                Dim param0 As New SqlParameter("@SiparisAdresi", SqlDbType.NVarChar)

                param0.Value = txtAdres.Text

                cmd.Parameters.Add(param0)

 

                Dim param1 As New SqlParameter("@SiparisTel", SqlDbType.NVarChar)

                param1.Value = txtTel.Text

                cmd.Parameters.Add(param1)

 

                Dim param As New SqlParameter("@siparisAlt", SqlDbType.Xml)

                param.Value = siparisAltTablosu

                cmd.Parameters.Add(param)

                cmd.ExecuteNonQuery()

            End Using

 

        Catch ex As Exception

            lblHata.Visible = True

            lblHata.Text = "HATA : " & ex.Message

        End Try

Konuyu özetlemek gerekirse; diğer kayıt işlemlerinden farklı olarak stored procedurede xml veri türünde bir parametre tanımladık. Stored procedure içerisinde xml node özelliğini kullanarak datatable içerisindeki alanları okuduk. Ve parametreye değer atamak için, datatable ‘ın içeriğini xml olarak yazdırdık. Bu üç farkın yazılımlarınızda yararlı olması dileğiyle…

Code Source için Tıklayınız
Yorumlarınız/sorularınız için incilay.cilesizoglu@msn.com adresine mail gönderebilirsiniz.