تجربة عملية ترقية MySQL 5.7 إلى الإصدار 8.0

صورة

لقد قمنا مؤخرًا بترقية خوادمنا من MySQL 5.7 إلى 8.0.

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

أولاً ، قبل التحديث ، يجدر النظر إلى قائمة التغييرات وتصحيح ملف التكوين الخاص بك.

كحد أدنى ، تم حذف الخيارات التالية:
innodb_file_format ، innodb_file_format_check ، innodb_file_format_max ، innodb_large_prefix
query_cache_limit ، query_cache_min_res_unit ، query_cache_size ، query_cache_type ، query_cache_wlock_invalidate.

في المعلمة sql_mode ، على وجه الخصوص ، تم حذف NO_AUTO_CREATE_USER - وهو أمر مهم بشكل خاص ، لأن في MySQL 5.7 ، تم تشغيله افتراضيًا.

بيركونا لديه تعليمات للترقية في المكان. وفي الحالة العامة ، يمكنك متابعته ، ومع ذلك ، تمكنا من تحديث كتلة واحدة فقط بهذه الطريقة ؛ أما بالنسبة للباقي ، فشلت محاولة تحديث هذا بسبب خطأ مشابه:

2019-06-22T05:04:18.510888Z 1 [ERROR] [MY-011014] [Server] Found partially upgraded DD. Aborting upgrade and deleting all DD tables. Start the upgrade process again. 2019-06-22T05:04:23.115018Z 0 [ERROR] [MY-010020] [Server] Data Dictionary initialization failed. 2019-06-22T05:04:23.115655Z 0 [ERROR] [MY-010119] [Server] Aborting 

لذلك ، قمنا بتحديث الكتل المتبقية عن طريق رفع نسخة فارغة جديدة واستعادة تفريغ قاعدة البيانات من الإصدار السابق.

للقيام بذلك ، أولاً ، تحتاج إلى تفريغ قاعدة بيانات. وهنا الخطر # 1 ينتظر - تفريغ مصنوع بالطريقة القياسية:

 mysqldump -u root -p --hex-blob --default-character-set=utf8mb4 --all-databases --triggers --routines --events > dump.sql 

لا يسترد إعطاء خطأ:

 ERROR 3554 (HY000) at line 15915: Access to system table 'mysql.innodb_index_stats' is rejected. 

الوصف موجود في MySQL bugtracker (مع الحالة Not a bug :) ، هناك أيضًا نصيحة حول كيفية التفريغ بحيث يمكن استعادته:

 mysqldump -u root -p --hex-blob --default-character-set=utf8mb4 --all-databases --triggers --routines --events --ignore-table=mysql.innodb_index_stats --ignore-table=mysql.innodb_table_stats > dump.sql 

ولكن عند محاولة استخدام مثل هذا التفريغ ، إذا كانت هناك مشغلات فيه (وكان لدينا) ، يمكن توقع الخطر رقم 2 ، في شكل مثل هذا الخطأ:

 ERROR 1231 (42000) at line 54: Variable 'sql_mode' can't be set to the value of 'NO_AUTO_CREATE_USER' 

سبب ذلك هو أن MySQL يستخدم sql_mode للمشغلات ، وهي: MySQL يحفظ قيمة sql_mode للمشغل في وقت إنشائه ثم ينفذها دائمًا بتلك القيمة. وبناء عليه ، يحفظ هذه القيمة في تفريغ.

وصف المساعدة لهذا:
dev.mysql.com/doc/refman/8.0/en/create-trigger.html
يقوم MySQL بتخزين إعداد متغير النظام sql_mode ساري المفعول عند إنشاء المشغل ، ويقوم دائمًا بتنفيذ نص المشغل مع هذا الإعداد المعمول به ، بصرف النظر عن وضع SQL للخادم الحالي عندما يبدأ المشغل في التنفيذ.

ماذا نفعل؟ لقد قمنا فقط بقص NO_AUTO_CREATE_USER من التفريغ النهائي. قيادة مماثلة:

 sed "s/50003 SET sql_mode = 'STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO,NO_AUTO_CREATE_USER/50003 SET sql_mode = 'STRICT_TRANS_TABLES,NO_ZERO_IN_DATE,NO_ZERO_DATE,ERROR_FOR_DIVISION_BY_ZERO/g" dump.sql > dump2.sql 

بعد ذلك ، يتم استعادة التفريغ بنجاح ، ولكن الخطر رقم 3 ينتظرنا (الحقيقة المتوقعة تمامًا) - تتم استعادة جداول النظام إلى الحالة من الإصدار 5.7 ولدينا الأخطاء التالية في السجلات:

 [ERROR] [MY-013143] [Server] Column count of mysql.user is wrong. Expected 51, found 45. The table is probably corrupted 

من تجربة الإصدارات السابقة ، يتم التعامل مع هذا عن طريق تشغيل mysql_upgrade - لكن منذ الإصدار 8.0.16 - هذا لا يعمل ، لأن أعلن mysql_upgrade إهمال ولا يفعل أي شيء.

الآن ، لكي يتم تحديث جداول النظام ، يجب عليك تشغيل MySQL مع ترقية الخيار = FORCE .

على أوبونتو الطازجة ، يمكن القيام بذلك على النحو التالي:

 systemctl set-environment MYSQLD_OPTS="--upgrade=FORCE" 

ثم أعد تشغيل MySQL. حسنًا ، بعد التحديث الناجح ، احذفه:

 systemctl unset-environment MYSQLD_OPTS 

Source: https://habr.com/ru/post/ar476852/


All Articles