المدونةنُشر في
باكند واحد للتطبيق واللوحة
عميل Flutter (أو Swift) ولوحة React على مشروع Supabase واحد. دخول، وقوانين صف، وتخزين. قاعدة ثانية للوحة خطأ.

منتج جوال يحتاج إليه من يشغّله — وليس تطبيقًا ثم لوحة. هو باكند Supabase واحد مع عميلين. الجوال Flutter، أو Swift إذا كان المنتج لـ Apple. والمكتب React. نفس المشروع.
مقالة اللوحة هي اللوحة التي تشغّل منها. وهذه المقالة عن البيانات. نفس المثلث. شغل آخر.
مشروع واحد، وعميلين
باكند تطبيق الجوال عندنا يعني قاعدة Postgres واحدة، ودخول واحد، وتخزين واحد. مو API للجوال وقاعدة ثانية للوحة. العميلين يستخدمون المفتاح العام وتوكن المستخدم. القاعدة تتصمم مرة.
Flutter هو جوالنا الافتراضي. Swift يكلّم نفس المشروع إذا المنتج حق Apple. اللوحة React في الحالتين. ما في مزامنة. في صف واحد.
قاعدة ثانية للوحة خطأ
مصدرين للحقيقة. «العرض نازل؟» تتحوّل إلى وظيفة مزامنة. انحراف. كتابة مرتين. تسوية ليلية لم يطلبها أحد. التاجر ينشر؛ والمتسوق يجب أن يرى هذا الصف. العيادة تثبّت؛ والمريض يجب أن يرى هذا الصف.
إذا أردت لاحقًا نسخة للتقارير، فهذه نسخة. ليست قاعدة منتج ثانية. اللوحة وجه ثانٍ على نفس البيانات، لا منتج ثانٍ.
المفتاح العام مكانه التطبيق
في 2026 يسمّي Supabase المفاتيح publishable و secret. الأسماء القديمة، anon و service_role، ما زالت تعمل ولم تُعطَّل بعد. التوثيق يقول إنها ستتوقف نهاية 2026. نستخدم الأسماء الحالية.
Flutter يُجهَّز برابط ومفتاح publishableKey. موقفهم الرسمي: هذا الزوج يكون في التطبيق، وهذا مقبول إذا كانت قوانين الصف تعمل. ولا يقرأ الجوال ملف .env سحريًا وقت التشغيل. المفاتيح تُدرج وقت البناء، ولا تُرفع إلى المستودع. جملة واحدة تكفي. هذي ليست درسًا في الإعداد.
المفتاح السرّي هو service_role القديم باسم جديد. وصول كامل. يتجاوز قوانين الصف. مكانه سيرفر تثق فيه أو Edge Function. ليس في IPA، ولا في AAB، ولا في حزمة React، ولا في لقطات الشاشة، ولا في السجلات. سرّ يُستخدم في المتصفح يرجع 401. وهذا لا يجعل السر المسرَّب آمنًا.
قوانين الصف هي البوابة
إخفاء زر في Flutter أو React ليس حماية. من معه المفتاح العام يستطيع استدعاء الـ API. أي جدول في مخطط مكشوف دون RLS يُقرأ ويُكتب بهذا المفتاح. محرّر الجداول يُفعّل RLS افتراضيًا. أما SQL الخام فلا.
Postgres يفحص الصلاحيات أولًا: هل يستطيع هذا الدور تنفيذ الفعل؟ ثم القوانين: أي صفوف؟ الجداول الجديدة في public تمنح أصلًا anon و authenticated و service_role صلاحيات القراءة والكتابة والتعديل والحذف. تضيف قوانين، فالصلاحيات لا تُسحب. وتشغّل RLS دون قوانين، فيرجع الـ API صفر صفوف على المفتاح العام. هذا هو الإغلاق الافتراضي. وليس منتجًا مكتملًا.
مفتاح الخدمة إذا اقترن بتوكن مستخدم يعمل كالمستخدم، لا كتجاوز. القانون الخاطئ يفشل بهدوء: القانون المفتوح أكثر من اللازم يرجع صفوفًا زائدة، والضيّق أكثر من اللازم يرجع ولا شيء دون أن يُظهر خطأ. والتعديل يحتاج قانون قراءة يطابقه. استشهد بالتوثيق، وقف. ما بنكتب كتاب قوانين.
الأدوار في app_metadata أو جدول عضوية
user_metadata يعدّله المستخدم. لا تضع صلاحية هناك. app_metadata لا يعدّله المستخدم. الأدوار والعلامات التي لا ينبغي تغييرها تكون هناك، أو في جدول عضوية.
التوكن ليس دائمًا حديثًا. يتغيّر app_metadata، لكن التوكن القديم يحمل الادعاءات القديمة حتى يتجدّد. أدوار منتج واحد — متسوق مقابل موظف تاجر — يمكن أن تكون في ادعاءات السيرفر. أما الجهات — عيادات كثيرة، وتجار كثيرون — فتحتاج جدول عضوية ومفتاح جهة. وهذا الفصل في مقالة الجهات. صاحب المنصة ومدير العيادة ليسا بنفس الدخول. إخفاء المسار ليس قانونًا.
صف واحد، ووجهين
T-CODE منتج واحد. التاجر يكتب عرضًا وفرعًا. المتسوق يقرأ العرض على الخريطة. تظهر فرعًا أو تخفيه، وتقفل الأكواد، وتسترد. نفس الصف، ووجهان. سعودي. ما ندّعي ستاكًا.
Naqrah.app موعد واحد. العيادة تنظّم يومها. المريض يحجز ويعدّل ويلغي. 100 نقطة = 1 ريال عُماني — منشور. عُمان. نفس الصف، ووجهان. نفس القوانين على التوكنين. والوجه الثاني عضوية، لا جدول ثانٍ.
CareerFolio: القانون في البيانات، على الويب
CareerFolio ويب. هذا ويب. سنة الأداء إذا انتهت تصبح أرشيفًا للقراءة فقط. والمراجع يأخذ رابطًا آمنًا للقراءة. هذه حالة على الصف وقانون، لا زرًّا معطّلًا. وصفحة الشغل أصلًا تسمّي Supabase وقوانين الصف. دليل على أن البوابة في Postgres حتى لو لم يوجد جوال.
التخزين نفس المشروع
صور عروض، وشعارات عيادات، ومرفقات ملفات: نفس المشروع، وقوانين على storage.objects. مزوّد تخزين ثانٍ للوحة هو نفس خطأ القاعدة الثانية. نذكره ثم نتوقف. ما سنشرح رفع الملفات.
القاعدة أولًا، ثم العميلان. والدخول للعميل عند التسليم. وإذا كانت اللوحة لاحقًا «Firebase بعدين»، فالمنتج لم يتحدد. اكتب لنا بالصفوف، لا بالشاشات فقط.