# Production-Grade Subject Management System Design
**(Bangla + English Mixed Explanation)**

This document outlines the architectural design for a robust Subject Configuration System that solves the "Single vs Two Paper" complexity and ensures future-proof data integrity.

---

## 1. Database Entities & Data Model (Recommended)

আমরা **JSON Config** এর বদলে **Relational Table (`subject_papers`)** ব্যবহার করার Strongly Recommend করছি। কারণ:
1.  **Unique Code Enforcement**: Database level-এ `unique` index ব্যবহার করে paper code duplication আটকানো সহজ (যা JSON-এ অসম্ভব)।
2.  **Reporting**: "সব Practical course এর list দাও" - এই ধরণের Query SQL দিয়ে সহজে করা যায়।

### A. Subject Master Table (`subjects`)
*Stable Identity of the Subject (Parent).*
*   `id` (PK)
*   `name` (String, Unique) → e.g., "Physics", "Bangla" (No "1st Paper" text here).
*   `short_name` (String) → e.g., "PHY", "BAN".
*   `has_multiple_papers` (Boolean) → `true` for Physics, `false` for ICT.
*   `is_4th_subject_eligible` (Boolean) → Flag to show this in 4th subject dropdown buckets.
*   `status` (Enum: active/archived).
*   *Note: No `group` or `marks` columns here.*

### B. Subject Papers Table (`subject_papers`)
*Physical Papers linked to the Master Subject.*
*   `id` (PK)
*   `subject_id` (FK to subjects)
*   `paper_type` (Enum: `single`, `first`, `second`)
*   `paper_code` (String, Unique Index) → The critical Board Code (e.g., 101, 102).
*   `name_suffix` (String, Nullable) → "1st Paper", "2nd Paper", or NULL.
*   `has_cq` (Boolean) → Default true.
*   `has_mcq` (Boolean) → Default true.
*   `has_practical` (Boolean) → Default false.
*   `full_marks` (Integer) → Default 100 (Acts as default blueprint).

---

## 2. Admin UX (Subject Add Form Behavior)

Admin Panel-এ "Add Subject" ফর্মটি ধাপে ধাপে কাজ করবে (Interactive UI):

**Step 1: Basic Info**
*   **Subject Name**: Admin type করবে "Physics".
*   **Paper Configuration**: Radio Button [ Single Paper (1 Code) ] / [ Two Papers (2 Codes) ].

**Step 2: Paper Code Logic**
*   **Scenario A (Single Paper Selected)**:
    *   Input: `Paper Code` (e.g., 275).
    *   System checks uniqueness immediately via AJAX.
    *   Toggles: `CQ`, `MCQ`, `Practical`.
*   **Scenario B (Two Papers Selected)**:
    *   Input: `1st Paper Code` (e.g., 174).
    *   **Auto-Suggest**: 1st Code টাইপ করার সাথে সাথে System `2nd Paper Code` ফিল্ডে `175` (174 + 1) বসিয়ে দেবে।
    *   **Hint Text**: "Next available code based on pattern".
    *   **Conflict Check**: যদি `175` অলরেডি "Chemistry" এর জন্য ব্যবহার হয়ে থাকে, তবে Field টি Red Border দেখাবে এবং Warning দেবে: *"Code 175 is taken! Please choose another."*
    *   Toggles: আলাদাভাবে 1st Paper এবং 2nd Paper এর জন্য `Practical/MCQ` অন/অফ করা যাবে। (যেমন: Math-এ Practical আছে, English-এ নেই)।

**Step 3: Future Proofing**
*   **No Group Selection**: ফর্মটিতে "Group" (Science/Arts) সিলেক্ট করার অপশন থাকবে না।
*   **Note**: সেভ করার পর User-কে `Subject Configuration` পেজে নিয়ে যাওয়া হবে, যেখানে সে `Academic Version` অনুযায়ী Subject-কে Group-এ ম্যাপ করবে।

---

## 3. Code Generation Strategy (2nd Paper)

Auto-suggestion logic for **Production Environment**:

1.  **Numeric Pattern**:
    *   Admin enters `101`.
    *   Logic: `101` is numeric? Yes. -> Suggest `102`.
    *    DB Check: `SELECT count(*) FROM subject_papers WHERE paper_code = 102`.
    *   If `count > 0` (Code Taken):
        *   Don't auto-fill. Show Warning: "102 is busy. Enter manually."
    *   If `count == 0` (Available):
        *   Auto-fill `102`.

2.  **String Pattern** (Rare but possible):
    *   Admin enters `PHY-A`.
    *   Logic: Ends with char? Increment char? (`PHY-B`).
    *   Usually hard to predict. Keep manual override open.

---

## 4. Validation Rules (Strict)

*   **Subject Name**: Must be unique in `subjects` table (Case insensitive).
    *   Invalid: "Physics 1st Paper" (Wrong naming convention).
    *   Valid: "Physics".
*   **Paper Type**: Required (Single or Two).
*   **Paper Codes**:
    *   `paper_code` MUST be unique across the entire system.
    *   Two subjects cannot share code `101`.
*   **Consistency**:
    *   If `has_multiple_papers = true`, then Exactly 2 rows must be created in `subject_papers`.
    *   If Practical is enabled (`has_practical = true`), ensure Blueprint allows Marks entry for Practical later.
*   **Soft Deletes**:
    *   Codes of soft-deleted subjects **cannot** be reused immediately (to prevent data corruption in archived results).
    *   Admin must "Permanently Delete" or "Restore" old subject to reuse code.

---

## 5. Integration with Result & Marks System

This structure connects seamlessly with the Marks Entry System:

1.  **Subject Blueprints (`subject_blueprints`) Integration**:
    *   Marks Distribution (Total 100 vs 75) নির্দিষ্ট `Academic Version` এর সাথে `Subject Master` কে লিঙ্ক করবে।
    *   কিন্তু `CQ/MCQ` On/Off flag টি `subject_papers` টেবিল থেকে Default হিসেবে আসবে।

2.  **Exam Snapshot (`exam_subjects`)**:
    *   পরীক্ষার সময় `subject_papers` টেবিলের `has_mcq` বা `has_cq` সেটিংস `exam_routines` বা result टेবিলে Snapshot হিসেবে রাখা ভালো।
    *   কারণ: ২০২৪ সালে ICT-তে Practical ছিল না, কিন্তু ২০২৫-এ যোগ হতে পারে। Master Data update করলেও পুরনো রেজাল্ট ভাঙবে না।

3.  **Marks Entry UI**:
    *   Teacher যখন মার্কস এন্ট্রি করবেন, তিনি `subject_papers` টেবিল থেকে পেপারগুলোর নাম দেখবেন ("Physics 1st Paper", "Physics 2nd Paper")।
    *   সিস্টেম অটোমেটিক বুঝবে Physics এর জন্য ২টি কলাম (1st, 2nd) জেনারেট করতে হবে মার্কশিটে।

---

**Summary:**
এই আর্কিটেকচারটি ফলো করলে আপনার সিস্টেমটি হবে **Flexible** (Subject reuse across groups), **Secure** (Unique Codes), এবং **User Friendly** (Auto-suggest codes).
