التعامل مع الأخطاء العابرة واتصل بكفاءة بـ Azure Database for MySQL

تُطبق على: قاعدة بيانات Azure للخادم الوحيد الخاص بـ MySQL

هام

قاعدة بيانات Azure لخادم MySQL الفردي على مسار الإيقاف. نوصي بشدة بالترقية إلى قاعدة بيانات Azure لخادم MySQL المرن. لمزيد من المعلومات حول الترحيل إلى خادم Azure Database for MySQL المرن، راجع ما الذي يحدث لقاعدة بيانات Azure لخادم MySQL الفردي؟

توضح هذه المقالة كيفية معالجة الأخطاء العابرة والاتصال بكفاءة بـ Azure Database for MySQL.

الأخطاء العابرة

الخطأ العابر، يُعرف أيضاً باسم الخلل العابر، هو خطأ سيعالج نفسه. تظهر معظم هذه الأخطاء عادة كاتصال بخادم قاعدة البيانات يتم إسقاطه. وأيضاً، لا يمكن فتح اتصالات جديدة بالخادم. يمكن أن تحدث الأخطاء العابرة على سبيل المثال عند حدوث فشل في الأجهزة أو الشبكة. ويتمثل أحد الأسباب الأخرى في وجود إصدار جديد من خدمة النظام الأساسي كخدمة التي يتم طرحها. ويتم تخفيف معظم هذه الأحداث تلقائياً بواسطة النظام في أقل من 60 ثانية. من أفضل الممارسات لتصميم التطبيقات وتطويرها في السحابة توقع الأخطاء العابرة. افترض أنها يمكن أن تحدث في أي مكون في أي وقت وأن يكون لديك المنطق المناسب للتعامل مع هذه المواقف.

معالجة الأخطاء العابرة

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

  • حدوث خطأ عند محاولة فتح اتصال
  • يتم إسقاط اتصال خامل من جانب الخادم. عندما تحاول إصدار أمر لا يمكن تنفيذه
  • إسقاط اتصال نشط يقوم حالياً بتنفيذ أمر.

تعد الحالة الأولى والثانية مباشرة إلى حد ما للتعامل معها. حاول فتح الاتصال مرة أخرى. عند النجاح، يتم تخفيف الخطأ العابر بواسطة النظام. يمكنك استخدام Azure Database for MySQL مرة أخرى. نوصي بالانتظار قبل إعادة محاولة الاتصال. تراجع إذا فشلت إعادة المحاولة الأولية. بهذه الطريقة يمكن للنظام استخدام جميع الموارد المتاحة للتغلب على حالة الخطأ. النمط الجيد الذي يجب اتباعه هو:

  • الانتظار لمدة 5 ثوانٍ قبل إعادة المحاولة الأولى.
  • لكل إعادة محاولة تالية، قم بزيادة فترات الانتظار بشكل تصاعدي، حتى 60 ثانية.
  • قم بتعيين الحد الأقصى لعدد مرات إعادة المحاولة، وعند هذه النقطة يعتبر تطبيقك أن العملية فشلت.

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

وتتمثل إحدى طرق القيام بذلك، في إنشاء معرّف فريد على العميل يتم استخدامه لجميع عمليات إعادة المحاولة. يمكنك تمرير هذا المعرّف الفريد كجزء من المعاملة إلى الخادم وتخزينه في عمود مع قيد فريد. بهذه الطريقة يمكنك إعادة محاولة المعاملة بأمان. وستنجح إذا تم التراجع عن المعاملة السابقة ولم يكن المعرف الفريد الذي أنشأه العميل موجوداً بعد في النظام. وستفشل مشيرة إلى انتهاك مفتاح مكرر إذا تم تخزين المعرّف الفريد مسبقاً لأن المعاملة السابقة اكتملت بنجاح.

عندما يتواصل برنامجك مع Azure Database for MySQL من خلال برنامج وسيط تابع لجهة خارجية، اسأل المورد عما إذا كانت البرامج الوسيطة تحتوي على منطق إعادة المحاولة للأخطاء العابرة.

تأكد من اختبار منطق إعادة المحاولة. على سبيل المثال، حاول تنفيذ التعليمات البرمجية الخاصة بك أثناء توسيع نطاق موارد الحوسبة أو خفضها لخادم Azure Database for MySQL. يجب أن يتعامل تطبيقك مع وقت التعطل القصير الذي تمت مواجهته أثناء هذه العملية دون أي مشكلات.

الاتصال بكفاءة بـ Azure Database for MySQL

تعد اتصالات قاعدة البيانات مورداً محدوداً، لذا فإن الاستفادة الفعالة من تجميع الاتصالات للوصول إلى Azure Database for MySQL يحسن من الأداء. يشرح القسم التالي كيفية استخدام تجميع الاتصالات أو الاتصالات المستمرة للوصول بشكل أكثر فعالية إلى Azure Database for MySQL.

يمكن أن يكون لإدارة اتصالات قاعدة البيانات تأثير كبير على أداء التطبيق ككل. لتحسين أداء التطبيق الخاص بك، يجب أن يكون الهدف هو تقليل عدد المرات التي يتم فيها إنشاء الاتصالات ووقت إنشاء الاتصالات في مسارات التعليمات البرمجية الرئيسية. نوصي بشدة باستخدام تجميع اتصالات قاعدة البيانات أو الاتصالات المستمرة للاتصال بـ Azure Database for MySQL. يعالج تجميع اتصالات قاعدة البيانات إنشاء اتصالات قاعدة البيانات وإدارتها وتخصيصها. عندما يطلب برنامج اتصال قاعدة بيانات، فإنه يعطي الأولوية لتخصيص اتصالات قاعدة البيانات الخاملة الموجودة، بدلا من إنشاء اتصال جديد. بعد انتهاء البرنامج من استخدام اتصال قاعدة البيانات، يتم استرداد الاتصال استعداداً لمزيد من الاستخدام، بدلاً من إغلاقه ببساطة.

للحصول على توضيح أفضل، توفر هذه المقالة جزءاً من نموذج التعليمات البرمجية التي تستخدم JAVA كمثال. لمزيد من المعلومات، اطلع على Apache DBCP الشائع.

إشعار

يعمل الخادم على تكوين آلية مهلة لإغلاق اتصال كان في حالة الخمول لبعض الوقت لتحرير الموارد. تأكد من إعداد نظام التحقق لضمان فعالية الاتصالات المستمرة عند استخدامها. لمزيد من المعلومات، اطلع على تكوين أنظمة التحقق من جانب العميل لضمان فعالية الاتصالات المستمرة.

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

الوصول إلى قواعد البيانات باستخدام آلية الانتظار وإعادة المحاولة مع الاتصالات القصيرة

إذا كانت لديك قيود على الموارد، نوصي بشدة باستخدام تجميع قواعد البيانات أو الاتصالات المستمرة للوصول إلى قواعد البيانات. إذا كان التطبيق الخاص بك يستخدم اتصالات قصيرة ويختبر فشل الاتصال عند الاقتراب من الحد الأعلى لعدد الاتصالات المتزامنة، يمكنك محاولة استخدام آلية الانتظار وإعادة المحاولة. يمكنك تعيين وقت انتظار مناسب، مع وقت انتظار أقصر بعد المحاولة الأولى. ومن ثَم يمكنك محاولة انتظار الأحداث عدة مرات.

تكوين آليات التحقق في العملاء لتأكيد فعالية الاتصالات المستمرة

يعمل الخادم على تكوين آلية مهلة لإغلاق اتصال كان في حالة الخمول لبعض الوقت لتحرير الموارد. عندما يصل العميل إلى قاعدة البيانات مرة أخرى، فإنه يعادل إنشاء طلب اتصال جديد بين العميل والخادم. لضمان فعالية الاتصالات أثناء عملية استخدامها، قم بتكوين آلية تحقق على العميل. كما هو موضح في المثال التالي، يمكنك استخدام تجميع اتصالات Tomcat JDBC لتكوين آلية التحقق هذه.

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

للحصول على معلومات حول الإعدادات المحددة، اطلع على مستند المقدمة الرسمي لتجمع اتصالات JDBC. تحتاج بشكل أساسي إلى تعيين المعلمات الثلاث التالية: TestOnBorrow (تعيين إلى true) وValidationQuery (تعيين إلى SELECT 1) وValidationQueryTimeout (تعيين إلى 1). يتم عرض نموذج التعليمات البرمجية المحدد أدناه:

public class SimpleTestOnBorrowExample {
      public static void main(String[] args) throws Exception {
          PoolProperties p = new PoolProperties();
          p.setUrl("jdbc:mysql://localhost:3306/mysql");
          p.setDriverClassName("com.mysql.jdbc.Driver");
          p.setUsername("root");
          p.setPassword("password");
            // The indication of whether objects will be validated by the idle object evictor (if any). 
            // If an object fails to validate, it will be dropped from the pool. 
            // NOTE - for a true value to have any effect, the validationQuery or validatorClassName parameter must be set to a non-null string. 
          p.setTestOnBorrow(true); 

            // The SQL query that will be used to validate connections from this pool before returning them to the caller.
            // If specified, this query does not have to return any data, it just can't throw a SQLException.
          p.setValidationQuery("SELECT 1");

            // The timeout in seconds before a connection validation queries fail. 
            // This works by calling java.sql.Statement.setQueryTimeout(seconds) on the statement that executes the validationQuery. 
            // The pool itself doesn't timeout the query, it is still up to the JDBC driver to enforce query timeouts. 
            // A value less than or equal to zero will disable this feature.
          p.setValidationQueryTimeout(1);
            // set other useful pool properties.
          DataSource datasource = new DataSource();
          datasource.setPoolProperties(p);

          Connection con = null;
          try {
            con = datasource.getConnection();
            // execute your query here
          } finally {
            if (con!=null) try {con.close();}catch (Exception ignore) {}
          }
      }
  }

الخطوات التالية