تنفيذ الإجراءات المخزنة مع معلمات التاريخ:كائن الأمر مقابل كائن الاتصال

StackOverflow https://stackoverflow.com/questions/83038

سؤال

عند توفير التواريخ لإجراء مخزن عبر معلمة، فأنا في حيرة من أمري بشأن التنسيق الذي سأستخدمه للتواريخ.استخدم بناء جملة VBA الأصلي الخاص بي كائن اتصال ADO لتنفيذ الإجراء المخزن:

Set SentDetailRS = Me.ADOConnectionToIntegrity.Execute("dbo.s_SelectAggregatedSentDetailList '" & fCSQLDate(EffectiveDate) & "'", , adCmdText)

هذا يعمل بشكل جيد بالنسبة لي باستخدام بناء جملة التاريخ yyyy-mm-dd ولكن عندما ينفذ مستخدم آخر الكود، فإنه يتلقى الخطأ:13 "نوع غير متطابق".

بعد بعض التجارب وجدت أن توفير التاريخ بالتنسيق dd/mm/yyyy يعمل على إصلاح هذا الخطأ للمستخدم ولكنه الآن يعطيني الخطأ!

يعمل تنفيذ الإجراء المخزن باستخدام كائن أمر مع معلمات بغض النظر عن تنسيق التاريخ (أفترض أن ADO يعتني بالتنسيق خلف الكواليس).اعتقدت أن استخدام الشكل yyyy-mm-dd ستعمل عالميا مع SQL Server؟

أنا أيضًا في حيرة من أمري لماذا تبدو هذه المشكلة خاصة بالمستخدم؟لقد لاحظت أن لغتي الافتراضية على SQL Server هي "الإنجليزية" بينما اللغة الافتراضية للمستخدم الآخر هي "الإنجليزية البريطانية"، فهل يمكن أن يسبب ذلك المشكلة؟

أنا أستخدم ADO 2.8 مع Access 2003 وSQL Server 2000، ويتم تسجيل الدخول إلى SQL Server عبر أمان Windows المتكامل.

هل كانت مفيدة؟

المحلول

كن حذراً، ولا تعتقد أن ADO يعتني بالمشكلة.تنسيق تاريخ SQL العالمي هو "YYYYMMDD"، بينما يتأثر كل من SQL وACCESS بالإعدادات الإقليمية للجهاز في طريقة عرض التواريخ وتحويلها في سلاسل أحرف.

لا تنس أن فاصل التاريخ هو # في Access، بينما هو ' في SQL

أفضل نصيحتي ستكون تحويل وصولك #MM-DD-YYYY# (أو ما شابه) بشكل منهجي إلى "YYYYMMDD" قبل إرسال التعليمات إلى الخادم الخاص بك.يمكنك بناء وظيفة صغيرة مثل:

Public function SQLdateFormat(x_date) as string

SQLDateFormat = _
   trim(str(datePart("yyyy",x_date))) & _
   right(str(datePart("m",date)),2) & _
   right(str(datePart("d",date)),2)

   ''be carefull, you might get something like '2008 9 3'
SQLDateFormat = replace(functionSQLDateFormat," ","0")
   '' you will have the expected '20080903'

End function

إذا لم تقم بإنشاء سلسلة INSERT/UPDATE برمجيًا قبل إرسالها إلى الخادم، فسوف أنصحك بعد ذلك بتحويل الإعدادات الإقليمية لجميع الأجهزة إلى الإعدادات الإقليمية للجهاز الذي يستضيف SQL.قد يتعين عليك أيضًا التحقق مما إذا كان هناك تنسيق تاريخ محدد على خادم SQL الخاص بك (لست متأكدًا).شخصيًا، قمت بحل هذا النوع من مشاكل الترجمة (يحدث أيضًا عند استخدام الفاصلة كفاصل عشري باللغة الفرنسية) أو مشاكل الأحرف الخاصة بـ SQL (عندما تكون علامات الاقتباس أو علامات الاقتباس المزدوجة في سلسلة) عن طريق التراجع عن تعليمات SQL قبل إرسالها إلى الخادم.

نصائح أخرى

أعتقد أن وظيفة fCSQLDate خاصة بالثقافة - أي.سيقوم بتحليل التاريخ بناءً على الإعدادات المحلية للمستخدم.ولهذا السبب ترى المشكلة.

على أي حال، يعد استخدام الاستعلامات ذات السلاسل المتسلسلة دائمًا فكرة سيئة (هجمات الحقن).أنت أفضل حالًا إذا كنت تستخدم المعلمات.

يستخدم Access # كمحدد لحقل التاريخ.يجب أن يكون التنسيق #mm/dd/yyyy# ومن المحتمل أن يعمل #mm-dd-yyyy# بشكل جيد أيضًا.

آسف، لا أعرف mysql، ولكن مع Oracle، أود دائمًا أن أذكر التنسيق الذي كنت أتوقع أن يكون التنسيق به، على سبيل المثال:"DD-MM-YYYY"، لتجنب مشاكل تنسيق التاريخ (الإقليمي).

لماذا لا تستخدم التنسيق

dd mmm yyyy

هناك طريقة واحدة فقط يمكن تفسيرها.

يمكنك استخدام الدالة Date() لإرجاع تاريخ عالمي استنادًا إلى إعدادات التاريخ والوقت الخاصة بالجهاز.ستحدد إعدادات المنطقة على الجهاز كيفية تنسيقها على جانب العميل.إذا تركت الحقل كحقل التاريخ والوقت، فيمكن لإعدادات منطقة العميل تنسيق التاريخ.

عند الدخول إلى الخادم، يجب أن تعمل وظيفة Date() أيضًا (إرجاع قيمة تاريخ عالمية).

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

مرخصة بموجب: CC-BY-SA مع الإسناد
لا تنتمي إلى StackOverflow
scroll top