Keyboard shortcuts

Press or to navigate between chapters

Press S or / to search in the book

Press ? to show this help

Press Esc to hide this help

04 — Information Architecture (Bulk Module)

Navigation, hierarchy, and the data contract that screens expose. Global IA in 00-shared/05; components in 00-shared/03. Sources: bulk module source files, students adapter, users/students services.


1. Placement in the global IA

Org Admin / Dashboard
└── People (or Admin section per module)
    ├── Users / Students list   (module surfaces)
    └── Import & Export  ────►  Bulk hub (SS1)   ← this module
        ├── SS2 Preview
        ├── SS3 Confirm
        ├── SS4 Result / Error review
        └── SS5 Export
  • Entry: one top-level "Import / Export" destination, not buried per-entity; entity choice is the first decision inside the flow (only students today, students-import.adapter.ts:15).
  • Exit: SS4 → Students list, SS5 → file download.

2. Sitemap (screens)

#ScreenRoute (forward-looking)Purpose
SS1Bulk Home / Upload/admin/bulkentity picker + file picker + template hint
SS2CSV Preview/admin/bulk/previewheader map, sample rows, contract warnings
SS3Confirm/admin/bulk/confirmrisk summary + go/no-go
SS4Result & Error Review/admin/bulk/resultreport rendering + error table
SS5Export/admin/bulk/exportentity selector + download

3. Entity taxonomy (backend-constrained)

  • entity path param is a free string; only students resolves (bulk-import.service.ts:17-20). Everything else → 404.
  • (planned) entities per IMPLEMENTATION_PLAN.md:172: fees, library, exams (and teachers, by symmetry). Until discovery exists, the client ships a hard-coded entity list ['students'].

4. Import flow state machine (summary; full in 13)

upload → preview → confirm → importing (in-flight) → done { success | partial | failed }
                                                ↘ review errors → fix → re-upload

5. The report as an information object

ImportReport (import-adapter.interface.ts:14-25) is the single source of truth for SS4:

FieldTypeMeaning
entitystringechoed entity slug
totalRowsnumberdata rows parsed (header excluded; bulk-import.service.ts:45-46)
importednumberrows whose create succeeded
failednumberrows rejected by validate OR create (:48-62)
errors{rowNumber, errors[]}[]one entry per failed row; rowNumber is the physical CSV line (header = 1)

Invariant: imported + failed === totalRows (every row is either counted or errored — :45-63). The UI can assert this to detect client/server drift.

6. Export shape ≠ import shape (flagged)

Import columns (students-import.adapter.ts:17-26)Export columns (:92-97)
firstName, lastName, email, admissionNumber, grade, section, academicYear, rollNumberadmissionNumber, rollNumber, status, admissionDate
  • Export = roster snapshot (status, admissionDate are system-owned; admissionDate is ISO string, :96).
  • Import = onboarding payload. Never present Export as "the template"; template is a client-side concern (forward-looking).

7. Error string taxonomy (SS4 grouping)

GroupStrings (exact, 08 §2)Where thrown
Missing / invalid fieldMissing required column "X"., Invalid email format.students-import.adapter.ts:43,47
DuplicateAdmission number "X" already exists., Email "X" already registered.:54,56
Reference not foundAcademic year "X" not found., Grade "X" not found., Section "X" not found., No class found for grade "X" section "Y".:117,121,125,140
Create-timearbitrary thrown message (e.g. duplicate-key race)bulk-import.service.ts:57-62

8. Navigation rules

  • SS2 → SS3 disabled when contract warnings are blocking (08 §1).
  • SS4 error rows link back to the source file's line number; "re-upload corrected file" returns to SS2 with the failed rows pre-highlighted by row number.
  • Breadcrumb: Bulk → Import → Preview → Confirm → Result.