PDA

View Full Version : transaction در سی شارپ



جوان ایرانی
یک شنبه 14 اسفند 1390, 10:22 صبح
سلام
من میخواهم سمت کلاینت از ترنس اکشن استفاده کنم که اون رو به صورت زیر نوشتم:
tran = con.BeginTransaction();
try
{
cm = new SqlCommand("INSERT INTO Questioner(QuestionerID) VALUES" + Convert.ToInt32(textBox5.Text),con,tran);
cm = new SqlCommand("INSERT INTO Question(QuestionerID) VALUES" + Convert.ToInt32(textBox5.Text), con, tran);
cm = new SqlCommand("INSERT INTO Question(RespondentID) VALUES" + Convert.ToInt32(textBox4.Text), con, tran);
tran.Commit();
}
catch(SqlException SqlError)
{
tran.Rollback();
}

اول می خواستم بدونم ترنس اکشن رو درست بکار بردم یانه
دوم اینکه با توجه به اینکه در هر sqlcommand دستوری متفاوت نوشتم چه طوری cm را اجرا کنم من هرکاری کردم هیچ اطلاعاتی در جداولم ذخیره نمیشد
ممنون میشم کمکم کنید

mehdi.mousavi
دوشنبه 22 اسفند 1390, 12:27 عصر
سلام.
بله، عملیات Transactional انجام میشه، اما مساله اینجاست که Command ها رو اجرا نکرده اید (ExecuteNonQuery رو روی cm ها قبل از Commit کردن اجرا کنید).
برای مشاهده نمونه کد، می تونید به این آدرس رجوع کنید (http://msdn.microsoft.com/en-us/library/2k2hy99x%28v=vs.100%29.aspx).

موفق باشید.

پاورقی: ضمنا، از Parametric Command ها استفاده کنید تا کد شما در برابر حملات SQL Injection آسیب پذیر نباشه.

Sirwan Afifi
دوشنبه 22 اسفند 1390, 12:35 عصر
ببخشید یه سوال:
این عملیات Transactional چی هست و برای چه مواردی استفاده میشه؟

mehdi.mousavi
دوشنبه 22 اسفند 1390, 12:59 عصر
ببخشید یه سوال: این عملیات Transactional چی هست و برای چه مواردی استفاده میشه؟

سلام.
فرض کنید قصد دارید N ریال (یا بقول پسرم، 20 دلار تومن :)) از حساب خودمون به حساب فرد دیگری واریز کنیم. در این انتقال وجه، ما باید بعنوان مجری تضمین کنیم که وقتی عملیات با موفقیت انجام میشه که


N ریال از حساب شما بدرستی کم بشه
N ریال به حساب دریافت کننده وجه، اضافه بشه

در واقع نباید سیستم رو در شرایطی رها کنیم که N ریال از حساب شما کم کنه، اما به حساب مقصد وجه رو واریز نکرده باشه (بدلیل قطع برق، یا هر ایراد دیگری).

عملیات Transactional عملیاتی هستش که در اون، مطمئن هستیم که State مجموعه ای از عملیات به یکی از دو وضعیت "موفق" یا "ناموفق" منجر میشه. این "جوان ایرانی"، قصد داره تا اطلاعاتی رو در سه جدول ثبت کنه. برای خودش مساله رو اینطور تعریف کرده که "یا اطلاعات در هر سه جدول بدرستی ثبت میشه، یا همه جداول دست نخورده باقی میمونه". به چنین عملیاتی، عملیات Transactional میگن که البته، فقط به ذخیره اطلاعات در بانک محدود نمیشه.


موفق باشید.

جوان ایرانی
سه شنبه 23 اسفند 1390, 00:38 صبح
آقای موسوی ممنون از راهنمایی تون
ولی بازهم هیچ اطلاعاتی ذخیره نشد

پاورقی: ضمنا، از Parametric Command ها استفاده کنید تا کد شما در برابر حملات SQL Injection آسیب پذیر نباشه
منظورتون رو از این جمله متوجه نشدم میشه کمی توضیح بدین


دلخوری از سایت:حتما باید یه نوشته فاقد محتوای فنی وناقض قوانین سایت بنویسم تایکی لطف کنه جواب بده:متعجب:

Sirwan Afifi
سه شنبه 23 اسفند 1390, 00:54 صبح
با اجازه استاد موسوی

به طور مثال قطعه کد زیر که مربوط به Login است نسبت به حملات SQL Injection (تزریق کد SQL) حساس است :

SqlConnection con = new SqlConnection("Data Source=.;Initial Catalog=University;Integrated Security=True");
SqlCommand cmd = new SqlCommand(string.Format("select *from Users where UserName=N'{0}' and Password=N'{1}'", txt_user.Text, txt_pass.Text), con);
con.Open();
SqlDataReader dr = cmd.ExecuteReader();
if (dr.HasRows)
{
new Sirwan().ShowDialog();
}
else
{
MessageBox.Show("Invalid User!");
}

و به راحتی با دادن مقدار :

' or '1'='1

به یکی از ورودی ها (UserName و یا Password) می توان از مرحله Login عبور کرد،به عبارتی کد بالا به صورت زیر برای برنامه قابل فهم می باشد :

select *from Users where UserName=' ' and Password=' ' or '1'='1'

که این شرط همیشه درست می باشد.

برای رفع این مشکل همانطور که استاد موسوی فرمودند باید از Parametric Command استفاده شود در نتیجه کد فوق را به صورت زیر تغییر می دهیم :

SqlConnection con = new SqlConnection("Data Source=.;Initial Catalog=University;Integrated Security=True");
SqlCommand cmd = new SqlCommand("select *from Users where UserName=@UserName and Password=@Password", con);
con.Open();
cmd.Parameters.AddWithValue("@UserName",txt_user.Text);
cmd.Parameters.AddWithValue("@Password",txt_pass.Text);
SqlDataReader dr = cmd.ExecuteReader();
if (dr.HasRows)
{
new Sirwan().ShowDialog();
}
else
{
MessageBox.Show("Invalid User!");
}
con.Close();