ترقية FlutterFire 5.0 بأمان: قائمة فحص لمشاريع Flutter الإنتاجية

بقلم مهندس برمجيات رئيسي · LinkedIn

حُدِّث مقال أصلي

دليل عملي لترقية FlutterFire 5.0: متطلبات Android وiOS، تغييرات App Check وFirebase AI، واختبارات Auth وFirestore وMessaging قبل الإنتاج.

ترقية FlutterFire 5.0 بأمان: قائمة فحص لمشاريع Flutter الإنتاجية

أطلقت Firebase في 15 أكتوبر 2026 الإصدار 5.0.0 من Flutter BoM. الاسم يوحي بترقية حزمة واحدة، لكن الواقع أن الإصدار يجمع قفزات رئيسية لمعظم إضافات FlutterFire: firebase_core 5، وcloud_firestore 7، وfirebase_auth 7، وfirebase_messaging 17، وغيرها. كما صنّفت ملاحظات الإصدار الرسمية عددًا كبيرًا من الحزم على أنها تحتوي تغييرات كاسرة.

لذلك لا تتعامل مع الترقية كأمر flutter pub upgrade --major-versions ثم نشر مباشر. الهدف هو تحديث طبقة Firebase على فرع مستقل، وفحص متطلبات المنصات، وتعديل واجهات البرمجة، ثم إثبات أن المسارات الحرجة ما زالت تعمل على Android وiOS والويب إن كان مدعومًا.

ما الذي تغيّر فعلًا؟

يتطلب firebase_core 5.0.0 وقطاع كبير من الإضافات Dart ^3.6.0 وFlutter >=3.27.0. بعض الحزم، مثل firebase_auth وfirebase_ai، تقبل Flutter >=3.16.0، لكن الاعتماد على الحد الأقل لحزمة واحدة لا يكفي إذا كان المشروع يستخدم مجموعة Firebase كاملة.

التغيير الأهم على Android هو أن الإضافات المبنية على Firebase Android BoM 35 تتطلب minSdk 24. إذا كان تطبيقك ما زال يدعم Android 6 أو 7.0 بإعداد أقل، فهذه ليست مشكلة compile فقط؛ إنها قرار منتج يغيّر الأجهزة التي تستطيع تثبيت الإصدار القادم.

على Apple، الإصدار يستخدم pin مزدوجًا: Swift Package Manager يحل Firebase Apple SDK 13.0.0، بينما CocoaPods يبقى على 12.19.0. أي أن رفع FlutterFire وحده لا ينقل التطبيق تلقائيًا إلى SPM. مدير الحزم الذي يستخدمه مشروعك هو الذي يحدد النسخة الأصلية.

بوابات ترقية FlutterFire 5. الحصر، توثيق الوضع الحالي، متطلبات المنصات، تحديث الحزم معًا، ترحيل الواجهات، الاختبار والنشر التدريجي. نجاح البناء خطوة. السلوك هو الدليل.

الخطوة 1: اعمل جردًا قبل لمس pubspec

أنشئ جدولًا صغيرًا بكل plugin تستخدمه وسبب وجوده والمسار الذي يعتمد عليه. مثال:

Pluginمسار منتج حرجاختبار مطلوب
firebase_authتسجيل الدخول واستعادة الجلسةدخول، خروج، refresh token
cloud_firestoreبيانات المستخدم أو الطلباتقراءة، كتابة، offline ثم sync
firebase_messagingفتح إشعار لمسار داخل التطبيقforeground، background، terminated
firebase_crashlyticsرصد الأعطالخطأ non-fatal ونسخة اختبار
firebase_app_checkحماية backenddebug provider ثم build إنتاجي

سجّل أيضًا الحد الحالي لـ Android، ومدير حزم Apple، والمنصات التي يبنيها CI. هذا الجرد يتحول إلى قائمة قبول بدل الاعتماد على أن نجاح البناء يعني نجاح المنتج.

الخطوة 2: ثبّت baseline قابلًا للمقارنة

قبل الترقية، شغّل على النسخة الحالية:

bashflutter --version
flutter pub outdated
flutter analyze
flutter test
flutter build appbundle --flavor production
flutter build ipa --flavor production --no-codesign

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

الخطوة 3: ارفع المتطلبات على مستوى المنصة عمدًا

راجع android/app/build.gradle أو ملف Kotlin DSL، وارفع minSdk إلى 24 عندما تتطلبه إضافاتك. ثم اختبر على أقدم إصدار Android ستدعمه، لا على أحدث محاكي فقط.

على Apple، قرر هل الفرع يستخدم Swift Package Manager أم CocoaPods. FlutterFire 5.0 يسمح بالمسارين، لكنه يعطيهما Firebase Apple SDK مختلفًا. لا تحذف Podfile ولا تغيّر مدير الحزم ضمن الترقية نفسها إلا إذا كانت لديك خطة انتقال واختبارات مستقلة؛ خلط هجرتين يجعل سبب العطل غامضًا.

الخطوة 4: حدّث الحزم على فرع واحد، لا حزمة كل يوم

FlutterFire plugins تتحرك كمجموعة مترابطة. ابدأ بقيود الإصدارات التي تحتاجها ثم نفّذ:

bashflutter pub upgrade --major-versions
flutter pub get
flutter pub deps | grep firebase

راجع pubspec.lock وتأكد أن الحزم platform-interface وweb جاءت متوافقة. في تطبيق متعدد packages، شغّل التحقق في كل package يحتوي كود Firebase أو نماذج مشتركة.

لا ترفع dependencies غير مرتبطة في pull request نفسه. تحديث routing أو state management أو generated models مع FlutterFire يجعل المراجعة والتراجع أصعب.

الخطوة 5: أصلح التغييرات الكاسرة المقصودة

App Check

غيّرت firebase_app_check أسماء معاملات activate. استبدل:

dartawait FirebaseAppCheck.instance.activate(
  androidProvider: AndroidProvider.playIntegrity,
  appleProvider: AppleProvider.appAttest,
);

بالصيغة الجديدة:

dartawait FirebaseAppCheck.instance.activate(
  providerAndroid: const AndroidPlayIntegrityProvider(),
  providerApple: const AppleAppAttestProvider(),
);

تحقق من التوقيعات الدقيقة وفق المنصة والإصدار الموجود في مشروعك؛ المثال يوضح اتجاه التغيير وليس بديلًا عن autocomplete ومرجع الحزمة. افصل debug providers عن production ولا تنشر debug token داخل المستودع.

Firebase Data Connect

أُزيل معاملا auth وappCheck من FirebaseDataConnect وinstanceFor لأن الإضافة أصبحت تحلهما من FirebaseApp. احذف الحقن اليدوي، لكن أبقِ wrappers الخاصة بك إن كانت تفيد في الاختبار وفصل الطبقات.

Firebase AI Logic

أزال الإصدار واجهات كانت معلّمة deprecated، وغيّر سلوك LiveSession.receive() بحيث يبقى stream مفتوحًا عند رسالة خادم غير معروفة. إذا كان BLoC ينتظر إغلاق stream ليعلن نهاية الجلسة، راجع منطق الإنهاء والـ cancellation صراحة.

ML Model Downloader

لم يعد firebase_ml_model_downloader يُنشر ضمن FlutterFire. النسخ القديمة ستبقى على pub.dev، لكن خدمة تنزيل النماذج ستتوقف في 15 يونيو 2027. الحل الموصى به هو نقل النماذج المستضافة إلى Cloud Storage وتنزيلها عبر firebase_storage، مع تحقق من checksum وسياسة cache واضحة.

الخطوة 6: اختبر السلوك، لا البناء فقط

يتضمن firebase_messaging 17 إصلاحات مهمة: Android يبدأ background engine واحدًا عند وصول دفعة إشعارات، وiOS يعالج الضغط على الإشعار الذي شغّل التطبيق في الخلفية. اختبر مصفوفة الحالات الثلاث:

  1. التطبيق مفتوح.
  2. التطبيق في الخلفية.
  3. التطبيق مغلق ويُفتح من الإشعار.

تحقق أن كل حالة تفتح المسار مرة واحدة فقط، وأن payload ناقصًا لا يكسر navigation. استخدم رسالة اختبار حقيقية من مشروع staging بدل الاكتفاء بوحدة اختبار.

بالنسبة إلى Auth، اختبر cold start مع جلسة محفوظة، انتهاء token، sign-out، ومزوّدات الدخول الخارجية. ومع Firestore، اختبر transaction timeout، والعمل دون اتصال، وإعادة الاتصال. شغّل Crashlytics في build مخصص للاختبار وتأكد أن الرموز مرتبطة بالإصدار الصحيح.

الخطوة 7: افصل التهيئة عن الـ UI

في Clean Architecture، احتفظ بتهيئة Firebase في composition root أو bootstrap service، لا داخل أول شاشة. يمكن أن تعيد الدالة نتيجة واضحة يستقبلها BLoC:

dartsealed class AppBootstrapResult {}
final class AppReady extends AppBootstrapResult {}
final class RecoverableBootstrapFailure extends AppBootstrapResult {
  RecoverableBootstrapFailure(this.cause);
  final Object cause;
}

هذا يسمح بعرض retry أو وضع محدود بدل شاشة بيضاء. كما يجعل اختبار فشل App Check أو Remote Config ممكنًا من دون تشغيل Firebase حقيقي في كل unit test.

الخطوة 8: أطلق تدريجيًا مع باب رجوع

انشر أولًا على internal testing وTestFlight. راقب login success، فتح الإشعارات، crash-free sessions، وعمليات القراءة والكتابة الحرجة. لا تغيّر Rules أو schema أو notification routing في الإصدار نفسه إلا لضرورة واضحة.

إذا كان CI يبني Android وiOS والويب، اجعل نجاح الثلاثة شرطًا قبل الدمج. أما rollback الحقيقي فهو commit يعيد قيود الحزم وملف lock وتعديلات المنصة معًا؛ مجرد تقليل firebase_core قد يترك plugins غير متوافقة.

قائمة قبول مختصرة

  • Dart وFlutter يحققان الحدود المطلوبة.
  • قرار minSdk 24 موثق واختُبر على أقدم جهاز مدعوم.
  • مدير حزم Apple معروف ونسخة SDK الأصلية مفهومة.
  • App Check وData Connect وFirebase AI عُدلت حيث تُستخدم.
  • Auth وFirestore وMessaging وCrashlytics اختُبرت سلوكيًا.
  • staging يمر قبل أي طرح إنتاجي.
  • يوجد commit رجوع مكتمل ومفهوم.

الخلاصة

FlutterFire 5.0 ليس تحديثًا تجميليًا. فائدته تشمل إصلاحات للمراسلة والمصادقة والأعطال، لكنه يرفع متطلبات المنصات ويزيل واجهات قديمة. الترقية الآمنة تبدأ بجرد المنتج، ثم فرع محدود النطاق، واختبارات لكل تكامل، وطرح تدريجي قابل للتراجع.

إذا كان تطبيق Flutter لديك يعتمد على Firebase في تسجيل الدخول أو الإشعارات أو البيانات، يمكنني مراجعة خطة الترقية وبناء مصفوفة اختبار قبل إرسال إصدار جديد إلى المستخدمين.

المصادر

مقالات أخرى

شاركواتسابXLinkedIn