# מערך שיעור: CRUD בסיסי — Minimal APIs📋 מערך מרצה

משך: 2 שעות אקדמיות (90 דקות).

מטרת השיעור: הסטודנטים ידעו לכתוב CRUD בסיסי (Minimal API) שממשי את ה-Methods וה-Status Codes שנלמדו בשיעור הקודם.

בסוף השיעור הסטודנטים צריכים: לכתוב את ארבעת ה-endpoints הבסיסיים (GET/POST/PUT/DELETE) עם `Results.X()` הנכון לכל אחד, ולהסביר את ההבדל בין Route Parameter, Query String ו-Body — ומתי משתמשים בכל אחד.

דגש קריטי: זהו שיעור-גשר — לא מושגים חדשים ברמת תיאוריה, אלא הפיכת מה שכבר נלמד (Methods/Status Codes) לקוד. אל תיתנו לזה להרגיש כמו "עוד שיעור תיאוריה" — הדגש הוא על כתיבה וריצה בפועל.

---

## מהלך השיעור

| חלק בשיעור | משך | הערות ודגשים |
| --- | --- | --- |
| פתיחה וחיבור | 5 דקות | הזכירו: "למדנו מה זה GET/POST/404/201 — אבל עדיין לא כתבנו קוד שמגיב". |
| שלב 1: GET לכל הרשימה | 10 דקות | `MapGet` הכי פשוט — בלי שום פרמטר |
| שלב 2: GET משאב בודד — Route Parameter | 15 דקות | `{id}` נקשר אוטומטית ל-`int id` — הצצה ל-Model Binding; `Results.Ok`/`NotFound`, קשרו ל-200/404 |
| שלב 3: סינון — Query String | 15 דקות | `int? minAge` — הדגישו את ה-Nullable ואת ההבדל מ-Route Parameter: מזהה משאב יחיד מול סינון רשימה |
| שלב 4: POST — Body | 10 דקות | `Results.Created` — קשרו ל-201 ול-Location header |
| שלב 5-6: PUT/DELETE — Route+Body יחד, ו-Route בלבד | 15 דקות | `Results.NoContent` — קשרו ל-204 |
| מה עדיין חסר (Controllers/DAL) | 5 דקות | פתיחת התיאבון לשני השיעורים הבאים, בלי לצלול לפרטים |
| תרגול מודרך | 10 דקות | תרגיל 1+2 + פתיחת הפרויקט המסכם (Tasks API עם endpoint חיפוש) |

---

## דגשים להעברת השיעור

- זהו שיעור "תרגום" — כל endpoint שנכתב צריך להיקשר במפורש למשהו שכבר נלמד ("זוכרים ש-404 זה 'לא נמצא'? זה בדיוק `Results.NotFound()`"). אל תציגו את זה כחומר חדש.
- הפרויקט המסכם כאן הוא בדיוק ההמשך של הפרויקט שתוכנן על נייר בשיעור הקודם — הדגישו את הרצף: תכנון (שיעור קודם) → קוד עובד (כאן) → Controller מסודר (שיעור הבא) → DAL אמיתי (בהמשך היחידה).
- הזהירו במפורש: In-Memory Store הוא לצורך הדוגמה בלבד. סטודנטים לפעמים מבינים בטעות שזה "מספיק טוב" — הבהירו שזה ייעלם בכל restart, וזה בדיוק מה ש-DAL Pattern בהמשך פותר.
- ה-Query String הוא לרוב הנקודה הכי מבלבלת בשיעור — סטודנטים נוטים לנסות "לדחוף" סינון לתוך Route Parameter (`/api/students/{minAge}`). חזרו על הכלל בקול: "אם זה מזהה משאב ספציפי — Route. אם זה מסנן רשימה — Query String."

---

## מושגים

**CRUD** — Create, Read, Update, Delete.
**Endpoint** — Method+URL שממופה לקוד מטפל.
**Route Parameter** — חלק משתנה ב-URL שמזהה משאב ספציפי, נקשר אוטומטית לפרמטר בקוד.
**Query String Parameter** — מידע אופציונלי אחרי `?` לסינון/מיון של רשימה.
**Body** — תוכן הבקשה בפורמט JSON, לאובייקט שלם (יצירה/עדכון).
**In-Memory Store** — רשימה בזיכרון, לא שורדת restart.

---

## תרגיל חשיבה

**שאלת פתיחה:** "אם נריץ `POST /api/students` פעמיים עם אותו Body בדיוק, מה יקרה? האם זו התנהגות רצויה?"

**מהלך:** הובילו את הסטודנטים לראות שבקוד הבסיסי הזה, שני תלמידים זהים ייווצרו עם אותו ID (או ID מתנגש) — כי אין שום בדיקת ולידציה או ייחודיות. זו בדיוק הבעיה שה-Validation (שיעור בהמשך היחידה) פותר — לא עכשיו, אבל שווה לזרוע את השאלה כבר כאן.

**מה המרצה מראה בסוף:** הריצו `POST` פעמיים ברצף עם Postman/curl, והראו את התוצאה (שני רשומות עם אותו תוכן, בלי שגיאה). הניגוד בין "זה עובד" לבין "זה לא באמת נכון" מכין קרקע טובה להמשך היחידה.
