سؤال

أنا أستخدم MySQL 5.0 لموقع يستضيفه GoDaddy (نظام التشغيل Linux).

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

لقد كنت أنا فقط المتصل بقاعدة البيانات، وليس مستخدمين آخرين.في كل صفحة من صفحاتي، أقوم بتضمين ملف config.php في الأعلى، وأغلق اتصال mysql في نهاية الصفحة.قد يكون هناك عدة استفسارات بينهما.أخشى أنني لا أقوم بإغلاق اتصالات mysql بشكل كافٍ (mysql_ Close ()).

ومع ذلك، عندما أحاول إغلاقها بعد تشغيل استعلام، أتلقى أخطاء في الاتصال على الصفحة.صفحاتي هي PHP وHTML.عندما أحاول إغلاق استعلام، يبدو أن الاستعلام التالي لن يتم الاتصال به.هل يجب علي تضمين config.php مرة أخرى بعد الإغلاق من أجل الاتصال؟

أخافني هذا الخطأ لأنه خلال أسبوعين، بدأ حوالي 84 شخصًا في استخدام تطبيق الويب هذا.

شكرًا.

يحرر:

إليك بعض التعليمات البرمجية الزائفة لصفحتي:

 require_once('../scripts/config.php');

 <?php
    mysql_query..

    if(this button is pressed){
       mysql_query...
    }
    if(this button is pressed){
       mysql_query...
    }
    if(this button is pressed){
       mysql_query...
    }
 ?>
 some html..
 ..
 ..
 ..
 ..
 <?php
   another mysql_query...
 ?>
 some more html..
 ..
 ..
 <?php mysql_close(); ?>

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

يحرر:

حسنًا، لقد أنهيت للتو المكالمة مع GoDaddy.على ما يبدو، مع الباقة الاقتصادية الخاصة بي، يقتصر عدد اتصالاتي على 50 اتصالًا في المرة الواحدة.على الرغم من أن مشكلتي اليوم حدثت مع دخولي أنا فقط إلى الموقع، إلا أنهم قالوا إنهم كانوا يواجهون بعض المشكلات في الخادم في وقت سابق.ومع ذلك، نظرًا لأنه سيكون لدي 84 مستخدمًا لتطبيق الويب الخاص بي، فمن المحتمل أن أقوم بالترقية إلى "Deluxe"، والذي يسمح بـ 100 اتصال في المرة الواحدة.في يوم معين، قد يكون هناك حوالي 30 مستخدمًا يصلون إلى موقعي في نفس الوقت، لذلك أعتقد أن 100 سيكون رهانًا أكثر أمانًا.هل توافقون يا رفاق؟

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

المحلول

يسمح موفرو الاستضافة المشتركة عمومًا بكمية صغيرة جدًا من الاتصالات المتزامنة لنفس المستخدم.

ما يفعله الكود الخاص بك هو:

  • افتح اتصالاً بخادم MySQL
  • افعلها (إنشاء الصفحة)
  • أغلق الاتصال في نهاية الصفحة.

الخطوة الأخيرة، عندما يتم ذلك في نهاية الصفحة ليست كذلك إلزامي :(نقلا عن mysql_closeدليل ):

باستخدام MySQL_Close () ليس ضروريًا عادةً ، حيث يتم إغلاق الروابط المفتوحة غير المتسقة تلقائيًا في نهاية تنفيذ البرنامج النصي.

لكن لاحظ أنه ربما لا ينبغي عليك استخدام الاتصالات المستمرة على أي حال...

نصيحتان:

  • يستخدم mysql_connect بدلا من mysql_pconnect (موافق بالفعل بالنسبة لك)
  • قم بتعيين المعلمة الرابعة لـ mysql_connect على false (موافق لك بالفعل، لأنها القيمة الافتراضية) :(نقلا عن الدليل):

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

تعدل المعلمة new_link هذا السلوك ويجعل mysql_connect () دائمًا يفتح رابطًا جديدًا ، حتى لو تم استدعاء mysql_connect () من قبل مع نفس المعلمات.



ما الذي يمكن أن يسبب المشكلة إذن؟

ربما تحاول الوصول إلى عدة صفحات بالتوازي (باستخدام علامات تبويب متعددة في متصفحك، على سبيل المثال), والتي سوف تحاكي عدة مستخدمين يستخدمون الموقع في نفس الوقت؟

إذا كان لديك العديد من المستخدمين يستخدمون الموقع في نفس الوقت والرمز بينهما mysql_connect وإغلاق الاتصال يستغرق الكثير من الوقت، وهذا يعني فتح العديد من الاتصالات في نفس الوقت...وسوف تصل إلى الحد الأقصى :-(

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



حسنًا ، أفكر في "الكثير من الاتصالات" و "max_connections"...

إذا كنت أتذكر بشكل صحيح، max_connections لا يحد من عدد الاتصالات أنت يمكن فتحه على خادم MySQL، لكن إجمالي عدد الاتصالات التي يمكن فتحها على ذلك الخادم، من قبل أي شخص متصل به.

نقلا عن وثائق MySQL على اتصالات كثيرة جدًا :

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

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

لذا، في الواقع، قد لا تكون المشكلة منك ولا من الكود الخاص بك (والتي تبدو جيدة، في الواقع) :قد يكون الأمر "فقط" أنك لست الوحيد الذي يحاول الاتصال بخادم MySQL هذا (تذكر، "الاستضافة المشتركة"), وأن هناك الكثير من الأشخاص يستخدمونه في نفس الوقت..

...و إذا كنت على حق وهذا هو, ، لا يوجد شيء يمكنك القيام به لحل المشكلة:طالما أن هناك عددًا كبيرًا جدًا من قواعد البيانات/المستخدمين على ذلك الخادم وذاك max_connection تم ضبطه على 200، وسوف تستمر في المعاناة ...


كملاحظة جانبية :قبل العودة إلى GoDaddy لسؤالهم عن ذلك، سيكون من الرائع أن يتمكن شخص ما من التحقق من صحة ما قلته للتو ^^

نصائح أخرى

كان لدي حوالي 18 شهرًا من التعامل مع هذا (http://ianchanning.wordpress.com/2010/08/25/18-months-of-dealing-with-a-mysql-too-many-connections-error/)

الحلول التي كانت لدي (والتي تنطبق عليك) في النهاية هي:

  1. ضبط قاعدة البيانات وفقا ل MySQLTuner.
  2. قم بإلغاء تجزئة الجداول أسبوعيًا بناءً على ذلك بريد

إلغاء تجزئة البرنامج النصي bash من المنشور:

#!/bin/bash

# Get a list of all fragmented tables
FRAGMENTED_TABLES="$( mysql -e `use information_schema; SELECT TABLE_SCHEMA,TABLE_NAME
FROM TABLES WHERE TABLE_SCHEMA NOT IN ('information_schema','mysql') AND
Data_free > 0` | grep -v '^+' | sed 's,t,.,' )"

for fragment in $FRAGMENTED_TABLES; do
  database="$( echo $fragment | cut -d. -f1 )"
  table="$( echo $fragment | cut -d. -f2 )"
  [ $fragment != "TABLE_SCHEMA.TABLE_NAME" ] && mysql -e "USE $database;
  OPTIMIZE TABLE $table;" > /dev/null 2>&1
done

تأكد من أنك لا تستخدم الاتصالات المستمرة. هذا عادة ما يكون فكرة سيئة ..

إذا كنت قد حصلت على ذلك .. وفي معظم جدا سوف تحتاج إلى دعم الاتصالات فقط بقدر ما لديك العمليات اباتشي. هل أنت قادرة على تغيير الإعداد max_connections؟

هل أنت متأكد تماما أن خادم قاعدة البيانات هو مخصص تماما بالنسبة لك؟

وقم بتسجيل الدخول إلى datbase كجذر واستخدام "PROCESSLIST إظهار" لمعرفة من المتصل. ومن الناحية المثالية ربط هذا إلى نظام مراقبة لعرض عدد الاتصالات هناك مع مرور الوقت والتنبيه في حالة وجود عدد كبير جدا.

ويمكن تكوين اتصالات قاعدة البيانات القصوى في my.cnf، ولكن احترس من نفاد الذاكرة أو عنوان الفضاء.

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

في لينكس، اكتب:

netstat -n -a |grep 3306

في النوافذ، اكتب:

netstat -n -a |findstr 3306

والحل يمكن واحد من هؤلاء، جئت عبر هذا في اختبار MCQA، حتى أنا لم يفهم احد الذي هو الحق!

وتعيين هذا في my.cnf "مجموعة-متغير = max_connections = 200"

وتنفيذ الأمر "SET GLOBALmax_connections = 200"

استخدم دائما mysql_connect () وظيفة من أجل الاتصال بالخادم الخلية

استخدم دائما mysql_pconnect () وظيفة من أجل الاتصال بالخادم الخلية

فيما يلي الحلول الممكنة:

1) قم بزيادة إعداد الاتصال الأقصى عن طريق تعيين المتغير العام في الخلية.

set global max_connection=200;

ملحوظة: سيزيد من تحميل الخادم.

2) قم بإفراغ تجمع الاتصال الخاص بك على النحو التالي:

FLUSH HOSTS;

3) تحقق من قائمة العمليات الخاصة بك وقم بقتل قائمة العمليات المحددة إذا كنت لا تريد أيًا منها.


يمكنك الرجوع لهذا :-

رابط المقال

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