• 0
السيد الهاشمي

سوال عن ترايقر في sql server

سؤال

السلام عليكم ورحمة الله وبركاته

عندي مشكلة في ترايقر .. اريد ان انشى تريقر .. خاص بجدول الاستعار عمل هذه الترايقر .. انه يقوم بالبحث عن الكتاب هل هو مستعار ام لا .. في حال انه مستعار يقوم بالغاء عملية الانسرت .. ويخبر اللمستخدم ان هذه الكتاب تم استعارته

قمة بنشاء هذه الترايقر ولكن لا اعلم ما هي المشكلة .. لاني اول مرة استخدم ترايقر .. وياليت الي عندة خبرة بالترايقر يوضح لي ايش الخطاء ويعدل على الترايقر .. ولكم جزيل الشكر والتدقير


ALTER TRIGGER insrt_book
on ast
for insert as
DECLARE @id_book int
DECLARE @b_flag int
if @[email protected]_book and @b_flag=1
begin

print('sorry u cant give thies book')
rollback transaction

end

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

14 إجابة على هذا السؤال .

  • 0

السلام عليكم...

alter TRIGGER insrt_book 
on ast
for insert as
DECLARE @id_book int
DECLARE @b_flag int
set @b_flag = 0
select @id_book=id_book from inserted
select @b_flag = b_flag from ast
where id_book = @id_book

if @b_flag = 1
begin
raiseerror ('sorry u cant give this book')
rollback transaction
end

inserted هو جدول وهمي يحوي السجلات المراد اضافتها

على نفس المبدأ هناك جدول وهمي اسمه deleted يحوي السجلات المراد حذفها

أما في حال تعديل سجل ما فيمكنك الوصول إلى القيم في هذا السجل باستخدام الجدولين الوهميين السابقين معا، حيث:

deleted هو السجل المراد تعديله و فيه الحقيم قبل التعديل

inserted هو الجدول الذي يجوي السجل المراد تعديله و فيه القيم الجديدة

أي كأننا نتعامل مع التعديل على أنه حذف للسجل و إعادة إضافته بالقيم الجديدة

ملاحظة: كل من الجدولين الوهميين: (inserted, deleted) يمكن أن يحوي أكثر من سجل و يمكن التعامل معهما كما نتعامل مع الجداول الحقيقية

و الله أعلم

تم تعديل بواسطه byte101
1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم...

alter TRIGGER insrt_book 
on ast
for insert as
DECLARE @id_book int
DECLARE @b_flag int
set @b_flag = 0
select @id_book=id_book from inserted
select @b_flag = b_flag from ast
where id_book = @id_book

if @b_flag = 1
begin
raiseerror ('sorry u cant give this book')
rollback transaction
end

inserted هو جدول وهمي يحوي السجلات المراد اضافتها

على نفس المبدأ هناك جدول وهمي اسمه deleted يحوي السجلات المراد حذفها

أما في حال تعديل سجل ما فيمكنك الوصول إلى القيم في هذا السجل باستخدام الجدولين الوهميين السابقين معا، حيث:

deleted هو السجل المراد تعديله و فيه الحقيم قبل التعديل

inserted هو الجدول الذي يجوي السجل المراد تعديله و فيه القيم الجديدة

أي كأننا نتعامل مع التعديل على أنه حذف للسجل و إعادة إضافته بالقيم الجديدة

ملاحظة: كل من الجدولين الوهميين: (inserted, deleted) يمكن أن يحوي أكثر من سجل و يمكن التعامل معهما كما نتعامل مع الجداول الحقيقية

و الله أعلم

-------------------------------------

مشكور اخي العزيز على ردك لي بس اخي جربت الي كتبته لي وطلع لي هذه الخطاء


The requested operation requires a SqlClr context, which is only available when running in the Sql Server process.

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

هل هذا الخطأ يظهر عندمحاولة انشاء الـ trigger أم عند التنفيذ؟

هل تستخدم sql server express أم غيره (enterprise مثلا)

ما هو اصدار ال visual studioالذي تستخدمه

1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

هل هذا الخطأ يظهر عندمحاولة انشاء الـ trigger أم عند التنفيذ؟

هل تستخدم sql server express أم غيره (enterprise مثلا)

ما هو اصدار ال visual studioالذي تستخدمه

=================

اخي العزيز .. التريقر اشتغل بنجاح بس لا يحقق المطلوب منه .. انا اريدة .. لو اول مرة عملت استعارة للكتاب يسوي استعارة بنجاح .. ويخلي قيمة b_flag=1 بس لو جيت مرة ثانية اسوي استعارة لنفس للكتاب .. المفروض يرفض ويطلع لي رسالة انه هذه الكتاب تم استعارته .

واريدة كمان يتحقق .. من count حق الكتاب .. اذا كان صفر لايقبل الاستعارة .. ام لو كان اكبر من الصفر يسوي استعارة .. وثاني شي اخي العزيز.. لا اريدة ان يطلع لي ارر مثل هذه

-------------------------------

The transaction ended in the trigger. The batch has been aborted.

sorry u cant give thies book

----------------------------------------------------------

اريدة ان يطلع لي رسالة خطاء من غير ما يخرج من الصفحة .. لكن هنا يطلع لي خطاء في الصفحة .. اتمنا اني اكون اوصلت الفكرة لك

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

The requested operation requires a SqlClr context, which is only available when running in the Sql Server process.

اخي العزيز .. التريقر اشتغل بنجاح بس لا يحقق المطلوب منه

هل هذا يعني أن الرسالة السابقة لم تعد تظهر؟

انا اريدة .. لو اول مرة عملت استعارة للكتاب يسوي استعارة بنجاح .. ويخلي قيمة b_flag=1 بس لو جيت مرة ثانية اسوي استعارة لنفس للكتاب .. المفروض يرفض ويطلع لي رسالة انه هذه الكتاب تم استعارته .

بالنسبة للكود لا يوجد فرق بين أول مرة و غيرها

واريدة كمان يتحقق .. من count حق الكتاب .. اذا كان صفر لايقبل الاستعارة .. ام لو كان اكبر من الصفر يسوي استعارة .. وثاني شي اخي العزيز.. لا اريدة ان يطلع لي ارر مثل هذه

لم تذكر موضوع عدد الكتب سابقا...

أحتاج إلى بعض التوضيح لأتمكن من مساعدتك..

ماذا يمثل الجدول الذي بحاول أن نضيف سجلات له؟ ما هي الأعمدة التي يحويها؟

أقترح عليك البنية التالية:

جدول اسمه books فيه الأعمدة التالية:

Id, Name, ....., TotalCount, availableCount

عندما تريد أن تعرف كتاب جديد (أي أحضرت كتاب جديد إلى المكتبة) عندها تقوم بعملية insert على هذا الجدول

أما في حالة أردت إعارة الكتاب فأنت تحتاج إلى عمل update على هذا الجدول و ليس insert

و من الأفضل أن يكون هناك جدول آخر اسمهالإعارات مثلا فيه الأعمدة التالية:

Id, clustomerId, bookId, lendingDate, LendingDuration

بالإضافة غلى جدول customers الذي سيرتبط معه العمود customerId من جدول الإعارات

أرجو توضيح بنية قاعدة البيانات التي تعتمدها (الجداول و الأعمدة في كل منها) حتى أتمكن من مساعدتك

متى تظهر رسالة الخطأ هذه؟

اريدة ان يطلع لي رسالة خطاء من غير ما يخرج من الصفحة .. لكن هنا يطلع لي خطاء في الصفحة .. اتمنا اني اكون اوصلت الفكرة لك

السؤال في البداية كان سؤال قواعد بيانات، صراحة أنا لست خبيرا ببرمجة الويب

في برمجة الويندوز، من الأفضل أن تجعل قاعدة البيانات تعيد خطأ باستخدام raiseerror ثم تتعامل معه من خلال try...catch

و لكن لدي اقتراح، لماذا لا تتأكد من توافر الكتاب قبل أن تمكّن المستخدم من اختياره؟

1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

هل هذا يعني أن الرسالة السابقة لم تعد تظهر؟

بالنسبة للكود لا يوجد فرق بين أول مرة و غيرها

لم تذكر موضوع عدد الكتب سابقا...

أحتاج إلى بعض التوضيح لأتمكن من مساعدتك..

ماذا يمثل الجدول الذي بحاول أن نضيف سجلات له؟ ما هي الأعمدة التي يحويها؟

أقترح عليك البنية التالية:

جدول اسمه books فيه الأعمدة التالية:

Id, Name, ....., TotalCount, availableCount

عندما تريد أن تعرف كتاب جديد (أي أحضرت كتاب جديد إلى المكتبة) عندها تقوم بعملية insert على هذا الجدول

أما في حالة أردت إعارة الكتاب فأنت تحتاج إلى عمل update على هذا الجدول و ليس insert

و من الأفضل أن يكون هناك جدول آخر اسمهالإعارات مثلا فيه الأعمدة التالية:

Id, clustomerId, bookId, lendingDate, LendingDuration

بالإضافة غلى جدول customers الذي سيرتبط معه العمود customerId من جدول الإعارات

أرجو توضيح بنية قاعدة البيانات التي تعتمدها (الجداول و الأعمدة في كل منها) حتى أتمكن من مساعدتك

متى تظهر رسالة الخطأ هذه؟

السؤال في البداية كان سؤال قواعد بيانات، صراحة أنا لست خبيرا ببرمجة الويب

في برمجة الويندوز، من الأفضل أن تجعل قاعدة البيانات تعيد خطأ باستخدام raiseerror ثم تتعامل معه من خلال try...catch

و لكن لدي اقتراح، لماذا لا تتأكد من توافر الكتاب قبل أن تمكّن المستخدم من اختياره؟

--------------------------------------

مشكور اخي العزيز تعبتك معاي كثير.. الله يجعلة في ميزان حسناتك .. بالنسبة للي ذكرت لي .. اول شي الكود اشتغل والرسالة القديمة لم تعد تطلع ابداّ

--------------------------------------------------------

ثانيا: الرسالة التي اصبحت تطلع لي هي الرسالة الي نكتبها في الترييقر .. اما عندما اقوم بكتابة raiseerror التريقر مايقبلها ..؟ مادري ليش

----------------------------------------

ثالثاُ : بالنسبة للحداول . انا عندي تقريباُ نفس الذي ذكرتها .. يعني عندي جدول خاص بالكتب .. وجدول خاص بالاستعارة . وجدول خاص بالزبون .. في انا مضيف بيانات اخرى للتواصل .. بس اغلب الي قلته موجود :

-------------------------------

بالنسبة للعملية التاكد من وجود الكتاب قبل عملية الاستعارة ... اخي العزيز .. اريدة ان تتم عن طريق التريقر . ... لاني استطيع حل المشكلة هاذي كاملة برمجياُ لكن .. طلب مني ان استخدم التريقر ... في هذه العملية .. ولك جزيل الشكر ..

ياليت تعدل لي على التريقر على حسب الجداول التالية :

book :

id_book :

book_name :

book_count:

book_flag : لتاكد من ان الكتاب جديد :

------------------

الجدول الثاني جدول الاستعارة :

id_Loan

id_book:

date_Loan

date_back:

flag_check:لتاكد من ان الكتاب مستعار ام لا

id_costmer:

---------------------

عندي جدول خاص بالزبون لكنه طويل .. لاني عملت بياناات كثيرة فيه .. ولكن انا رابطة مع جدول الاستعارة

ياليت تعدل لي التريقر على حسب هذه الجداول ولك جزيل الشكر اخي العزيز

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

book_flag : لتاكد من ان الكتاب جديد :

لم أفهم ما علاقة كون الكتاب جديد بموضوع الإعارة. أظن أننا لا نحتاج هذا العمود فيما يخص الإعارة

flag_check:لتاكد من ان الكتاب مستعار ام لا

هل بينة الجداول التي ذكرتها مفروضة عليك كما هي و عليك الالتزام بها أم أنك أنت من وضعها؟

خصوصا العمود السابق (flag_check) إذ لا داعي لهذا العمود.

من الأفضل أن يكون جدول الإعارة كمرجع لعمليات الإعارة التي قائمة حالياً أو السابقة. و أن يتم التحقق من توافر الكتاب من خلال عمود يحوي عدد النسخ الحالية المتوافرة من الكتاب كما أوضحت في ردي السابق

أعتذر عن كثرة الأسئلة و لكنني أحاول أن نصل إلى الحل الأقرب للحل المثالي. إن أردت الأمر أن يتم كما هو، أرجو أن تخبرني بذلك

1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

لم أفهم ما علاقة كون الكتاب جديد بموضوع الإعارة. أظن أننا لا نحتاج هذا العمود فيما يخص الإعارة

هل بينة الجداول التي ذكرتها مفروضة عليك كما هي و عليك الالتزام بها أم أنك أنت من وضعها؟

خصوصا العمود السابق (flag_check) إذ لا داعي لهذا العمود.

من الأفضل أن يكون جدول الإعارة كمرجع لعمليات الإعارة التي قائمة حالياً أو السابقة. و أن يتم التحقق من توافر الكتاب من خلال عمود يحوي عدد النسخ الحالية المتوافرة من الكتاب كما أوضحت في ردي السابق

أعتذر عن كثرة الأسئلة و لكنني أحاول أن نصل إلى الحل الأقرب للحل المثالي. إن أردت الأمر أن يتم كما هو، أرجو أن تخبرني بذلك

--------------------------

اخي العزيز انا من وضع البنية حق الجدول .. طيب اخي كيف اقوم بالتحقق من عدد النسخ من جدول الكتب قبل عملية الاعارة .. بحيث لو كان عدد النسخ = 0 يطلع لي رسالة يقول لي لايمكن الاستعارة لان عدد النسخ يساوي 0 ؟

كيف اطبق هذه بالتريقر ياليت تقولي لاني بحاجة الية ضروري يوم غداُ

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

أخي الكريم أقترح أن تكون بنية الجداول كالتالي:

جدول اسمه books فيه الأعمدة التالية:

Id, Name, ....., TotalCount, availableCount

جدول آخر اسمه Lends مثلا فيه الأعمدة التالية:

Id, customerId, bookId, lendingDate, LendingDuration

بالإضافة غلى جدول customers الذي سيرتبط معه العمود customerId من جدول الإعارات

و ال trigger يكون كالتالي:


alter TRIGGER lend_book
on lends
for insert as
DECLARE @book_id int
DECLARE @count_available int

set @book_id = 0;
set @count_available = 0;

select @bookId = bookId from inserted;
select @count_available = availableCount from books;
where id = @book_id;

if @count_available > 0
begin
update books
set availableCount = availableCount - 1
where id = @book_id;
end
else
begin
raiseerror ('sorry u cant give this book');
rollback transaction;
end;

GO

كون المطلوب منك هو استخدام الـ trigger فلا بد من استخدام عبارة raiseerror التي ستعيد خطأ إلى البرنامج. البرنامج سيتعامل معها و يظهرها بالطريقة التي تريد من خلال try...catch

و لا مشكلة في ذلك إذ أن عملية الـ insert لم تتم بسبب وجود عبارة: rollback transaction

الـ trigger مرتبط بجدول الإعارات و لكنه يقرأ و يعدل على جدول الكتب

يقوم الـtrigger عند محاولة الإدخال (إعارة جديدة) يفحص عدد النسخ المتوافرة من الكتاب في جدول الكتب فإن كان أكبر من 0 ينقص القيمة بمقدار 1 و تتم عملية الإدخال في جدول الإعارة

و إلا فلا تتم.

1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

أخي الكريم أقترح أن تكون بنية الجداول كالتالي:

جدول اسمه books فيه الأعمدة التالية:

Id, Name, ....., TotalCount, availableCount

جدول آخر اسمه Lends مثلا فيه الأعمدة التالية:

Id, customerId, bookId, lendingDate, LendingDuration

بالإضافة غلى جدول customers الذي سيرتبط معه العمود customerId من جدول الإعارات

و ال trigger يكون كالتالي:


alter TRIGGER lend_book
on lends
for insert as
DECLARE @book_id int
DECLARE @count_available int

set @book_id = 0;
set @count_available = 0;

select @bookId = bookId from inserted;
select @count_available = availableCount from books;
where id = @book_id;

if @count_available > 0
begin
update books
set availableCount = availableCount - 1
where id = @book_id;
end
else
begin
raiseerror ('sorry u cant give this book');
rollback transaction;
end;

GO

كون المطلوب منك هو استخدام الـ trigger فلا بد من استخدام عبارة raiseerror التي ستعيد خطأ إلى البرنامج. البرنامج سيتعامل معها و يظهرها بالطريقة التي تريد من خلال try...catch

و لا مشكلة في ذلك إذ أن عملية الـ insert لم تتم بسبب وجود عبارة: rollback transaction

الـ trigger مرتبط بجدول الإعارات و لكنه يقرأ و يعدل على جدول الكتب

يقوم الـtrigger عند محاولة الإدخال (إعارة جديدة) يفحص عدد النسخ المتوافرة من الكتاب في جدول الكتب فإن كان أكبر من 0 ينقص القيمة بمقدار 1 و تتم عملية الإدخال في جدول الإعارة

و إلا فلا تتم.

----------------------------------------------------

مشكور اخي العزيز .. الله يرضى عليك .. ماقصرت والله خلاص انحلت المشكلة بس بقي شي واجد عندما اكتب raiseeror اماعند كتابة print تنكتب ليش ؟ لااعلم لماذا ؟

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

ما فهمت السؤال أخي الكريم

print تستخدم لطباعة قيمة نصية على شاشة الconsole

raiseerror لتوليد خطأ على مستوى قاعدة البيانات و بالتالي تستطيع التعامل معه باستخدام try...catch

أرجو التوضيح إن لم أكن قد أجبت على السؤال

1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

ما فهمت السؤال أخي الكريم

print تستخدم لطباعة قيمة نصية على شاشة الconsole

raiseerror لتوليد خطأ على مستوى قاعدة البيانات و بالتالي تستطيع التعامل معه باستخدام try...catch

أرجو التوضيح إن لم أكن قد أجبت على السؤال

----------------------

اخي العزيز المقصود اني اريد ان اطبع الخطاء الذي اكتبة في التريقر عبر ليبل .. لكن لا اعلم ماهي الطريقة ما التريقر الي كتبتة لي كان صحيح اخي العزيز ونحلت المشكلة باقي بس كيف اطبع رسالة الخطاء الي اكتبها في التريقر عبر ليبل في الصفحة

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

الكود في الصفحة يكون كالتالي:


try
{
//كود الاستعارة هنا
}
catch (Exception ex)
{
label1.Text = ex.message;
}

و يبقى كود ال trigger كما هو (أي باستخدام raiserror)

1

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه
  • 0

السلام عليكم

الكود في الصفحة يكون كالتالي:


try
{
//كود الاستعارة هنا
}
catch (Exception ex)
{
label1.Text = ex.message;
}

و يبقى كود ال trigger كما هو (أي باستخدام raiserror)

----------------------------------------

مشكور اخي العزيز ماقصرت والله

0

شارك هذا الرد


رابط المشاركة
شارك الرد من خلال المواقع ادناه

من فضلك سجل دخول لتتمكن من التعليق

ستتمكن من اضافه تعليقات بعد التسجيل



سجل دخولك الان

  • يستعرض القسم حالياً   0 members

    لا يوجد أعضاء مسجلين يشاهدون هذه الصفحة .