الفريق العربي للبرمجةأرشيف المنتديات · 2000 – 2023
نسخة أرشيفية للقراءة فقط — التسجيل والمشاركة مغلقان، والمحتوى محفوظ كما كان.

مشكلة ترقيم الفواتير

بدأه TOPSOFT في 22 فبراير 2009 · 10 رد · 3,389 مشاهدة · في قواعد بيانات Microsoft SQL Server
مشاركة: واتساب X فيسبوك تيليجرام
#1 صاحب الموضوع

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

الأخوة أعضاء هذا المنتدى الجميل

سوف أعرض عليكم مشكلتي مع السيرفر وأرجو من كل من لديه معلومه بأن لا يبخل بها علينا

المشكلة هي

قمت بعمل برنامج مستشفى مصغر يقوم البرنامج بعمل فواتير المراجعين على الاستقبال ويوجد لديا فواتير أجله خاصة بشركات التأمين وفواتير كاش

ويعمل على البرنامج أكثر من 10 مستخدمين في وقت واحد على الاستقبال

بالنسبة لقاعدة البيانات وهي اس كيو ال بالطبع فقد قمت بعمل جدول اسمه INV_NO وهذا الجدول به حقل واحد فقط وهو خاص فقط لعمل الترقيم بمعنى أن كل عملية أو كل فاتورة يقوم البرنامج بمقارنة أخر رقم ويضيف عليه واحد ويأخذ رقم فاتورة جديد ويضيف عليه حرفين CH إذا كانت الفاتورة كاش وحرفين CR إذا كانت الفاتورة أجل .

ملحوظة شكل الفواتير عندي على هذا النحو CH-0000 - CR-0000 بمعنى الحرفين يرمزو لنوع الفاتورة أن كانت كاش أو أجل

وسوف أضع الكود المستخدم في ذلك وهو كالتالي

Private Sub GenFatora()
		strSql = "SELECT Max([INV_NO].INV_NO_CR) AS MaxOfOrderID " & _
				"FROM [INV_NO];"
		txtDocNo.Text = "CR-" & (Val(GET_MAX_ID(strSql, "MaxOfOrderID")) + 1)
'
				If RsInv.State = adStateOpen Then RsInv.Close: Set RsInv = Nothing
				RsInv.Open "UPDATE [INV_NO] SET [INV_NO_CR] ='" & txtDocNo & "'", CN, adOpenStatic, adLockPessimistic

End Sub

والمشكلة هي أن في بعض الأحيان يقوم السيرفر بإعطاء رقم فاتورة واحد لأكتر من مستخدم

بمعنى أنه يكون عندي رقمين متشابهين

بمعنى أنه ممكن أن يعطي رقم 1 لأكثر من مستخدم في آن واحد

فكل ما أريده هو ما هي المشكلة هل هي

-بطء من السيرفر او الأجهزة الطرفية في سرعة تنفيذ العملية

-أو هل هو خطأ في الكود

-أو هو خطأ في كود الاتصال بقاعدة البيانات

- هل هناك خاصية معينة في اس كيو ال لتنظيم هذه العملية وعدم تكرارها

والسؤال الأخر هل هذه المشكلة ممكن أن تحصل في حال أذا ضغط عدد 2 مستخدمين على كوماند الحفظ في آن واحد وبالطبع ممكن أن تحصل هذه العملية لكثرة المرضى وازدحام الاستقبال .

وأنا أعرف أن اس كيو أل يقوم بترتيب العمليات الوارده إليه والاستجابه لها FIFO

أحد الأخوه ممكن أن يقول لي لماذا لا تعمل ترقيم تلقائي داخل جدول الفواتير

ولكن المشكله ان عندي حروف في الفاتورة للتمييز بينهم

وأخيرا أرجو من كل من لديه فكره بأن لا يبخل بها

وشكرا مقدما

تم تعديل هذه المشاركة بواسطة Night Coder في 22 فبراير 2009 في 15:18

" الحمـــــد لله الــــذي تتـــــــم بـــــــه الصالحـــــات "

#2

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

واضح ان الكود مكتوب بفيجوال بيسك 6 هناك حل يفيد فى حالتك ان شاء الله

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

Technical Lead Developer

My LinkedIn Profile

اللهم قنى شر الجهل و الجهلاء

( اقْتَرَبَ لِلنَّاسِ حِسَابُهُمْ وَهُمْ فِي غَفْلَةٍ مَّعْرِضُونَ ) {الأنبياء:1}

#3

شكرا أخي العزيز Night Coder

على ردك

وهو فعلا حل معقول ولكن أنا أريد أن أعرف بعض الشيء عن اس كيو ال

يعني لو يتفضل أحد الأخوه بشرح هذه النقطه حتى نستفيد

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

هل هي للأسرع أم هو يقوم باستقبالها وترتيبها وإعطاء الأولويات

وكيف نتلاشى حالات ازدحام السيرفر وبطء استجابته

وشكرا جزيلا

" الحمـــــد لله الــــذي تتـــــــم بـــــــه الصالحـــــات "

#4
اقتباس
يعني لو يتفضل أحد الأخوه بشرح هذه النقطه حتى نستفيد

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

راجع هذا الرابط فى رد حول ال Locking

عمل Lock على Row معين

تم تعديل هذه المشاركة بواسطة Night Coder في 24 فبراير 2009 في 04:11

Technical Lead Developer

My LinkedIn Profile

اللهم قنى شر الجهل و الجهلاء

( اقْتَرَبَ لِلنَّاسِ حِسَابُهُمْ وَهُمْ فِي غَفْلَةٍ مَّعْرِضُونَ ) {الأنبياء:1}

#5

مشرفنا العزيز Night Coder

أعزرني على تأخري في الرد

فأنا حاولت أن أجمع أكبر معلومات عن transaction isolation level

وبالفعل قد تعرفت عليها وسأكتب لك ما فهمته مع نفس الدلة السابقة لتوليد فاتورة جديده بس مع عملية ال isolation level

وأرجو أن تراجع الكود وتشوف هل هو صحيح أم خطأ

Private Sub GenFatora()
SET TRANSACTION ISOLATION LEVEL REPEATABLE READ
GO
		strSql = "SELECT Max([INV_NO].INV_NO_CR) AS MaxOfOrderID " & _
				"FROM [INV_NO];"
		txtDocNo.Text = "CR-" & (Val(GET_MAX_ID(strSql, "MaxOfOrderID")) + 1)
'
				If RsInv.State = adStateOpen Then RsInv.Close: Set RsInv = Nothing
				RsInv.Open "UPDATE [INV_NO] SET [INV_NO_CR] ='" & txtDocNo & "'", CN, adOpenStatic, adLockPessimistic
...
COMMIT TRANSACTION
End Sub

هل بهذه الطريقة تنجح العملية أم هناك نقص في الأكواد

عزرا أن كنت أثقلت عليك فأنا ما زلت مبتدأ ونطمع في سعة صدركم للتعلم

كما أن هناك عدة أنواع لل Isolation

READ COMMITTED

READ UNCOMMITTED

REPEATABLE READ

SERIALIZABLE

أيهما أفضل بالنسبة لبرنامجي هل ال REPEATABLE READ أم SERIALIZABLE

وشكرا لك مقدما أخي العزيز

تم تعديل هذه المشاركة بواسطة Night Coder في 25 فبراير 2009 في 10:05 — السبب: Adding Code Tag

" الحمـــــد لله الــــذي تتـــــــم بـــــــه الصالحـــــات "

#6

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

الاخ الحمدان المشكلة في الاستعلام في عن اكبر .

مثال قام احد المستخدمين بعمل فاتورة جديد وكان العدد الاكبر للفاتورة هو 500

وقام مستخدم اخر بعمل فاتورة قبل ان يقوم المستخدم الاخر بتخزين الفاتورة الاول. سيكون العدد الاكبر 500

لهذا سوف يكون تكرار برقم الفاتورة لهذا اقترح عليك ان.

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

ارجو اني افدتك واذا لم اكن واضح في كلامي ارجوا سوالي نقاط الافهم

#7

ألسلام عليكم ورحمة الله .. لقد واجهة نفس المشكلة ببرنامجي .. والحل بسيط جدا ..

عليك بعمل فنكشن للفاتورة .. ألا وهي كالتالي ..

	Function GetBillCode() As String

		Dim Now As DateTime = DateTime.Now

		Dim year As String = Now.Year.ToString()
		Dim Month As String = Now.Month.ToString()
		Dim day As String = Now.Day.ToString()
		Dim hour As String = Now.Hour.ToString()
		Dim Second As String = Now.Second.ToString()
		Dim milisecond As String = Now.Millisecond.ToString()

		Dim DateAndTime As String = year & Month & day & hour & Second & milisecond

		Return DateAndTime

	End Function

وبالتالي سيكون كود الفاتورة غير عن أي فاتورة أخرى لأنه الفنكشن يحسب الوقت بالميلي لكل عميل

وطبعا ممكن إضافة الكود إذا كان كاش أو فاتورة كالتالي ,,

Dim FatoraCode as String = GetBillCode()

Dim credit as String = "Cr-"+ FatoraCode

Dim bill as String = "Ch-" +FatoraCode

وإذا تريد كود كامل مع قاعدة البيانات أنا حاضر ..

تحياتي ..

#8

الأخوة / العيسائي - Tariq AlFars

السلام عليكم

طبعا أنا كنت قد فقدت الأمل أن يرد عليا أحد في هذا الموضوع

ولكن لا ينقطع أم إن شاء الله بوجود أمثالكم المحبين للمساعدة والتعاون

أولا أخي العيسائي أشكرك جزيلا على ردك وبالنسبه لكلامك ما فهمته هو أن لا أقوم بأخذ رقم الفاتورة إلا قبل تخزين بيانات الفاتورة مباشرتا بمعنى أن لا أقوم بأخذ رقم والتأخر في تخزينه حتى لا يأخذه أحد غيري

عموما أنا بالفعل أقوم باستدعاء الفنكشن بتوليد رقم جديد وحفظه في نفس الفنكشن لو نظرت للكود المرفق ستتضح لك الرؤيه

عموما بارك الله فيك

ثانيا أخي Tariq AlFars

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

عموما سوف أجرب وأوافيك بالنتيجه

وبالنسبه لعملية ال isolation

طبعا الاخ طارق وضع عنوان للموضوع ولم يكمله وأنا قمت بالبحث فيها كثيرا ولم أتوصل لحل مفيد

وأعتقد من ردودكم أنها ليست الحل الأمثل

وشكرا

" الحمـــــد لله الــــذي تتـــــــم بـــــــه الصالحـــــات "

#9

الأخ / Tariq AlFars

قمت بتجربة الكود الخاص بك ولم يظبط معي لأني أعمل على فيجوال بيسك 6

على العموم قمت بعمل فنكشن أخرى لاستخراج نفس النتيجه ولكن أعتقد أنه سوف يكون هناك تكرار في حالة إذا قام أكثر من مستخدم بتنفيذ الأمر في نفس اللحظه

بالخصوص أني لو عملت هذه الفنكشن سوف أعتمد على تاريخ السيرفر وسوف يكون هناك تفاوت في استجابة السيرفر للأوامر وممكن يعطي نفس الرقم

أرجو وضع مثال ربما أكون أن مخطىء

شكرا لكم تعاونكم

تم تعديل هذه المشاركة بواسطة TOPSOFT في 7 مارس 2009 في 20:21

" الحمـــــد لله الــــذي تتـــــــم بـــــــه الصالحـــــات "

#10
TOPSOFT كتب:
الأخ / Tariq AlFars

قمت بتجربة الكود الخاص بك ولم يظبط معي لأني أعمل على فيجوال بيسك 6

على العموم قمت بعمل فنكشن أخرى لاستخراج نفس النتيجه ولكن أعتقد أنه سوف يكون هناك تكرار في حالة إذا قام أكثر من مستخدم بتنفيذ الأمر في نفس اللحظه

بالخصوص أني لو عملت هذه الفنكشن سوف أعتمد على تاريخ السيرفر وسوف يكون هناك تفاوت في استجابة السيرفر للأوامر وممكن يعطي نفس الرقم

أرجو وضع مثال ربما أكون أن مخطىء

شكرا لكم تعاونكم

أخي العزيز TOPSOFT ..

فكرت بالأمر ووجدت الحل المناسب وشغال 100% معي وهو كالتالي:

نستخدم الفنكشن السابق ونضيف عليه شي لا يتكرر مثلا رقم الإيدي لليوزر (UserID) بمعنى يمكن نضيف أول رقمين أو ثلاثة لليوزر أيدي أو رقم الزبون(CustomerID) وبالتالي لا يمكن للزبون الموجود أمامك يكون موجود بمكان ثاني أو اليوزر النيم لمدخل البيانات يستخدم من قبل شخص آخر في نفس الوقت ..

بخصوص الفنكشن لليوزر أيدي كالتالي:

Protected Sub Page_Load(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Load

		Try
			'Creating instance object of userID 
'loginNamePas2 is the label control which handle the user id while the page load
Dim userID2 as String
			Dim UserGUID As String = User.Identity.ToString
			UserGUID = loginNamePas2.Text
			Dim UserId As Guid = Membership.GetUser().ProviderUserKey()


			loginNamePas2.Text = UserId.ToString
			loginNamePas2.Visible = False
userID2 = loginNamePas2.Text
'getBillCode is the date function which gose with user id as unique id
userID2= userID2 + GetBillCode()
		Catch ex As Exception

			Response.Redirect("login.aspx")
		End Try

وإذا لم تعجبك الفكرة لدي حل آخر ولكن معقدة قليلا..

#11

شكرا جزيلا / Tariq AlFars

هي طبعا فكره جيده وبالفعل فكرت بها

عموما هي المشكله عندي في السيرفر لأنه بطئ بعض الشيء وأيضا الترقيم للفواتير كلها موجود في جدول واحد

فأنا فكرت في عمل جدولين للترقيم مثلا الكاش جدول والأجل جدول

وهذا لتخفيف العبئ على جدول واحد

وبالطابع بالاستعانه بالفنكشن أعلاه إن شاء الله سوف تضبط الأمور

شكرا لإهتمامك

" الحمـــــد لله الــــذي تتـــــــم بـــــــه الصالحـــــات "

مواضيع مشابهة