Step 1
الفصل الثاني: مراجعة سريعة للدرس الأول وإعداد بيئة العمل
مرحبًا بك مرة أخرى. في هذا الفصل، سنقوم بجسر الفجوة بين المفاهيم النظرية التي ناقشناها في الفصل الأول والتنفيذ العملي. سنبدأ بمراجعة مركزة للأسس، ثم ننتقل مباشرة إلى إعداد بيئة تطوير احترافية ومحكمة، مصممة خصيصًا لمشروع Node.js متصل بـ Supabase. التركيز هنا على "لماذا" نختار أدوات معينة و"كيف" نُهيئها لتدفق عمل قوي وقابل للتطوير.
مراجعة معمقة: هندسة التطبيق والاختيارات الاستراتيجية
في الفصل الأول، حددنا معمارية التطبيق: خادم Node.js (Express) يعمل كطبقة منطق أعمال وسيطة بين واجهة المستخدم وقاعدة بيانات Supabase. دعنا نتعمق في سبب كون هذا النموذج قويًا:
- فصل المسؤوليات (Separation of Concerns): يتحكم خادمك في جميع قواعد العمل والمنطق، مما يمنحك نقطة تحكم واحدة. هذا يمنع الواجهة الأمامية من التواصل مباشرة مع قاعدة البيانات، مما يعزز الأمان ويوحد منطق الأعمال.
- المرونة الأمنية: يمكنك استخدام Row Level Security (RLS) في Supabase كخط دفاع أخير، بينما تتحكم في الصلاحيات والتحقق من الهوية بشكل مركزي في خادم Node.js. هذا النمط (التحقق المزدوج) هو معيار في التطبيقات ذات الحساسية العالية.
- إخفاء التعقيد: يمكن لخادمك تجميع استعلامات متعددة إلى Supabase، أو دمج بيانات من مصادر خارجية، قبل إرجاع استجابة موحدة للعميل. الواجهة الأمامية لا تحتاج لمعرفة هذه التعقيدات.
supabase-js للاستخدام مباشرة من المتصفح. اختيارنا لمسار الخادم الوسيط ليس بسبب قصور في Supabase، بل هو قرار معماري لبناء تطبيقات أكثر تعقيدًا وقابلية للصيانة وأمانًا، حيث يكون منطق العمل حاسمًا ولا يجب تعريضه في الواجهة الأمامية.
إعداد بيئة العمل الاحترافية: الأدوات والهيكلة
سنستخدم الأدوات التالية لضبط بيئة تطوير قادرة على مواكبة مشروع احترافي. التركيز على أدوات تزيد الإنتاجية وتضمن الجودة.
1. تهيئة مشروع Node.js مع إدارة الإصدارات
ابدأ بإنشاء دليل للمشروع وتهيئة package.json. نوصي باستخدام pnpm أو npm مع Node.js LTS (الإصدار 18 أو أعلى).
# إنشاء الدليل والانتقال إليه
mkdir node-supabase-server
cd node-supabase-server
# تهيئة مشروع Node.js (استخدم -y لتخطي الأسئلة أو أزلْها للإعداد اليدوي)
npm init -y
# تهيئة مستودع Git (إلزامي للعمل الاحترافي)
git init
package.json يدويًا بعد التهيئة. عيّن "type": "module" لاستخدام وحدات ES6 (import/export) بدلاً من CommonJS. هذا هو الاتجاه الحديث ويوفر توافقًا أفضل مع العديد من الحزم. أيضًا، أضف حقلي "engines" و "scripts" كما سنرى لاحقًا.
2. تثبيت الاعتماديات الأساسية والتطويرية
سنقسم الحزم إلى اعتماديات تشغيلية (dependencies) واعتماديات تطويرية (devDependencies). هذا الفصل حاسم لإدارة الحزم ونشر التطبيق.
# الاعتماديات الأساسية للتشغيل
npm install express dotenv cors
npm install @supabase/supabase-js
# الاعتماديات التطويرية (للتطوير والبناء فقط)
npm install -D nodemon eslint prettier
دعنا نشرح الاختيارات:
- express: إطار العمل الخفيف والقوي لبناء واجهات برمجة التطبيقات (APIs).
- dotenv: لتحميل متغيرات البيئة من ملف
.env. ضروري مطلقًا لإخفاء مفاتيح Supabase الحساسة. - cors: لتكوين سياسة مشاركة الموارد بين المصادر (CORS) للسماح لطلبات الواجهة الأمامية من نطاق معين.
- @supabase/supabase-js: المكتبة الرسمية للعميل على الخادم للتواصل مع Supabase.
- nodemon: لإعادة تشغيل الخادم تلقائيًا عند حفظ التغييرات في الكود.
- eslint & prettier: لفرض جودة الكود وتنسيقه بشكل ثابت عبر الفريق.
.env أبدًا إلى Git. تأكد من إضافته إلى .gitignore فورًا. قم بتعريف جميع المتغيرات المطلوبة في ملف .env.example (بدون قيمها الفعلية) وارفع هذا الملف بدلاً من ذلك كدليل لفريقك.
3. هيكلة الدلائل والملفات الأساسية
الهيكلة المنظمة هي ما يفصل بين المشروع العشوائي والتطبيق القابل للصيانة. إليك الهيكل الأولي الذي نوصي به:
node-supabase-server/
├── src/
│ ├── config/ # لتكوين Supabase، قاعدة البيانات، etc.
│ ├── index.js # نقطة الدخول الرئيسية (يدير بدء التشغيل)
│ └── app.js # تعريف تطبيق Express وتكوين الوسائط (middleware)
├── .env # متغيرات البيئة (مخفية في .gitignore)
├── .env.example # قالب لمتغيرات البيئة المطلوبة
├── .gitignore
├── package.json
└── package-lock.json
4. تكوين Supabase العميل على الخادم
هذه هي الخطوة الأهم للربط. سننشئ عميل Supabase باستخدام مفاتيح المشروع الخاصة (Service Role Key أو Anonymous Key). تحذير: استخدام مفتاح "Service Role" يمنح صلاحيات كاملة، لذا يجب أن يقتصر استخدامه على الخادم الموثوق به فقط.
أولاً، أنشئ ملف src/config/supabaseClient.js:
// استيراد المكتبة وإنشاء العميل
import { createClient } from '@supabase/s
Loading ratings...