طَبِّقْهاتعلّم المبدأ، وطبّقه بيدكمقرر 302 · من الفكرة إلى المنتج (٢): نظام حجز مواعيد
الدرس 2 · الوحدة 1: الفكرة والتخطيط والتصميم

المحطّة ٢: تصميم الواجهة البرمجية (API) ونموذج البيانات

العقد قبل البناء: نموذج البيانات والمسارات ورموز الحالة. ⏱ نحو 24 دقيقة.

بعد هذا الدرس ستستطيع أن:
  • تصمّم نموذج بياناتٍ يعبّر عن حالة الموارد.
  • تشتقّ مسارات REST من قصص المستخدم بطرقٍ ورموزٍ صحيحة.
  • توحّد شكل الردود والأخطاء.
  • تبني «عقدًا» يفصل الواجهة عن الخادم.

١الـ API عقدٌ بين طبقتين

مشروعنا طبقتان: واجهة React وخادم Express. بينهما عقدٌ هو الـ API: مجموعة مساراتٍ متّفقٌ عليها، كلٌّ له طريقةٌ (GET/POST…) ومدخلٌ وشكل ردّ. نصمّم هذا العقد قبل كتابة أيّ طبقة، فتُبنيان بالتوازي دون أن تنتظر إحداهما الأخرى — كما تعلّمت في مقرّر 242.

الـ API الجيّد يجعل الواجهة والخادم مستقلّين: لو غيّرت شكل الواجهة لاحقًا لن يتأثّر الخادم، والعكس، ما دام العقد ثابتًا.

٢نموذج البيانات: ما شكل «الموعد»؟

كل موعدٍ كائنٌ بسيط. الحقل المفتاح هو bookedBy: فارغٌ (null) يعني «متاح»، وغير فارغٍ يعني «محجوز» لمن فيه:

// نموذج البيانات: موعد (Appointment){  "id": 1,  "doctor": "د. منى",  "time": "2026-10-25 09:00",  "bookedBy": null        // null = متاح، أو اسم المريض الذي حجزه}

بهذا الحقل وحده نفرّق المتاح من المحجوز، ونمنع الحجز المزدوج: لا نحجز إلّا إذا كان bookedBy === null.

٣تصميم المسارات (Endpoints)

نشتقّ المسارات من قصص المستخدم. المورد جمعٌ (appointments)، والطريقة هي الفعل، ورمز الحالة يصف النتيجة — كلّها من مقرّر 242:

الطريقة والمساريفعلالنجاحالفشل
GET /api/appointmentsكل المواعيد (?status=free للمتاح)200—
POST /api/appointments/:id/bookيحجز موعدًا متاحًا200404 غير موجود · 409 محجوز · 422 بلا اسم
POST /api/appointments/:id/cancelيلغي حجزًا200404
POST /api/loginيسجّل الدخول ويعيد رمزًا200401

مثالٌ على العقد — طلبٌ وردّ لحجزٍ ناجح:

طلب HTTP · من المتصفح إلى الخادم
POST /api/appointments/1/book HTTP/1.1
Content-Type: application/json
 
{"patient": "سعود"}
استجابة HTTP · من الخادم إلى المتصفح
HTTP/1.1 200 OK
Content-Type: application/json
 
{"data": {"id": 1, "doctor": "د. منى", "bookedBy": "سعود"}}

٤شكلٌ موحّدٌ للردود والأخطاء

نثبّت غلافًا واحدًا لكل الردود يسهّل على الواجهة التعامل معها (كما في 242):

توقّع وتحقّق

أيّ مسارٍ يتبع تصميم REST؟

موردٌ جمعٌ + طريقة.

ما رمز الحالة لمحاولة حجز موعدٍ محجوزٍ أصلًا؟

تعارض.

كيف نميّز الموعد المتاح في نموذجنا؟

ما فائدة توحيد شكل الرد {data}/{error}؟

الخلاصة

تحدٍّ تصميمي: عقد الـ API لنظام الحجز

تصميمي

صمّم الواجهة البرمجية لمشروعك: نموذج البيانات، وجدول المسارات بطرقها ورموز حالتها، وشكلٌ موحّدٌ للردود والأخطاء. سنُنفّذ هذا العقد في المحطّات القادمة.

المطلوب:
  • نموذج بيانات «الموعد» بحقوله.
  • جدول مساراتٍ يغطّي كل قصص المحطّة 1.
  • رمز حالةٍ مناسبٌ لكل نتيجة (نجاح وفشل).
  • شكلٌ موحّدٌ للردّ الناجح وللخطأ.
☑ راجع عملك قبل التسليم:
💡 تلميح 1
اشتقّ المسارات من الأفعال في القصص: «يرى» ← GET، «يحجز/يلغي» ← POST.
💡 تلميح 2
لكل مسارٍ اسأل: ما رمز النجاح؟ وما كل أنواع الفشل ورموزها؟

🐞 لاحظت خطأً في هذا الدرس؟ أبلغني بالبريد

📝 معلم؟ أرسل ملاحظة للمؤلف عن هذا الدرس