PDA

View Full Version : سوال: مدیریت صحیح تراکنش ها در سیستم های تحت شبکه



csharpcollegian
شنبه 28 اسفند 1395, 23:39 عصر
سلام دوستان وقتتون به خیر
سال نو رو پیشاپیش تبریک عرض می کنم خدمتتون
دوستان من میخوام زمانی که کابر در سیستم روی دکمه ویرایش کالا کلیک می کنه، جدول مربوط به کالاها یا حداقل رکورد مربوط به کالای انتخاب شده به حالت انتظار بره و کاربرای دیگه سیستم در این فاصله زمانی که کاربر اول مشغول ویرایش اطلاعاته، تنونن اطلاعات اون رکورد رو تغییر بدن تا سیستم درست کار کنه. واسه پیاده سازی این مساله باید چی کار کنم ؟
آیا راه حل اصولی کنترل تراکنش ها در سیستم های تحت شبکه همینه ؟
باید از Transaction ها استفاده کنم یا راه حل دیگه ای داره ؟
ممنون میشم اگه یه سمپل کوچیک هم قرار بدید
متشکرم

alireza_s_84
یک شنبه 29 اسفند 1395, 00:33 صبح
سلام دوستان وقتتون به خیر
سال نو رو پیشاپیش تبریک عرض می کنم خدمتتون
دوستان من میخوام زمانی که کابر در سیستم روی دکمه ویرایش کالا کلیک می کنه، جدول مربوط به کالاها یا حداقل رکورد مربوط به کالای انتخاب شده به حالت انتظار بره و کاربرای دیگه سیستم در این فاصله زمانی که کاربر اول مشغول ویرایش اطلاعاته، تنونن اطلاعات اون رکورد رو تغییر بدن تا سیستم درست کار کنه. واسه پیاده سازی این مساله باید چی کار کنم ؟
آیا راه حل اصولی کنترل تراکنش ها در سیستم های تحت شبکه همینه ؟
باید از Transaction ها استفاده کنم یا راه حل دیگه ای داره ؟
ممنون میشم اگه یه سمپل کوچیک هم قرار بدید
متشکرم
برای اینکار نیازی به مدیریت تراکنش ها ندارین بلکه باید از RowVersion برای اینکار استفاده کنید.
https://msdn.microsoft.com/en-us/library/ms182776.aspx

csharpcollegian
دوشنبه 30 اسفند 1395, 01:25 صبح
برای اینکار نیازی به مدیریت تراکنش ها ندارین بلکه باید از RowVersion برای اینکار استفاده کنید.
https://msdn.microsoft.com/en-us/library/ms182776.aspx


جناب alireza_s_84 بابت پاسختون ممنونم
در رابطه با RowVersion و کاربرد اون در کنترل تداخلات همروندی جستجو کردم و نتایج مورد نیازم رو پیدا کردم. برای تست این مساله یه پروژه ایجاد کردم و با مشکل زیر روبه رو شدم که البته ربطی به RowVersion نداره و مربوط به Entity Framework هستش که ممنون میشم اگر راهنماییم کنید.
مطابق عکس رو به رو یه جدول ایجاد کردم و یک ستون از نوع RowVersion براش در نظر گرفتم :


144720


بعد به وسیله Entity Framework مدل داده ای دیتابیسم رو وارد پروژه کردم. همونطور که توو عکس زیر میبینید در دو خط متوالی اطلاعات یک رکورد خاص رو از دیتابیس خوندم، اما بینشون از یک BreakPoint استفاده کردم. به این صورت که وقتی در خط کد Person1 اطلاعات رکورد اول جدول Person خونده میشه، برنامه در خط بعدی متوقف میشه. زمانی که برنامه متوقف شده در SQL Server اون رکورد خونده شده رو آپدیت کردم تا محتویات ستون RowVersionColumn تغییر بکنه که این اتفاق هم می افته. اما وقتی توو ویژوال استودیو برنامه رو ادامه میدم باز هم همون اطلاعات قبلی خونده میشه در صورتی که باید در خط کد Person2 اطلاعات جدیدی که در رکورد بروز شدن خونده بشه !



144721


144722


مشکل از کجاست ؟ چرا در خط کد Person2 محتویات جدید رکورد خونده نمیشه و همون اطلاعات قبلی از دیتابیس برگردونده میشه ؟
البته زمانی که خط کد Person2 رو در یک using جداگانه از TestDBEntities نوشتم مشکل برطرف شد، اما خب سوالم اینجاست که به هر دلیلی اگر قرار نیست در خط کد Person2 اطلاعات جدید برگردونده بشه پس باید در شرایط عکس زیر هم خط کد Person2 مقدار رکورد رو به خودش بگیره، اما null میشه ! انگار توو این حالت خط کد Person2 متوجه تغییر RowVersionColumn میشه !!!


144723



ببخشید که سوالم خیلی طولانی شد
لطف می کنید اگر مجددا راهنماییم کنید

alireza_s_84
دوشنبه 30 اسفند 1395, 09:07 صبح
وقتی شما از EF برای ویرایش استفاده میکنید زمانی که موجودیت واکشی شد در حافظه کش میشه و تغییر اطلاعات در پایگاه داده تاثیری روی اون نداره. برای مدیریت همزمانی در EF باید پراپرتی مربوطه در مدل رو با Attribute امضا کنید:
[Timestamp]
public byte[] RowVersion { get; set; }
اطلاعات بیشتر:
https://docs.microsoft.com/en-us/aspnet/mvc/overview/getting-started/getting-started-with-ef-using-mvc/handling-concurrency-with-the-entity-framework-in-an-asp-net-mvc-application

csharpcollegian
پنج شنبه 03 فروردین 1396, 04:14 صبح
وقتی شما از EF برای ویرایش استفاده میکنید زمانی که موجودیت واکشی شد در حافظه کش میشه و تغییر اطلاعات در پایگاه داده تاثیری روی اون نداره. برای مدیریت همزمانی در EF باید پراپرتی مربوطه در مدل رو با Attribute امضا کنید:
[Timestamp]
public byte[] RowVersion { get; set; }
اطلاعات بیشتر:
https://docs.microsoft.com/en-us/aspnet/mvc/overview/getting-started/getting-started-with-ef-using-mvc/handling-concurrency-with-the-entity-framework-in-an-asp-net-mvc-application

عرض سلام مجدد جناب alireza_s_84 عزیز
من تمام کارهایی که فرموده بودید رو انجام دادم و موضوع رو تست و نتیجه مثبت گرفتم. اما وقتی تصمیم گرفتم داخل پروژه اصلی پیاده سازیش کنم به یک مشکل عجیب برخوردم !
در پروژه اصلی زمانی که کاربر از دیتاگرید کالای مورد نظرش رو انتخاب می کنه، اطلاعات کالای انتخاب شده رو به کمک کد زیر برای فرم ویرایش ارسال می کنم :

144727


البته آبجکتی که به فرم ویرایش ارسال می کنم دقیقا خوده Product (کالا) نیست بلکه آبجکت View ساخته شده از کالا (VwProduct) هست. بعد هم در فرم ویرایش زمانی که کاربر روی دکمه ثبت کلیک می کنه، مجددا یک بار دیگه اطلاعات آبجکت Product رو از دیتابیس می خونم و فیلد RowVersion اون رو با فیلد RowVersion آبجکتی که به فرم ارسال شده بود مقایسه می کنم تا متوجه تغییرات در فیلد مربوطه بشم.
اما مشکل اینجاست که حتی زمانی که هیچ ویرایشی صورت نمی گیره و فیلد RowVersion ثابته، باز هم برنامه RowVersion آبجکت ارسالی رو با RowVersion آبجکت خونده شده از دیتابیس برابر نمی دونه در صورتی که که وقتی با یک BreakPoint برنامه رو بررسی کردم متوجه شدم که مقدار RowVersion ها با هم کاملا برابره ! ولی if اون ها رو نابرابر تشخیص میده :
عکس مقدار آبجکت خونده شده از دیتابیس :



144728

عکس مقدار آبجکت ارسال شده به فرم :

144729



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

csharpcollegian
پنج شنبه 03 فروردین 1396, 21:24 عصر
مشکل از اینجا بود که باید پراپرتی RowVersion رو قبل از مقایسه Convert می کردم تا if درست عمل کنه.
با تشکر از جناب alireza_s_84