مشروع التخرج: تطبيق Flutter حقيقي

تكامل Firebase وضبط إعدادات المشروع

16 دقيقة الدرس 2 من 10

تكامل Firebase وضبط إعدادات المشروع

Firebase هي منصة تطوير التطبيقات الشاملة من Google التي توفر مجموعة من خدمات الواجهة الخلفية — Firestore (قاعدة بيانات NoSQL)، والمصادقة، والتخزين، ووظائف السحابة، وغيرها — وكلها يمكن الوصول إليها من Flutter دون إدارة أي بنية تحتية للخادم. في هذا الدرس ستقوم بتوصيل مشروع Flutter الرئيسي الخاص بك بمشروع Firebase باستخدام FlutterFire CLI، وضبط الخدمات الثلاث الأساسية (Firestore، والمصادقة، والتخزين)، وإعداد خيارات خاصة بكل بيئة لكلٍّ من Android وiOS.

الخطوة الأولى — إنشاء مشروع Firebase

قبل كتابة أي كود، تحتاج إلى مشروع Firebase في Google Firebase Console:

  • اذهب إلى console.firebase.google.com وانقر إضافة مشروع.
  • أعطِه اسماً (مثلاً capstone-app)، فعّل Google Analytics اختيارياً، ثم انقر إنشاء مشروع.
  • بمجرد الإنشاء، فعّل الخدمات الثلاث: Firestore Database، وAuthentication (فعّل مزود البريد الإلكتروني/كلمة المرور)، وStorage.
ملاحظة: ابقِ Firestore في وضع الاختبار في البداية حتى تتمكن من القراءة والكتابة بحرية أثناء التطوير. قبل الإطلاق للإنتاج يجب عليك تشديد قواعد الأمان.

الخطوة الثانية — تثبيت FlutterFire CLI وfirebase_core

FlutterFire CLI تؤتمت الضبط الخاص بكل منصة (توليد google-services.json لـ Android وGoogleService-Info.plist لـ iOS) وتنتج ملف firebase_options.dart واحداً يستخدمه تطبيقك في وقت التشغيل.

تثبيت الاعتماديات

# تثبيت Firebase CLI عالمياً (إذا لم يكن مثبتاً)
npm install -g firebase-tools
firebase login

# تثبيت FlutterFire CLI عالمياً
dart pub global activate flutterfire_cli

# إضافة الحزم المطلوبة لمشروع Flutter
flutter pub add firebase_core cloud_firestore firebase_auth firebase_storage
نصيحة: تأكد من أن ~/.pub-cache/bin موجودة في متغير البيئة PATH حتى يُعرف الأمر flutterfire. على macOS/Linux، أضف export PATH="$PATH":"$HOME/.pub-cache/bin" إلى ملف تهيئة الشل.

الخطوة الثالثة — تشغيل flutterfire configure

بعد تثبيت الـ CLI، شغّل الأمر التالي من جذر مشروع Flutter. سيطلب منك اختيار مشروع Firebase ويضبط تلقائياً كلاً من Android وiOS:

ضبط FlutterFire

flutterfire configure --project=capstone-app

سيقوم الـ CLI بـ:

  • تنزيل ووضع android/app/google-services.json لـ Android.
  • تنزيل ووضع ios/Runner/GoogleService-Info.plist لـ iOS.
  • توليد lib/firebase_options.dart — ملف Dart يحتوي على فئة DefaultFirebaseOptions بمفاتيح API ومعرفات المشروع الخاصة بكل منصة.
تحذير: لا تلتزم أبداً بـ google-services.json أو GoogleService-Info.plist أو firebase_options.dart في مستودع عام. أضفها إلى .gitignore. هذه الملفات تحتوي على مفاتيح API التي يمكن إساءة استخدامها إذا انكشفت.

الخطوة الرابعة — تهيئة Firebase في main.dart

يجب تهيئة Firebase قبل runApp(). لأن التهيئة غير متزامنة، يجب أن تكون main() من نوع async وأن تستدعي WidgetsFlutterBinding.ensureInitialized() أولاً:

lib/main.dart — تهيئة Firebase

import 'package:firebase_core/firebase_core.dart';
import 'package:flutter/material.dart';
import 'firebase_options.dart';

Future<void> main() async {
  // يجب استدعاؤها قبل أي عمل غير متزامن في main()
  WidgetsFlutterBinding.ensureInitialized();

  await Firebase.initializeApp(
    options: DefaultFirebaseOptions.currentPlatform,
  );

  runApp(const MyApp());
}

DefaultFirebaseOptions.currentPlatform تختار تلقائياً الضبط الصحيح (Android مقابل iOS مقابل Web) في وقت التشغيل بناءً على المنصة المكتشفة.

الخطوة الخامسة — ضبط ملفات منصتَي Android وiOS

بجانب ملفات JSON/plist، تحتاج كل منصة إلى إعداد بسيط لمرة واحدة.

Android — افتح android/build.gradle وأضف مسار الفئة لإضافة Google Services، ثم طبّقها في android/app/build.gradle:

android/build.gradle (مستوى المشروع)

buildscript {
  dependencies {
    // أضف هذا السطر:
    classpath 'com.google.gms:google-services:4.4.1'
  }
}

android/app/build.gradle (مستوى التطبيق) — أسفل الملف

// طبّق الإضافة في الأسفل:
apply plugin: 'com.google.gms.google-services'

iOS — شغّل cd ios && pod install بعد إضافة حزم Firebase حتى تسحب CocoaPods SDKs Firebase الأصلية. عيّن أيضاً الحد الأدنى لهدف نشر iOS إلى 13.0 في ios/Podfile:

ios/Podfile

platform :ios, '13.0'

الخطوة السادسة — الوصول إلى خدمات Firebase

بمجرد التهيئة، يُمكن الوصول إلى كل خدمة عبر نسختها المفردة (singleton). إليك مرجعاً مختصراً:

الوصول إلى Firestore وAuth وStorage

import 'package:cloud_firestore/cloud_firestore.dart';
import 'package:firebase_auth/firebase_auth.dart';
import 'package:firebase_storage/firebase_storage.dart';

// Firestore — قاعدة البيانات NoSQL
final FirebaseFirestore db = FirebaseFirestore.instance;

// المصادقة
final FirebaseAuth auth = FirebaseAuth.instance;

// Cloud Storage (رفع الملفات)
final FirebaseStorage storage = FirebaseStorage.instance;

// مثال: كتابة مستند إلى Firestore
Future<void> saveUser(String uid, String name) async {
  await db.collection('users').doc(uid).set({
    'name': name,
    'createdAt': FieldValue.serverTimestamp(),
  });
}

الضبط الخاص بكل بيئة

التطبيقات في الإنتاج عادةً تستخدم مشاريع Firebase منفصلة للبيئتين — التطوير والإنتاج — لتفادي تلويث البيانات الحقيقية بعمليات كتابة الاختبار. شغّل flutterfire configure مرة لكل بيئة واحفظ كل firebase_options.dart المولَّد باسم ملف مختلف، ثم اختر الصحيح منهم عبر تعريف Dart في وقت البناء:

اختيار الضبط عبر --dart-define

# البناء للإنتاج
flutter run --dart-define=FLAVOR=production

# في lib/firebase_options_loader.dart:
import 'firebase_options_dev.dart' as dev;
import 'firebase_options_prod.dart' as prod;

const String _flavor =
    String.fromEnvironment('FLAVOR', defaultValue: 'dev');

FirebaseOptions get currentPlatformOptions {
  return _flavor == 'production'
      ? prod.DefaultFirebaseOptions.currentPlatform
      : dev.DefaultFirebaseOptions.currentPlatform;
}

ملخص

لقد قمت بتوصيل مشروع Flutter الرئيسي الخاص بك بـ Firebase من البداية إلى النهاية. الخطوات الرئيسية هي: إنشاء مشروع Firebase وتفعيل الخدمات في وحدة التحكم، وتثبيت FlutterFire CLI وتشغيل flutterfire configure لتوليد ملفات ضبط المنصة، واستدعاء Firebase.initializeApp() قبل runApp()، وتطبيق إضافة Gradle لخدمات Google لـ Android، وتشغيل pod install لـ iOS. تضمن DefaultFirebaseOptions.currentPlatform المولَّدة استخدام المفاتيح الصحيحة على كل منصة دون أي منطق شرطي يدوي في كود Dart الخاص بك.