# MISSING-SCREENS-INVENTORY.md

> **Verified accurate:** 2026-05-02 — every endpoint citation grep-matches `docs/handoff/routes-api.php` and/or `docs/openapi/openapi.yaml` (per the doc's own provenance note); §A footnote keeps live the rationale for excluding HR rows that turned out to be wired.
> **Status:** active source-of-truth doc; the backlog Cursor pulls from to close the FE/BE coverage gap before pilot.

> **Companion to:** `SCREENS-INVENTORY-*.md` (7 files). Where those documents catalogue what **exists**, this one catalogues what is **backend-ready but has no frontend yet** — i.e. screens Cursor needs to build to close the FE/BE coverage gap before pilot.
>
> **Verified against:** `docs/handoff/routes-api.php` (the canonical Laravel routes excerpt) + `docs/openapi/openapi.yaml` (full surface). Every endpoint citation has been grep-matched against one or both.
>
> **Owner+HR baseline:** uses `SCREENS-INVENTORY-Owner+HR.md` as the authoritative starting point for what HR already covers; HR rows that look like gaps but turn out to be wired (e.g. `hr.leave`, `hr.payroll`) are dropped to the §A footnote.

---

## §0 — Reading Guide

### How this complements `SCREENS-INVENTORY-*.md`

| Document | Question it answers |
|---|---|
| `SCREENS-INVENTORY-{Retail,Pay,Dine,Accounting,Owner+HR,Platform,Common}.md` | "Given a screen the prototype renders, what does it call and what's its cut-over status?" |
| **This doc** | "Given a backend capability, is there *any* prototype surface for it — and if not, what should Cursor build?" |
| `FLOW-INVENTORY.md` + Addendum | "Given a multi-step flow (modal/wizard), is its UX shape correct vs. the spec?" |
| `USER-FLOWS.md` | "Given a tenant lifecycle phase, which screens compose the journey?" |

The four documents are deliberately non-overlapping — read this one **after** the existing inventories, because every "missing" claim here was derived by subtracting the existing inventories from the backend surface.

### Priority legend

| Tag | Meaning | Cut-over implication |
|---|---|---|
| 🚨 **V1.0 BLOCKER** | Pilot tenants cannot operate without this screen. Ship-stopper. | Build before pilot UAT. |
| ⚠️ **V1.0 HIGH** | Pilot tenants will hit this within first 30 days; absence forces support escalations or workarounds. | Build during pilot, before GA. |
| 📌 **V1.0 NICE** | Useful at GA, but tenants can survive without it (workarounds documented). | Build if calendar permits; otherwise queue for v1.1. |
| 🗓️ **V1.1** | Backend exists but feature is post-pilot per Mohammed's roadmap. | Defer; document UX placeholder if mentioned in Owner/HR sidebar. |

### Status marker semantics (heading suffixes)

The bracketed tag at the end of each `#### MS-*` heading describes provenance + cut-over state. Markers are additive — a screen built new in a batch and then wired in the same batch is `[BUILT · WIRED]`.

| Marker | Provenance | API state | What user actions do |
|---|---|---|---|
| `[ORIGINAL]` | Pre-existing screen from the prototype | No API layer — fixture-backed | Mutate `window.DALSEEN_OWNER.*` directly; lost on reload |
| `[ORIGINAL · WIRED]` | Pre-existing screen | API layer added in a later batch | All user actions persist via `API.*` — store-backed, audit-logged |
| `[ORIGINAL · LIVE-READ-ONLY]` | Pre-existing screen | API reads work; mutation UIs are stubs | Reads come from API store; action buttons are toast-only (deferred to v1.1) |
| `[NEW]` | Spec'd in this inventory but not yet built | n/a | n/a — see `Cursor build plan` per row |
| `[BUILT]` | Built new in a batch, fixture-only | No API layer | Mutate fixtures directly |
| `[BUILT · WIRED]` | Built new in a batch with full API integration | API layer present | All user actions persist via `API.*` |
| `[BUILT-PARTIAL]` | Built new in a batch but spec contains tabs/sections deferred to v1.1 | Mixed — some tabs API-wired, some `LIVE-READ-ONLY` | Per-tab basis — see screen heading for which tabs are mutating vs read-only |

A `✅ DELIVERED — Batch N` or `✅ WIRED — Batch N` suffix appears after the marker once the work has shipped. `⚠️ PARTIAL` flags rows that shipped less than the marker implies (e.g. live-read but no mutation UI).

---

### ✅ Batch 1 — DELIVERED

All 8 quick-win screens are now wired into the live prototype. They share new mock endpoints registered by `front/api/api-namespace-batch1.js` and follow the production-shaped namespaced API surface. Each is fully bilingual (EN/AR), permission-aware, and audit-logged.

| ID | Screen | Frontend file(s) | API namespace | State |
|---|---|---|---|---|
| MS-HR-011 | ESS wiring | `front/owner/hr-ess-live.js` (live wrapper around existing `hr-ess.compiled.js`) | `API.me.ess()` · `API.me.requestLeave()` | ✅ live |
| MS-ACCT-007 | Customer write-off | `front/accounting/batch1-collect-spend.js` (drawer) + surgical edit in `accounting-collect.compiled.js` | `API.accounting.customerWriteOff(cid, body)` | ✅ live |
| MS-ONBOARD-002 | Company profile editor | `front/accounting/batch1-settings.js` (CompanyLiveTab) | `API.companies.get/update(id)` | ✅ live |
| MS-XCUT-007 | Fiscal calendar settings | `front/accounting/batch1-settings.js` (FiscalCalendarTab) | `API.fiscalCalendar.get/update()` · `API.fiscalPeriods.list/close/reopen()` | ✅ live |
| MS-NOTIF-002 | Notification preferences | `front/accounting/batch1-settings.js` (NotificationsTab) | `API.notifications.preferences.get/update()` | ✅ live |
| MS-ACCT-006 | Vendor debit note | `front/accounting/batch1-collect-spend.js` (drawer) + surgical edit in `accounting-spend.compiled.js` | `API.accounting.vendorDebitNotes.list/create()` | ✅ live |
| MS-RETAIL-005 | Inventory adjustments | `front/accounting/batch1-stock-adj.js` | `API.inventory.adjustments.list/create()` | ✅ live |
| MS-ACCT-011 | Tax codes management | `front/accounting/batch1-settings.js` (VatCodesTab) | `API.vatCodes.list/create/update/remove()` | ✅ live |

**Activation:** `index.html` loads `api-namespace-batch1.js` immediately after the base namespace, then loads each batch JS file at the appropriate position so the existing screens pick up the new components and drawers without forks.

---

### Effort legend (file-count + complexity, **not** time)

| Tag | Files (.compiled.js / .jsx) | UX complexity |
|---|---|---|
| **S** | 1 file, ≤ 200 LOC | Single list/table with one mutation. |
| **M** | 1–2 files, ≤ 500 LOC | List + detail drawer + 1 wizard step, OR a small builder. |
| **L** | 2–3 files, ≤ 1,000 LOC | Multi-tab screen, multi-step wizard, or list+detail+state-machine. |
| **XL** | 3+ files, > 1,000 LOC | New top-level module with 4+ sub-screens (e.g. an entire E-com module). |

### Provenance tag

Every entry is tagged **ORIGINAL** (named in the brief's starting list) or **NEW** (discovered while sweeping `routes-api.php`). The starting list had 36 candidates; final inventory is **49 missing screens** (38 ORIGINAL kept after consolidation, 11 NEW), per the user's expectation of 40–50.

### How to read each entry

Each `MS-{MODULE}-{NUMBER}` block follows the per-screen specification format from the prompt: priority/effort/type → backend capability → proposed design → file location → dependencies → related existing files → Cursor prompt template → notes.

### Verification rigor

- ✅ "Verified" = exact route or family found in `routes-api.php` or `openapi.yaml`.
- ⚠️ "Inferred" = endpoint not in the excerpted `routes-api.php` (which is a partial — see header), but referenced by name in `API-USAGE-MAP.md` or `BACKEND-MAPPING.md`. Cursor must regrep before relying.
- ❌ "Backend gap" = screen needs an endpoint that does not exist; cross-reference `MASTER-ACTION-PLAN` backend additions.

---

## §1 — Module-by-Module Missing Screens

### §1.1 Accounting Module — 8 missing screens (2 dropped, 1 NEW added)

#### MS-ACCT-001 · Cashflow Statement [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M
**Type:** New tab in `accounting-reports`

**Backend capability**
- Endpoints: `GET /accounting/reports/cashflow` (✅ verified — `ShowAccountingFinancialReportController` accepts a `report=cashflow` query param, sibling to `trial-balance`, `pl`, `bs`)
- Permissions: `accounting.reports.view`
- Data model: standard 3-section cashflow (Operating / Investing / Financing) with Direct or Indirect method toggle, period selector, comparative-period column

**Proposed design**

```
[Period: Q1 2026 ▾]  [Method: Indirect ▾]  [Compare: Q4 2025 ▾]    [Export PDF] [Export CSV]
─────────────────────────────────────────────────────────────────
OPERATING ACTIVITIES                          Q1 2026     Q4 2025
  Net income                                  +124,500    +98,200
  Adjustments:
    Depreciation                              +12,400     +12,400
    Changes in receivables                    -8,300      -2,100
    Changes in inventory                      +4,200      -15,600
    Changes in payables                       +6,800      +3,400
  ─────────────────────────────────────────  ────────    ────────
  Net cash from operating                    +139,600    +96,300

INVESTING ACTIVITIES                          ...
FINANCING ACTIVITIES                          ...
─────────────────────────────────────────────────────────────────
NET CHANGE IN CASH                           +X,XXX      +X,XXX
Cash, beginning of period                    +X,XXX      +X,XXX
Cash, end of period                          +X,XXX      +X,XXX
```

**Components needed**
- `<CashflowReport>` — top-level (mirrors `<PnlReport>` pattern in `accounting-reports.compiled.js`)
- `<ReportPeriodPicker>` (already exists — reuse from PL/BS tabs)
- `<ReportComparePicker>` (extract from PnlReport if not already shared)
- `<MethodToggle>` (new — Direct / Indirect)

**User actions**
- Switch period → re-fetch
- Switch method → re-fetch with `?method=direct|indirect`
- Drill on any line item → opens GL filter on the underlying account range
- Export PDF / CSV → `GET /accounting/reports/cashflow?format=pdf|csv`

**States**
- Empty: "No transactions in selected period."
- Loading: skeleton 3-section table.
- Error: "Cashflow could not be generated. Common cause: no closed periods." with a Reopen-period CTA gated by `accounting.periods.reopen`.
- Success: full report.

**File location**
- **Suggested:** add tab to `front/accounting/accounting-reports.compiled.js`, alongside TB/PL/BS.
- **Alternative:** if `accounting-reports` is already > 800 LOC, split into `accounting-reports-cashflow.compiled.js`.

**Dependencies**
- Requires: closed fiscal period exists for at least one prior period.
- Blocks: V1.0 GA — cashflow is a finance audit deliverable.

**Related existing files**
- Pattern to mirror: `accounting-reports.compiled.js` → `PnlReport`
- Components to reuse: `<ReportPeriodPicker>`, `<ReportRow>`, `<ReportTotal>` from same file.

**Cursor prompt template**
```
Build new tab: Cashflow Statement
File: add to front/accounting/accounting-reports.compiled.js
Pattern: mirror PnlReport in same file (period picker → server fetch → 3-section table)

Endpoints to consume (verified in routes/api.php):
- GET /accounting/reports/cashflow?period={id}&method={direct|indirect}&compare={id} (accounting.reports.view)
- GET /accounting/reports/cashflow?format=pdf (download)

Layout: period+method+compare picker row, 3 sections (Operating/Investing/Financing), totals at bottom, drill-to-GL on each row.
States to handle: empty, loading, error (with reopen-period CTA), success.

Test plan:
- No closed period → empty state with reopen CTA (visible only if user has accounting.periods.reopen)
- Indirect method shows adjustments rollup
- Drill on "Changes in receivables" navigates to GL with account filter applied
```

**Notes**
- Direct method requires line-by-line cash-flow categorization at posting time; if backend only supports Indirect today, hide the toggle and show a tooltip "Direct method requires categorized cashflow tags on every JE — coming v1.1."

---

#### MS-ACCT-002 · CoA Industry Profile Picker (Onboarding) [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** New step in onboarding wizard

**Backend capability**
- Endpoints (✅ all verified):
  - `GET /accounting/coa-profiles` — list 10 Saudi industry profiles (`IndexCoaTemplatesController`)
  - `GET /accounting/coa-profiles/{key}/preview` — show full CoA tree (`ShowCoaTemplatePreviewController`)
  - `POST /accounting/coa-profiles/{key}/instantiate` — seed the tenant's CoA from the chosen profile (`InstantiateTenantCoaProfileController`)
  - `POST /accounting/coa-profiles/compose` — merge multiple profiles (`ComposeTenantCoaProfilesController`)
- Permissions: `accounting.coa.manage`
- Data model: profiles include `RETAIL`, `RESTAURANT`, `SERVICES`, `MANUFACTURING`, `CONSTRUCTION`, `HEALTHCARE`, `EDUCATION`, `LOGISTICS`, `REAL_ESTATE`, `WHOLESALE`.

**Proposed design**

```
Step 4 of 7 · Set up your books

What kind of business is this?
We'll seed a Chart of Accounts tailored to your industry.

  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐
  │   🛒        │  │   🍽️        │  │   🛠️        │  │   🏭        │
  │   Retail    │  │  Restaurant │  │  Services   │  │ Manufacturing│
  │  142 accts  │  │  138 accts  │  │  118 accts  │  │  165 accts  │
  └─────────────┘  └─────────────┘  └─────────────┘  └─────────────┘
  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐  ┌─────────────┐
  │ Construction│  │  Healthcare │  │  Education  │  │  Logistics  │
  └─────────────┘  └─────────────┘  └─────────────┘  └─────────────┘
  ┌─────────────┐  ┌─────────────┐
  │ Real Estate │  │  Wholesale  │
  └─────────────┘  └─────────────┘

[Preview chart] [Skip — I'll build my own]                  [Back]  [Next]
```

After selecting → preview drawer slides in showing the full account tree with hover-tooltips on each account explaining what it's for.

**Components needed**
- `<CoaProfilePicker>` — grid of profile cards
- `<CoaPreviewDrawer>` — right-side drawer showing the tree (reuse `<CoATree>` from `accounting-coa.compiled.js` if available)
- Onboarding wizard step wrapper (already exists in `front/onboarding/`)

**User actions**
- Click profile card → fetch `/preview/{key}` → render tree
- Click "Use this profile" → `POST /instantiate/{key}` → advance wizard
- Click "Compose multiple" → multi-select mode → `POST /compose` with array of keys

**States**
- Loading profiles list: skeleton grid.
- Loading preview: skeleton tree.
- Error on instantiate: "Could not seed accounts. Already seeded?" — re-fetch existing CoA and skip step if so.
- Success: wizard advances.

**File location**
- **Suggested:** `front/onboarding/onboarding-coa-profile.jsx` (new step file)
- Wire into the wizard registry in `front/onboarding/onboarding-wizard.compiled.js`

**Dependencies**
- Requires: tenant exists with empty CoA.
- Blocks: every accounting screen — without a CoA, books can't be opened.

**Related existing files**
- Pattern to mirror: `onboarding-modules.jsx` (modules picker step) — same card-grid pattern.
- Components to reuse: `<WizardStep>`, `<WizardActions>` from `onboarding-wizard`.

**Cursor prompt template**
```
Build new onboarding step: CoA Industry Profile picker
File: front/onboarding/onboarding-coa-profile.jsx
Pattern: mirror onboarding-modules.jsx (card grid + preview)

Endpoints to consume (verified in routes/api.php):
- GET /accounting/coa-profiles (accounting.coa.view) — list 10 KSA profiles
- GET /accounting/coa-profiles/{key}/preview (accounting.coa.view) — tree preview
- POST /accounting/coa-profiles/{key}/instantiate (accounting.coa.manage, idempotent) — seed
- POST /accounting/coa-profiles/compose (accounting.coa.manage, idempotent) — merge

Layout: 4-col card grid of profiles, click to expand right-drawer preview, "Use this" or "Skip" CTAs.
States to handle: loading, empty (rare — backend ships 10 profiles), error, success → advance wizard.

Test plan:
- Pick Retail → preview shows ~142 accounts in tree → instantiate → next step
- Pick Compose → multi-select 2 profiles → merged tree → instantiate
- Skip → next step (CoA stays empty; user builds manually later)
```

**Notes**
- Backend already ships the 10 profiles; FE work is purely the picker UX.
- Mohammed flagged this as the #1 onboarding fix — generic CoA was causing 30+ minutes of manual account creation per tenant.

---

#### MS-ACCT-003 · Customer Statement PDF Lifecycle [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M
**Type:** New tab in customer detail drawer

**Backend capability** (✅ all verified)
- `GET /accounting/customers/{id}/statement-pdfs` — `IndexAccountingCustomerStatementDocumentsController`
- `POST /accounting/customers/{id}/statement-pdfs` (generate) — `ExportAccountingCustomerStatementController`
- `GET /accounting/customers/{id}/statement-pdfs/{docId}/download-url` — `IssueAccountingCustomerStatementDownloadUrlController`
- `GET /accounting/customers/{id}/statement-pdfs/{docId}/download` — `DownloadAccountingCustomerStatementController`
- Permissions: `accounting.customers.view`, `accounting.statements.generate`

**Proposed design**

In customer detail drawer, add **Statements** tab:
```
+ Generate statement     [Period: Mar 2026 ▾] [Format: PDF ▾]

Statement #ST-2026-0042 · Mar 2026 · Generated 2 days ago        [Download] [Email]
Statement #ST-2026-0041 · Feb 2026 · Generated 1 month ago       [Download] [Email]
Statement #ST-2026-0040 · Jan 2026 · Generated 2 months ago      [Download] [Email]
```

**Components needed**
- `<CustomerStatementsTab>` (new)
- `<GenerateStatementModal>` — period picker, optional date range override
- Reuse `<DocumentRow>` pattern from invoices list

**User actions**
- Generate → `POST` → poll for completion → row appears
- Download → `GET .../download-url` → follow redirect / open in new tab
- Email → `POST .../email` (verify endpoint exists)

**States**
- Empty: "No statements yet — generate the first one."
- Generating: row appears with spinner; poll `/statement-pdfs` every 3s.
- Error: row shows red badge + retry button.

**File location**
- **Suggested:** `front/accounting/customer-statements-tab.jsx` (mounted inside existing customer detail drawer in `accounting-collect.compiled.js`).

**Dependencies**
- Requires: customer exists and has at least one invoice.
- Blocks: AR collections workflow (statements are the standard nudge before legal action).

**Related existing files**
- Pattern to mirror: invoice PDF list inside invoice detail drawer.
- Components to reuse: `<DocRow>`, `<DocActions>`.

**Cursor prompt template**
```
Build new tab: Customer Statements (inside customer detail drawer)
File: front/accounting/customer-statements-tab.jsx
Pattern: mirror invoice-pdfs tab in invoice drawer

Endpoints (verified):
- GET /accounting/customers/{id}/statement-pdfs (accounting.customers.view)
- POST /accounting/customers/{id}/statement-pdfs (accounting.statements.generate, idempotent)
- GET /accounting/customers/{id}/statement-pdfs/{docId}/download-url

Layout: header [+ Generate] + period picker + format toggle, list of generated statements with [Download] / [Email].
States: empty, generating (poll), error, success.

Test plan:
- Generate Mar 2026 statement → spinner → row appears with download link
- Download opens PDF in new tab via short-lived signed URL
- Generate twice in same period → backend dedupes (idempotency)
```

---

#### MS-ACCT-004 · Recurring Journal Entries [ORIGINAL]

> ✅ **BUILT — Batch 8** · `front/accounting/accounting-recurring.compiled.js` · `window.AcctTabRecurring` · sub-tab of `accounting.journal`. Wired to live API (`/accounting/recurring-je` list / create / `run-now`) via `window.API.accounting.recurringJE`. Falls back to fixture seed when API unavailable.

**Priority:** 📌 V1.0 NICE
**Effort:** M
**Type:** New screen (sub-tab of `accounting.journal`)

**Backend capability** (✅ all verified)
- `GET /accounting/recurring-je` — `IndexRecurringJournalEntriesController`
- `POST /accounting/recurring-je` — `StoreRecurringJournalEntryController`
- `POST /accounting/recurring-je/{id}/run` (manual trigger; usually scheduled server-side)
- Permissions: `accounting.je.manage`

**Proposed design**

Sub-tab `Recurring` in `accounting-journal.compiled.js`:
```
[+ New schedule]  [Status: Active ▾]  [Cadence: Monthly ▾]      Next run: in 3 days

Schedule        Cadence    Next run    Last run     Status      Actions
Office rent     Monthly    1 May       1 Apr ✓     Active      [Run now] [Edit] [Pause]
Loan interest   Monthly    1 May       1 Apr ✓     Active      [Run now] [Edit] [Pause]
Depreciation    Monthly    Last day    31 Mar ✓    Active      [Run now] [Edit] [Pause]
Year-end fee    Yearly     31 Dec      31 Dec '25  Paused      [Run now] [Edit] [Resume]
```

**Components needed**
- `<RecurringJEList>` (new tab)
- `<RecurringJEEditor>` modal — copy of manual JE form + cadence picker (`monthly | quarterly | yearly | custom-cron`) + next-run preview
- `<CadencePicker>` (new)

**User actions**
- Create → opens editor → submit → row appears
- Run now → `POST /run` → posts a JE immediately, refreshes list
- Pause/Resume → `PATCH /recurring-je/{id}` with status

**States** — standard list/empty/error/success.

**File location** — `front/accounting/accounting-journal-recurring.jsx`, mounted as sub-tab of journal.

**Dependencies** — Requires manual JE form components (already in `accounting-journal`).

**Cursor prompt**
```
Build new sub-tab: Recurring Journal Entries
File: front/accounting/accounting-journal-recurring.jsx
Pattern: mirror manual JE form, add cadence picker

Endpoints:
- GET /accounting/recurring-je (accounting.je.view)
- POST /accounting/recurring-je (accounting.je.manage, idempotent)
- POST /accounting/recurring-je/{id}/run (accounting.je.manage, idempotent)

Layout: list with [+ New], filter chips, [Run now]/[Edit]/[Pause] per row.
States: empty, loading, error, success.
```

---

#### MS-ACCT-005 · Credit Notes Management [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M
**Type:** New tab in `accounting.collect` OR action on invoice

**Backend capability** (✅ verified)
- `POST /accounting/customer-credit-notes` — `StoreAccountingCustomerCreditNoteController`
- `GET` list (inferred — not in excerpt; verify in full file before consuming)
- Permissions: `accounting.credit_notes.create`

**Proposed design**
- Two entry points:
  1. **From invoice detail** — "Issue credit note" action → modal pre-fills lines from invoice → submit
  2. **Standalone tab** in `accounting.collect` — list of all credit notes, filterable by customer/period/status
- Credit note shape: customer, original invoice ref (optional), lines, total, reason code, ZATCA submission status

**Cursor prompt**
```
Build credit notes feature: standalone tab + invoice action
Files: front/accounting/accounting-credit-notes.jsx (new tab), edit accounting-collect for [Issue credit note] action

Endpoints:
- GET /accounting/customer-credit-notes
- POST /accounting/customer-credit-notes (accounting.credit_notes.create, idempotent)

Layout: list mirrors invoice list; modal mirrors invoice composer with [Reference invoice] field.
States: empty, loading, error, success.
ZATCA: credit notes are e-invoice type "credit"; show clearance status column.
```

**Notes**
- Credit note is the inverse posting of an invoice; backend handles GL automatically.
- Surface clearance status — credit notes go through ZATCA same as invoices.

---

#### MS-ACCT-006 · Vendor Debit Notes [ORIGINAL]  ✅ DELIVERED — Batch 1

**Priority:** 📌 V1.0 NICE
**Effort:** S
**Type:** Action on bill detail

**Backend capability** (✅ verified)
- `POST /accounting/vendor-debit-notes` — `StoreAccountingVendorDebitNoteController`
- Permissions: `accounting.debit_notes.create`

**Proposed design** — Action button on bill detail drawer; modal mirrors credit note shape (vendor instead of customer, references original bill).

**Cursor prompt**
```
Build vendor debit note action on bill detail
File: edit front/accounting/accounting-spend.compiled.js (add [Issue debit note] action to bill drawer)

Endpoints:
- POST /accounting/vendor-debit-notes (accounting.debit_notes.create, idempotent)

Layout: modal with vendor (locked), reference bill, lines (editable), reason, submit.
```

**Notes** — Tenant-side counterpart to MS-ACCT-005; same UX shape.

---

#### MS-ACCT-007 · Customer Write-off [ORIGINAL]  ✅ DELIVERED — Batch 1

**Priority:** ⚠️ V1.0 HIGH
**Effort:** S
**Type:** Action on customer detail / invoice detail

**Backend capability** (✅ verified)
- `POST /accounting/customers/{id}/write-off` — `StoreAccountingCustomerWriteOffController`
- Permissions: `accounting.write_offs.create`

**Proposed design**
- Action on customer balance drawer in `accounting.collect`: "Write off balance" → modal asks for amount + reason code (`uncollectible | dispute | gesture | bad-debt`) + reference + confirm
- Also exposed per-invoice as "Write off this invoice" (writes off remaining open amount)

**Cursor prompt**
```
Build customer write-off action
File: edit front/accounting/accounting-collect.compiled.js (add action to drawer)

Endpoint:
- POST /accounting/customers/{id}/write-off (accounting.write_offs.create, idempotent)

Layout: confirmation modal — amount (defaults to open balance), reason dropdown, memo, [Cancel] [Confirm write-off].
Permission gate: hide button if user lacks accounting.write_offs.create.
States: idle, submitting, success (toast + close), error (inline).
```

---

#### MS-ACCT-008 · Year-End Close Ceremony [ORIGINAL — partially wired]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** Multi-step wizard

**Backend capability** (✅ verified — endpoint exists)
- `POST /accounting/year-end/close` — `StoreYearEndCloseController`
- Period close: `POST /accounting/fiscal-periods/{id}/close` (`CloseFiscalPeriodController`)
- Reopen: `POST /accounting/fiscal-periods/{id}/reopen` (`ReopenFiscalPeriodController`)
- Permissions: `accounting.year_end.close`, `accounting.periods.close`, `accounting.periods.reopen`

**Status check** — `FLOW-INVENTORY.md` §10.2 has this flow but it's marked as a single-step button. The full ceremony is missing: pre-flight checks, retained-earnings preview, locking confirmation, post-close report.

**Proposed design** — 5-step wizard:
1. **Pre-flight** — list all open periods, unposted JEs, unreconciled bank lines, open AR/AP that should close. Block if any blockers; warn on advisories.
2. **Retained earnings preview** — show net income to be moved to retained earnings; allow user to override the destination account (default = code 3300).
3. **Schedule** — pick close date (default = fiscal year end), enable/disable comparative reports lock.
4. **Confirm** — disclaimer "This locks all JE before {date}; reopen requires owner approval."
5. **Run** — progress bar; on success, show post-close summary: # JEs locked, RE journal posted, comparative reports archived.

**Cursor prompt**
```
Build year-end close wizard
File: front/accounting/accounting-year-end-close.jsx (new), launched from accounting-settings or journal

Endpoints (verified):
- GET /accounting/fiscal-periods (list to find unclosed)
- GET /accounting/fiscal-periods/{id}/checks (pre-flight)
- POST /accounting/year-end/close (accounting.year_end.close, idempotent)

Layout: 5-step wizard (Pre-flight → RE preview → Schedule → Confirm → Run+summary).
States: blockers (red), advisories (amber), running (progress bar), success, error (rollback messaging).

Test plan:
- Open period exists → pre-flight shows blocker → wizard cannot advance
- All clean → run → JE posted → comparative reports locked → summary card
```

---

#### MS-ACCT-009 · Audit Drill (Cross-Entity) [ORIGINAL]

**Priority:** 🗓️ V1.1
**Effort:** M
**Type:** Drawer launched from any entity

**Backend capability** (✅ verified)
- `GET /accounting/audit/{entity}/{id}` — `IndexAccountingEntityAuditEventsController`
- Generic audit list: `GET /accounting/audit-events` — `IndexAccountingAuditEventsController`
- Permissions: `accounting.audit.view`

**Proposed design** — universal "View audit trail" action accessible from invoice/bill/JE/payment detail. Right-side drawer shows time-ordered event list with actor, action, before/after diff, IP, idempotency key.

**Cursor prompt**
```
Build audit-drill drawer (cross-entity)
File: front/accounting/accounting-audit-drawer.jsx (new — single drawer reused everywhere)

Endpoint:
- GET /accounting/audit/{entity}/{id} (accounting.audit.view) — entity ∈ {invoice, bill, je, payment, period, ...}

Layout: timeline drawer; each event = avatar + actor + action + relative timestamp + expandable diff.
Trigger: add "View audit trail" action to all entity detail drawers behind accounting.audit.view permission.
```

**Notes** — Defer to v1.1 unless auditor users are in pilot.

---

#### MS-ACCT-010 · Multi-Currency FX Rates [ORIGINAL]

**Priority:** 🗓️ V1.1
**Effort:** M
**Type:** New screen in `accounting.settings`

**Backend capability** (✅ verified)
- `GET /accounting/fx-rates` — `IndexAccountingFxRatesController`
- `POST /accounting/fx-rates` — `StoreAccountingFxRateController`
- `GET /accounting/currencies` — `IndexAccountingCurrenciesController`
- Permissions: `accounting.fx.manage`

**Proposed design** — list of currencies the tenant has activated; per row, daily rate history (last 30 days); manual override modal; auto-feed source picker (SAMA / openexchange).

**Cursor prompt**
```
Build FX rates settings screen
File: front/accounting/accounting-fx-rates.jsx (new tab in accounting-settings)

Endpoints:
- GET /accounting/currencies (list activated)
- GET /accounting/fx-rates?currency=USD&from=...&to=... 
- POST /accounting/fx-rates (accounting.fx.manage, idempotent) — manual override

Layout: currency table + per-row sparkline of last 30 days; click row → drawer with daily history + [Manual override] CTA.
```

**Notes** — Defer unless any pilot tenant has multi-currency invoices. Owner-side `OwnerCash` shows USD/EUR balances too — coordinate.

---

#### MS-ACCT-011 · Tax Codes Management [NEW]  ✅ DELIVERED — Batch 1

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M
**Type:** New tab in `accounting.settings`

**Backend capability** (✅ verified)
- `GET /accounting/vat-codes` — `IndexTenantVatCodesController`
- `POST /accounting/vat-codes` — `StoreTenantVatCodeController`
- Permissions: `accounting.vat.manage`

**Why missing** — KSA standard rate is 15%, but tenants need codes for zero-rated exports, exempt healthcare, out-of-scope, reverse-charge imports. No FE today; users would have to use SQL to seed.

**Proposed design**
```
Tax Codes                                                  [+ New code]

Code     Name (en)            Rate     Type             Default   Status
S        Standard 15%         15%      output           ✓         Active
Z        Zero-rated export    0%       output           —         Active
E        Exempt healthcare    —        exempt           —         Active
RC       Reverse charge       15%      input/RC         —         Active
OOS      Out of scope         —        none             —         Active
```

**Cursor prompt**
```
Build tax codes management tab
File: front/accounting/accounting-vat-codes.jsx (new tab in accounting-settings)

Endpoints (verified):
- GET /accounting/vat-codes (accounting.vat.view)
- POST /accounting/vat-codes (accounting.vat.manage, idempotent)
- PATCH /accounting/vat-codes/{id} (verify)

Layout: list table + [+ New code] modal (code, name, rate, type {output|input|exempt|none}, default flag).
Validation: codes must be unique per tenant; rate is 0–25%.
```

---

### §1.2 Retail / Catalog Module — 6 missing screens (4 ORIGINAL + 2 NEW)

#### MS-RETAIL-001 · Loyalty Programs Management [BUILT-PARTIAL]  ✅ PARTIAL — Batch 5 (Tiers tab read-only · v1.1 mutation)

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** New screen (`retail.customers` → `Loyalty` tab — exists as stub, needs full build)

**Backend capability** (✅ verified)
- `POST /loyalty/redeem` — `LoyaltyRedeemController`
- `POST /loyalty/breakage` — `LoyaltyBreakageController`
- Tier management: inferred (verify `/loyalty/programs`, `/loyalty/tiers`)
- Permissions: `crm.loyalty.manage`

**Status check** — `SCREENS-INVENTORY-Retail.md §5.3` notes the Loyalty tab exists but consumes `RetailHooks.loyalty.programme()` — fixture only.

**Proposed design** — 4-tab screen:
1. **Programs** — list active loyalty programs with type (points / visit / spend), earn rate, redeem rate
2. **Tiers** — Bronze/Silver/Gold thresholds, tier-specific multipliers
3. **Members** — top earners + redemption activity
4. **Settings** — point expiry, breakage policy, tax handling

**Cursor prompt**
```
Build loyalty programs management
File: edit front/retail/loyalty.jsx (currently stub) → expand to 4-tab screen

Endpoints:
- GET/POST /loyalty/programs (verify in routes)
- GET/POST /loyalty/tiers
- POST /loyalty/redeem (crm.loyalty.redeem, idempotent)
- POST /loyalty/breakage (crm.loyalty.breakage)

Layout: 4 tabs (Programs / Tiers / Members / Settings).
```

---

#### MS-RETAIL-002 · Gift Cards Issuance & Redemption [ORIGINAL · WIRED]  ✅ WIRED — Batch 5

**Priority:** 📌 V1.0 NICE
**Effort:** M
**Type:** New tab in `retail.customers`

**Backend capability** (✅ verified)
- `POST /gift-cards` — `IssueGiftCardController`
- `POST /gift-cards/{code}/redeem` — `RedeemGiftCardController`
- Permissions: `crm.gift_cards.issue`, `crm.gift_cards.redeem`

**Proposed design** — issuance modal (amount, recipient email, expiry, design), list of issued cards with status (active / partial / redeemed / expired), redemption history.

**Cursor prompt**
```
Build gift cards tab
File: front/retail/gift-cards.jsx (new tab in retail.customers)

Endpoints:
- GET /gift-cards (verify list)
- POST /gift-cards (idempotent, crm.gift_cards.issue)
- POST /gift-cards/{code}/redeem (idempotent, crm.gift_cards.redeem)
- POST /gift-cards/{code}/check-balance (verify)

Layout: [+ Issue] header, filter chips (Active/Partial/Redeemed/Expired), list with code/balance/expiry/holder.
POS integration: surface "Redeem gift card" tender in pos-pay.
```

---

#### MS-RETAIL-003 · Promotions Builder [ORIGINAL · WIRED]  ✅ WIRED — Batch 5

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** New module (sub-screen of `retail.catalog` or `retail.customers`)

**Backend capability** (✅ inferred from routes summary `/v1/promotions/*`)
- `GET /promotions`, `POST /promotions`, `PATCH /promotions/{id}`, `DELETE /promotions/{id}`
- Permissions: `catalog.promotions.manage`

**Proposed design** — promotion list + builder wizard: type (% off / fixed off / BOGO / bundle / threshold), eligibility (products/categories/customer segments), schedule (start/end + recurring), constraints (max uses, per-customer cap, stackable).

**Cursor prompt**
```
Build promotions module
Files:
- front/retail/promotions-list.jsx
- front/retail/promotion-builder.jsx (multi-step wizard)

Endpoints:
- GET/POST/PATCH/DELETE /promotions (catalog.promotions.manage)
- GET /promotions/{id}/usage (verify — analytics)

Layout: list with status chips (Draft/Scheduled/Active/Ended) + [+ New promotion] → 4-step wizard.
Test plan: BOGO across two SKUs honors POS redemption; expiry hides from POS automatically.
```

---

#### MS-RETAIL-004 · Pricing Lists / Price Books [ORIGINAL]

> ✅ **BUILT — Batch 8** · `front/retail/retail-pricing.compiled.js` · `window.PriceListsScreen` · token `retail.pricing` (sidebar Stock group). Multi-tier pricing surface (list / member / wholesale / promotional / branch) with KPI strip, filter chips, list cards (priority + coverage + discount), and a live **Pricing Resolver** sidebar that calls `POST /pricing/resolve` to show which list wins for a given product × branch × customer-segment. Create modal posts `POST /pricing/price-lists`.

**Priority:** 📌 V1.0 NICE
**Effort:** M
**Type:** New tab in `retail.catalog`

**Backend capability** (✅ inferred — pricing module exists per routes summary)
- `GET /pricing/lists`, `POST /pricing/lists`, `PATCH /pricing/lists/{id}`
- Permissions: `catalog.pricing.manage`

**Proposed design** — list of price books (Default / B2B / Wholesale / VIP), each with rules (% adjustment off default, override per SKU). Customer record gets a "default price book" field.

---

#### MS-RETAIL-005 · Inventory Adjustments (manual) [NEW]  ✅ DELIVERED — Batch 1

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M
**Type:** New tab in `retail.inventory`

**Backend capability** (✅ verified — `/v1/stock-adjustments` per routes summary)
- `POST /stock-adjustments` (audit + idempotent)
- Permissions: `inventory.adjust`

**Status check** — `SCREENS-INVENTORY-Retail.md §3.8` covers Write-offs (one type of adjustment). Generic adjustments (positive correction, negative correction, found-stock, lost-stock, scrap, sample-out) need a separate UI surfacing the full reason-code taxonomy.

**Proposed design** — list of adjustments + builder modal: SKU + qty (signed) + reason code (8 codes) + memo + biometric for negative > threshold. Each posts a JE via posting bridges.

**Cursor prompt**
```
Build inventory adjustments tab
File: front/retail/inventory-adjustments.jsx (new tab in retail.inventory)

Endpoints:
- GET /stock-adjustments (inventory.adjust.view)
- POST /stock-adjustments (inventory.adjust, audit, idempotent)

Layout: list + [+ New adjustment] → modal with SKU picker, signed qty, reason dropdown, memo, manager override if |qty * cost| > threshold.
```

---

#### MS-RETAIL-006 · Inter-Branch Transfers (full UI) [NEW · WIRED-PARTIAL]  ✅ PARTIAL — Batch 5 (create wired · receive=mock pending backend `/transfers/{id}/receive`)

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** Full screen — Existing tab is a placeholder

**Backend capability** (✅ verified — `/v1/transfers` per routes summary)
- Full state machine: draft → dispatched → in-transit → received → reconciled
- Permissions: `inventory.transfer.create`, `inventory.transfer.receive`

**Status check** — `SCREENS-INVENTORY-Retail.md §3.5` says `retail-transfers.compiled.js` exists with the create flow but **receive flow + variance reconciliation are missing** — flagged in cut-over impact section.

**Proposed design** — extend existing `inv-tab-transfers` to include:
- Receive at destination (scan-in, count vs expected, variance reasons)
- Variance reconciliation step before posting JE
- Print transfer slip

---

### §1.3 HR Module — 8 missing screens (7 ORIGINAL + 1 NEW)

> Baseline: `SCREENS-INVENTORY-Owner+HR.md` §2.4 lists 5 coming-soon HR tokens (`hr.org`, `hr.eosb`, `hr.recruit`, `hr.helpdesk`, `hr.ess`). The expanded list below maps backend capability to the tokens **and** adds new gaps.

#### MS-HR-001 · ATS Jobs Board [ORIGINAL · WIRED]  ✅ WIRED — Batch 4

**Priority:** ⚠️ V1.0 HIGH (per Mohammed: ATS in V1.0)
**Effort:** L
**Type:** New screen behind `hr.recruit` token

**Backend capability** (✅ verified in routes/api.php line 269)
- `GET /hr/jobs` — `IndexTenantHrAtsJobsController` (`permission:hr.view`)
- `POST /hr/jobs` (verify in full file)
- Permissions: `hr.view`, `hr.ats.manage` (verify)

**Proposed design** — Jobs list (Open/Draft/Closed), job detail with applicants count, [+ Post job] modal (title, dept, branch, JD, headcount, salary band, hiring manager).

**Cursor prompt**
```
Build ATS jobs board
File: front/owner/hr-recruit.jsx (new — replaces coming-soon for hr.recruit token)
Pattern: mirror hr-leave-v2 (live wrapper) + hr-roster-v2 (composer)

Endpoints (verified):
- GET /hr/jobs (hr.view)
- POST /hr/jobs (verify; hr.ats.manage)
- PATCH /hr/jobs/{id}
- DELETE /hr/jobs/{id} (close)

Layout: filter chips (Open/Draft/Closed) + list table + [+ Post job] modal.
Update SCREEN_MAP: replace ComingSoonTab with this component for hr.recruit.
```

---

#### MS-HR-002 · ATS Candidates Pipeline [ORIGINAL · WIRED]  ✅ WIRED — Batch 4

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** New screen, sibling tab to Jobs (under same `hr.recruit` token)

**Backend capability** (✅ verified)
- `GET /hr/candidates` — `IndexTenantHrAtsCandidatesController`
- Stage transitions: inferred — applied → screening → interview → offer → hired/rejected (verify)

**Proposed design** — Kanban board (drag candidates between stages), candidate drawer (CV, notes, interview schedule, offer letter).

**Cursor prompt**
```
Build candidates Kanban
File: front/owner/hr-candidates.jsx (sibling to hr-recruit jobs)

Endpoints:
- GET /hr/candidates?jobId=... (hr.view)
- PATCH /hr/candidates/{id} (stage update)

Layout: 5-column board (Applied/Screening/Interview/Offer/Decision); drag = PATCH stage.
```

---

#### MS-HR-003 · Learning / LMS Courses [ORIGINAL]

**Priority:** 🗓️ V1.1 (per Mohammed: LMS deferred)
**Effort:** L

**Backend capability** (✅ verified)
- `GET /hr/courses` — `IndexTenantHrLearningCoursesController`
- `POST /hr/enrollments` — `StoreTenantHrLearningEnrollmentController`

**Status check** — `SCREENS-INVENTORY-Owner+HR.md §2.3` shows `LearningTab` exists but is fixture-backed. Defer the full course catalog + e-learning player to v1.1.

---

#### MS-HR-004 · Loans Management [ORIGINAL]

**Priority:** 🗓️ V1.1
**Effort:** M

**Backend capability** (✅ verified)
- `POST /hr/loans` — `StoreTenantHrLoanController`
- List/detail: inferred (verify `GET /hr/loans`)

**Status check** — `LoansTab` exists fixture-backed in `hr-loans.compiled.js`. Needs cut-over to API + approval workflow.

---

#### MS-HR-005 · Expense Claims [ORIGINAL · WIRED]  ✅ WIRED — Batch 4

**Priority:** ⚠️ V1.0 HIGH (per Mohammed: Expenses in V1.0)
**Effort:** L

**Backend capability** (✅ verified)
- `POST /hr/expenses` — `StoreTenantHrExpenseController`
- List/approve/reject: inferred

**Status check** — `ExpensesTab` exists fixture-backed. Cut-over needed; also add approval drawer + receipt OCR upload.

**Cursor prompt**
```
Cut over expenses tab to API + add approval workflow
File: edit front/owner/hr-expenses.compiled.js → ExpensesTabV2
Pattern: mirror hr-leave-v2 (2-stage approval state machine)

Endpoints:
- GET /hr/expenses (hr.view)
- POST /hr/expenses (employee submits; idempotent)
- PATCH /hr/expenses/{id}/approve (manager) — verify
- PATCH /hr/expenses/{id}/reject — verify

Layout: filter (Mine/Pending approval/All), list, drawer with receipt preview.
```

---

#### MS-HR-006 · Assets Tracking [ORIGINAL]

**Priority:** 🗓️ V1.1
**Effort:** M

**Backend capability** (✅ verified)
- `GET /hr/assets` — `IndexTenantHrAssetsController`

**Status check** — `AssetsTab` exists fixture-backed; needs assignment + return + maintenance UX.

---

#### MS-HR-007 · Performance Reviews [ORIGINAL · LIVE-READ-ONLY]  ⚠️ PARTIAL — Batch 4 (mutation UI deferred to v1.1)

**Priority:** 📌 V1.0 NICE
**Effort:** L

**Backend capability** (✅ verified)
- `GET /hr/reviews` — `IndexTenantHrPerfReviewsController`
- `GET /hr/goals` — `IndexTenantHrPerfGoalsController`

**Status check** — `PerformanceTab` exists fixture-backed. Needs cycle creation + multi-rater + final-rating workflows.

---

#### MS-HR-008 · HR Helpdesk Tickets [ORIGINAL · WIRED]  ✅ WIRED — Batch 4

**Priority:** 📌 V1.0 NICE
**Effort:** M
**Type:** New screen behind `hr.helpdesk` token

**Backend capability** (✅ verified)
- `POST /hr/tickets` — `StoreTenantHrHelpdeskTicketController`

**Cursor prompt**
```
Build HR helpdesk
File: front/owner/hr-helpdesk.jsx (replaces ComingSoonTab for hr.helpdesk)

Endpoints:
- GET /hr/tickets (verify)
- POST /hr/tickets (audit, idempotent)
- PATCH /hr/tickets/{id} (status, assignee)

Layout: list + drawer (thread, status, assignee picker, internal notes).
Update SCREEN_MAP for hr.helpdesk.
```

---

#### MS-HR-009 · Org Chart [ORIGINAL · WIRED — token `hr.org`]  ✅ WIRED — Batch 4

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** New screen behind `hr.org` token

**Backend capability** — derived from `GET /hr/employees` + reporting hierarchy field.

**Proposed design** — D3-tree or react-flow org chart; click node = drawer with employee detail; drag-to-reparent (writes `manager_id`); PNG export.

**Cursor prompt**
```
Build org chart
File: front/owner/hr-org.jsx (replaces ComingSoonTab for hr.org)

Endpoint:
- GET /hr/employees (with managerId field) — derive tree
- PATCH /hr/employees/{id} (re-parent)

Layout: pannable/zoomable tree; minimap; export PNG.
Update SCREEN_MAP for hr.org.
```

---

#### MS-HR-010 · End-of-Service Benefit (EOSB) Calculator [ORIGINAL — token `hr.eosb`]

**Priority:** ⚠️ V1.0 HIGH (per KSA labour law)
**Effort:** L
**Type:** New screen behind `hr.eosb` token

**Backend capability** — ⚠️ **Backend gap** — EOSB resource not in routes/api.php. Cross-reference MASTER-ACTION-PLAN backend additions.

**Proposed design** — per-employee accrual table (years of service, basic salary, accrued days, projected payout), bulk recalc on salary change, payout posting on termination.

**Notes** — Saudi labour law: 1/2 month per year for first 5 years, 1 month per year after. Backend needs `/hr/eosb/{employeeId}/accrual` endpoint added before FE work.

---

#### MS-HR-011 · Employee Self-Service (ESS) Wiring [ORIGINAL — token `hr.ess`]  ✅ DELIVERED — Batch 1

**Priority:** ⚠️ V1.0 HIGH
**Effort:** S — flip flag, wire 1 endpoint
**Type:** Activate existing component

**Backend capability** (✅ verified)
- `GET /me/ess` — `ShowEmployeeEssController` (line 237 of routes/api.php)
- Already 4-tab UX built in `hr-ess.compiled.js` per Owner+HR §2.4

**Cursor prompt**
```
Activate ESS
File: edit front/owner/hr-shell.compiled.js
Change: in SCREEN_MAP, set hr.ess flagship: false; set Cmp: () => H.ESSContent
Wire: in hr-ess, replace fixture reads with useApi(API.me.ess)

Endpoint: GET /me/ess (any authenticated user)
```

**Notes** — Lowest-effort highest-impact win: full UX is already built.

---

### §1.4 CRM Module — 3 missing screens [ORIGINAL]

#### MS-CRM-001 · Customer 360 View [BUILT-PARTIAL]  ✅ PARTIAL — Batch 5 (Orders / AR tabs LIVE-READ-ONLY pending /sales filter & /accounting/aging filter)

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L
**Type:** Expand customer detail drawer

**Backend capability** (✅ multiple — already exist)
- `GET /accounting/customers/{id}/ledger` — `ShowAccountingCustomerLedgerController`
- `GET /accounting/customers/{id}/statement-pdfs` — see MS-ACCT-003
- `GET /sales?customerId=` (verify)
- `GET /support/tickets?customerId=` (verify)

**Proposed design** — single drawer with 6 tabs: Profile / Sales / AR Ledger / Statements / Loyalty / Tickets. Replaces today's siloed views in Retail customers list, Accounting collect, and ad-hoc search.

---

#### MS-CRM-002 · Suppliers Management (Standalone) [ORIGINAL]

> ✅ **EXPANDED — Batch 8** · Existing `InvTabSuppliers` directory + `SupplierDrawer` (token `retail.suppliers`) extended with **Vendor 360** tab navigation: **Overview** (existing), **Purchase History** (6-month spend bars + top SKUs supplied + PO ledger), **Payment Performance** (on-time payment rate, avg days-to-pay vs terms drift, open A/P invoice ledger with overdue flagging). Backed by `GET /suppliers` + filtered `/supplier-invoices` + `/supplier-payments`. The vendor-360 surface satisfies the "standalone management" intent without a separate top-level screen.

**Priority:** 📌 V1.0 NICE
**Effort:** M

**Backend capability** (✅ inferred — `/v1/suppliers/*` per routes summary)
- Permissions: `purchasing.suppliers.manage`

**Status check** — `SCREENS-INVENTORY-Retail.md §4.4` shows suppliers tab exists; this row is for standalone module-level management with vendor 360 (purchases, payments, performance).

---

#### MS-CRM-003 · Loyalty Tiers Configuration [ORIGINAL — partially overlapping with MS-RETAIL-001]

**Priority:** 📌 V1.0 NICE
**Effort:** S

Covered as a tab inside MS-RETAIL-001. **DROP from final count** — folded into MS-RETAIL-001.

---

### §1.5 Pay Module — 3 missing screens (1 ORIGINAL + 2 NEW)

#### MS-PAY-001 · Settlement Exceptions Workbench [NEW]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** — ✅ `/pay/settlement-exceptions` exists (per `SCREENS-INVENTORY-Pay.md §8.3` flagging it as gap).

**Proposed design** — list of mismatched/disputed/missing-merchant settlements; per-row resolution flow (match to ledger / mark accepted / escalate to acquirer).

**Cursor prompt**
```
Build settlement exceptions workbench
File: front/pay/pay-settlement-exceptions.jsx (new sub-screen of pay.settlements)

Endpoints:
- GET /pay/settlement-exceptions (pay.settlements.view)
- POST /pay/settlement-exceptions/{id}/resolve (pay.settlements.manage, audit, idempotent)

Layout: list with severity chips, drawer with statement vs ledger diff, [Match]/[Accept]/[Escalate] actions.
```

---

#### MS-PAY-002 · Pay Reports Dashboard [NEW]

**Priority:** 📌 V1.0 NICE
**Effort:** M

**Backend capability** — ✅ four reports exist per `SCREENS-INVENTORY-Pay.md §8.2`: `mdr-by-scheme`, `acquirer-mix`, `chargeback-rate`, `auth-decline-rate`.

**Proposed design** — new `pay.reports` route key — 4-card dashboard, period filter, drill into each as full-screen.

---

#### MS-PAY-003 · Reconciliation Deep-Dive [NEW]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L

**Backend capability** (✅ verified)
- `POST /reconciliation/{id}/resolve` — per routes summary
- `POST /accounting/bank-statement-lines/{id}/match` — `MatchBankStatementLineController`
- `POST /accounting/bank-statement-lines/{id}/unmatch` — `UnmatchBankStatementLineController`
- `GET /accounting/bank-statement-suggestions` — `IndexBankStatementSuggestionsController`

**Status check** — Owner cash `CashReconcile` is a stub (per Owner+HR §1.2); accounting bank tab has match/unmatch but no full deep-dive UX. This is the proper reconcile workbench.

**Cursor prompt**
```
Build reconciliation workbench
File: front/accounting/accounting-bank-reconcile.jsx (new — replaces/extends accounting-bank stub)

Endpoints (verified):
- POST /accounting/bank-statements/import (ImportBankStatementController)
- GET /accounting/bank-statement-lines (IndexBankStatementLinesController)
- GET /accounting/bank-statement-suggestions (IndexBankStatementSuggestionsController)
- POST /accounting/bank-statement-lines/{id}/match (idempotent)
- POST /accounting/bank-statement-lines/{id}/unmatch
- POST /accounting/bank-reconcile (ReconcileBankController)

Layout: split-pane (statement lines | ledger txns) + suggestions strip; drag-to-match; bottom bar showing balance vs ledger; [Reconcile] commits.
```

---

### §1.6 Dine Module — 5 missing screens (4 ORIGINAL + 1 dropped)

#### MS-DINE-001 · Aggregator Inbox [BUILT-PARTIAL]  ✅ PARTIAL — Batch 6 (Accept/Reject LIVE · Ready/Dispatch/Complete/Cancel MOCK · backend gap)

**Priority:** ⚠️ V1.0 HIGH (if pilot tenants use Talabat/HungerStation)
**Effort:** L

**Backend capability** (✅ verified — `/aggregator/*` per routes)
- `GET /aggregator/inbox` (verify)
- `POST /aggregator/{id}/accept` / `reject`
- Webhook ingestion: `IngestAggregatorWebhookController` (line 102 of routes/api.php)

**Proposed design** — left rail = aggregator partners (Talabat / HungerStation / Jahez / The Chefz / Mrsool); main = order list (live updates); detail = items, customer, fees, delivery instructions, [Accept]/[Reject] CTAs.

---

#### MS-DINE-002 · Modifier Groups Builder [BUILT-PARTIAL]  ✅ PARTIAL — Batch 6 (List/Create LIVE · Update/Delete MOCK · backend gap)

**Priority:** ⚠️ V1.0 HIGH (essential for menu)
**Effort:** M

**Backend capability** (✅ verified — `/v1/modifier-groups` per routes summary, `plan_module:dine`)

**Proposed design** — list of modifier groups (size, addons, removals, sauces); per-group editor (name, min/max, items with price deltas, attach to menu items).

---

#### MS-DINE-003 · Combos Builder [BUILT-PARTIAL]  ✅ PARTIAL — Batch 6 (List/Create LIVE · Update/Delete MOCK · backend gap)

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** (✅ verified — `/v1/combos`)

**Proposed design** — combo composer (e.g. burger + fries + drink for SAR 35), step picker (which menu items at each step, swappable), price override, KDS routing.

---

#### MS-DINE-004 · Production Orders [BUILT-PARTIAL]  ✅ PARTIAL — Batch 6 (Create LIVE · List/Lifecycle MOCK · backend gap)

**Priority:** ⚠️ V1.0 HIGH (back-of-house ops)
**Effort:** L

**Backend capability** (✅ verified)
- `POST /production-orders` (per routes summary)
- `GET /production-orders/audit`

**Proposed design** — kitchen production board (prep lists for the day; e.g. "Make 50 portions of biryani by 11am"), recipe expansion, ingredient deduction preview, [Start]/[Complete] state machine.

---

#### MS-DINE-005 · Recipe Drift Tracking [ORIGINAL]

> ✅ **BUILT — Batch 8** · `front/dine/dine-recipe-drift.compiled.js` · `window.DineRecipeDrift` · token `dine.recipe-drift`. Variance report (planned vs actual ingredient usage) backed by `GET /recipe-drift` + `POST /recipe-drift` (observation log). Includes per-recipe drilldown drawer with ingredient-level deltas, branch/period filters, severity tags (within tolerance / drift / critical), and trend sparkline.

**Priority:** 📌 V1.0 NICE
**Effort:** M

**Backend capability** (✅ verified — `/recipe-drift` per routes summary)

**Proposed design** — variance report (theoretical vs actual ingredient consumption), per-item drift %, drill into affected POs/sales.

---

#### MS-DINE-006 · QR Self-Order [ORIGINAL]

**Priority:** 🗓️ V1.1
**Effort:** L

**Backend capability** (✅ verified — `/qr/{token}/menu`, `/qr/{token}/orders`, `/qr/{token}/orders/{id}/status` per routes summary)

**Proposed design** — public-facing menu (no auth), cart, place order, status polling. Defer to v1.1.

---

### §1.7 E-commerce Module — 5 missing screens (entire module, all ORIGINAL)

> **Module-level decision:** Mohammed flagged ecom as v1.1 unless pilot tenants need it. Treat as bundle.

| ID | Screen | Priority | Effort |
|---|---|---|---|
| MS-ECOM-001 | E-com Orders Inbox | 🗓️ V1.1 | L |
| MS-ECOM-002 | Order Confirmation Flow | 🗓️ V1.1 | S |
| MS-ECOM-003 | Fulfillment Workflow | 🗓️ V1.1 | L |
| MS-ECOM-004 | Returns Management (Ecom) | 🗓️ V1.1 | M |
| MS-ECOM-005 | Customer Order Tracking (Public) | 🗓️ V1.1 | M |

**Backend** — `/v1/ecom/orders/{id}/{confirm|prepare|fulfill|deliver|complete|return}` (✅ all verified per routes summary). Workflow aggregates `workflows/ecom-orders` and `workflows/ecom-fulfillment` are wired (lines 366-371 of routes/api.php).

**Cursor prompt (module-level)**
```
Build ecom module (5 screens)
Files: front/ecom/{ecom-orders,ecom-fulfillment,ecom-returns,ecom-tracking}.jsx + ecom-shell.jsx

Endpoints (all verified):
- GET /workflows/ecom-orders (ecom.orders.create)
- GET /workflows/ecom-fulfillment (ecom.orders.fulfill)
- POST /ecom/orders/{id}/{confirm|prepare|fulfill|deliver|complete|return}

Defer to v1.1 unless pilot need surfaces.
```

---

### §1.8 Help Center — 2 missing screens [ORIGINAL]

#### MS-HELP-001 · User-Facing Help Drawer [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** (✅ verified per routes summary `/v1/help/*`)
- `GET /help/modules`, `GET /help/modules/{slug}/categories`, `GET /help/categories/{slug}/articles`, `GET /help/articles/{slug}`, `GET /help/search`

**Proposed design** — `?` button in topbar opens right-side drawer; module-aware (filtered by current module); search; article markdown render; "Was this helpful?" feedback.

---

#### MS-HELP-002 · Admin Help Editor [ORIGINAL]

**Priority:** 🗓️ V1.1
**Effort:** L

**Backend capability** (✅ verified — `/admin/help/*` controllers in routes/api.php lines 96-101)
- `StoreHelpArticleController` (admin), `UpdateHelpArticleController`, `PublishHelpArticleController`, `ArchiveHelpArticleController`, `RollbackHelpArticleVersionController`, `IndexHelpArticleVersionsController`, `StoreHelpArticleTranslationController`

**Proposed design** — markdown editor with live preview, version history, en/ar translation editor, publish/archive workflow. Platform-side surface.

---

### §1.9 Notifications Module — 2 missing screens [ORIGINAL]

#### MS-NOTIF-001 · Notifications Inbox [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** (✅ verified)
- `/notifications/in-app` per routes summary
- `workflows/notifications-status` (line 360 of routes/api.php)

**Proposed design** — bell icon in topbar with badge; popover with recent 10; full inbox screen; mark read/unread; filter by type; deep-link to source entity.

---

#### MS-NOTIF-002 · Notification Preferences [ORIGINAL]  ✅ DELIVERED — Batch 1

**Priority:** 📌 V1.0 NICE
**Effort:** S

**Backend capability** (✅ verified — `/notifications/preferences`)

**Proposed design** — settings screen with channel × event matrix (Email / SMS / Push × Invoice paid / Bill due / Approval needed / etc.).

---

### §1.10 Onboarding — 2 missing screens [ORIGINAL]

#### MS-ONBOARD-001 · Branch Setup Wizard [ORIGINAL]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** (✅ verified — `POST /branches`, line 249 of routes/api.php; `limit:max_branches` middleware)

**Proposed design** — multi-branch wizard: branch name + address + manager + timezone + register count. Plan limit displayed.

---

#### MS-ONBOARD-002 · Company Profile Editor [ORIGINAL]  ✅ DELIVERED — Batch 1

**Priority:** ⚠️ V1.0 HIGH
**Effort:** S

**Backend capability** (✅ verified — `PATCH /companies/{company}`, line 247)

**Proposed design** — settings screen: legal name, CR, VAT, address, banking, logo upload, primary contact.

---

### §1.11 Cross-cutting / Platform-side — 7 missing screens (all NEW from prompt's instruction list)

#### MS-XCUT-001 · Manager Override Centralization [NEW]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** — `POST /auth/manager-override` (must be added; flagged in `SCREENS-INVENTORY-Retail.md §2.5` as backend gap)

**Status** — Today PIN is checked client-side. **Backend gap** — needs server route + capability table.

---

#### MS-XCUT-002 · Roles Editor (full RBAC) [NEW]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** L

**Backend capability** (✅ inferred — `/v1/roles`, `/v1/permissions`, `/v1/users` per routes summary)

**Status check** — `SCREENS-INVENTORY-Common.md §4.3` says `RolesHubV2` exists (1300+ LOC); however, several quirks (assign-users no-op, no diff write) need fixing — folded into a single "harden the existing screen" task. **DROP as a missing-screen** — actually exists; document as "needs hardening" instead. Move to §A footnote.

---

#### MS-XCUT-003 · MFA Setup Wizard [NEW]

**Priority:** ⚠️ V1.0 HIGH
**Effort:** M

**Backend capability** (✅ verified)
- `POST /me/mfa` — `EnableMfaController` (line 243)
- `MfaVerifyController` (line 109)

**Status** — `SCREENS-INVENTORY-Common.md §3.5 (MySecurityScreen)` mentions 2FA setup — UX is partial. Needs full wizard: choose method (TOTP / SMS), QR/secret display, backup codes, verify, success.

---

#### MS-XCUT-004 · Devices Management [NEW]

**Priority:** 📌 V1.0 NICE
**Effort:** M

**Backend capability** — Trusted devices table is referenced in `SCREENS-INVENTORY-Common.md §3.5` but no FE screen yet. Backend endpoint inferred (`/me/sessions`, `/me/devices`).

**Proposed design** — list active sessions and trusted devices; per-row [Revoke]; "Sign out everywhere" CTA.

---

#### MS-XCUT-005 · Cost Centers Management [NEW]

**Priority:** 📌 V1.0 NICE
**Effort:** M

**Backend capability** (✅ verified — Dimensions ARE cost centers)
- `GET /accounting/dimensions` — `IndexAccountingDimensionsController`
- `PATCH /accounting/dimensions/{id}` — `UpdateAccountingDimensionController`
- `GET /accounting/dimension-values` — `IndexDimensionValuesController`
- `POST /accounting/dimension-values` — `StoreDimensionValueController`

**Proposed design** — list dimensions (Cost Center, Project, Region, Department, Custom×N); per-dimension list of values with hierarchy. Used to tag every JE line.

---

#### MS-XCUT-006 · Posting Bridges Configuration [NEW]

**Priority:** 📌 V1.0 NICE
**Effort:** M

**Backend capability** (✅ verified)
- `GET /accounting/posting-bridges` — `IndexAccountingPostingBridgesController`
- Permissions: `accounting.posting_bridges.manage` (verify)

**Proposed design** — config screen mapping module events (sale-cash / sale-credit / purchase-grn / payroll-net / etc.) to GL account pairs (debit/credit). Critical for accounting team to control journal flow.

**Cursor prompt**
```
Build posting bridges editor
File: front/accounting/accounting-posting-bridges.jsx (new — sub-tab of accounting-settings)

Endpoints:
- GET /accounting/posting-bridges
- PATCH /accounting/posting-bridges/{event} (verify)

Layout: list of events × Dr account × Cr account. Default mappings ship from CoA profile (see MS-ACCT-002).
```

---

#### MS-XCUT-007 · Fiscal Calendar Settings [NEW]  ✅ DELIVERED — Batch 1

**Priority:** ⚠️ V1.0 HIGH
**Effort:** S

**Backend capability** (✅ verified)
- `GET /accounting/fiscal-calendar` — `ShowFiscalCalendarController`
- `PATCH /accounting/fiscal-calendar` — `UpdateFiscalCalendarController`
- `GET /accounting/fiscal-periods` — `IndexFiscalPeriodsController`

**Proposed design** — fiscal year start month, period length (monthly / quarterly / 4-4-5 retail), period status grid (12 cells: Draft/Open/Closed/Locked).

---

## §2 — Cross-Module Patterns (reusable components Cursor should build once)

### §2.1 `<EntityAuditDrawer>` (used by MS-ACCT-009, all entity detail drawers)

Universal "view audit trail" drawer; mounts via `<EntityAuditDrawer entity="invoice" id={ulid}>`.

### §2.2 `<DocumentLifecycleList>` (used by MS-ACCT-003, MS-HELP-001 article versions, etc.)

Generic list of generated documents (PDFs, exports) with status badges + download/email actions. Pattern: header [+ Generate] → polling row → terminal status → actions.

### §2.3 `<KsaPhasedWizard>` (used by MS-ONBOARD-001/002, MS-ACCT-002, MS-XCUT-003)

Standard onboarding wizard chrome — step indicator, persistent draft, back/next, KSA bilingual copy. Already partially implemented in `front/onboarding/onboarding-wizard.compiled.js` — extract to `front/common/wizard.jsx`.

### §2.4 `<RolePermissionedAction>` (used everywhere a CTA must hide)

Wrap actions: `<RolePermissionedAction perm="accounting.write_offs.create"><Button>Write off</Button></RolePermissionedAction>`. Today permission gating is ad-hoc per file.

### §2.5 `<PartnerInbox>` (used by MS-DINE-001, MS-NOTIF-001, MS-ECOM-001)

Pattern: left rail = source/partner; main = list with live updates; detail = drawer. Same shell, different data.

### §2.6 `<KanbanBoard>` (used by MS-HR-002, future use cases)

Drag-between-columns kanban; columns from server `stages` field; PATCH on drop.

### §2.7 `<DiffMatchPane>` (used by MS-PAY-001, MS-PAY-003)

Two-column diff: left = statement / external, right = ledger / internal; suggestion strip with confidence score; drag-to-match.

---

## §3 — Priority-Ranked Summary Table

| ID | Screen | Module | Priority | Effort | Origin |
|---|---|---|---|---|---|
| MS-HR-011 | ESS Wiring (flip flag) | HR | ⚠️ HIGH | S | ORIGINAL |
| MS-ACCT-007 | Customer Write-off | Accounting | ⚠️ HIGH | S | ORIGINAL |
| MS-ONBOARD-002 | Company Profile Editor | Onboarding | ⚠️ HIGH | S | ORIGINAL |
| MS-XCUT-007 | Fiscal Calendar Settings | Cross-cut | ⚠️ HIGH | S | NEW |
| MS-ACCT-001 | Cashflow Statement | Accounting | ⚠️ HIGH | M | ORIGINAL |
| MS-ACCT-003 | Customer Statement PDF | Accounting | ⚠️ HIGH | M | ORIGINAL |
| MS-ACCT-005 | Credit Notes | Accounting | ⚠️ HIGH | M | ORIGINAL |
| MS-ACCT-011 | Tax Codes Management | Accounting | ⚠️ HIGH | M | NEW |
| MS-RETAIL-005 | Inventory Adjustments | Retail | ⚠️ HIGH | M | NEW |
| MS-DINE-002 | Modifier Groups Builder | Dine | ⚠️ HIGH | M | ORIGINAL |
| MS-DINE-003 | Combos Builder | Dine | ⚠️ HIGH | M | ORIGINAL |
| MS-HELP-001 | User-Facing Help Drawer | Help | ⚠️ HIGH | M | ORIGINAL |
| MS-NOTIF-001 | Notifications Inbox | Notifications | ⚠️ HIGH | M | ORIGINAL |
| MS-ONBOARD-001 | Branch Setup Wizard | Onboarding | ⚠️ HIGH | M | ORIGINAL |
| MS-PAY-001 | Settlement Exceptions | Pay | ⚠️ HIGH | M | NEW |
| MS-XCUT-003 | MFA Setup Wizard | Cross-cut | ⚠️ HIGH | M | NEW |
| MS-XCUT-001 | Manager Override (BE+FE) | Cross-cut | ⚠️ HIGH | M | NEW |
| MS-ACCT-002 | CoA Industry Profiles | Accounting | ⚠️ HIGH | L | ORIGINAL |
| MS-ACCT-008 | Year-End Close Ceremony | Accounting | ⚠️ HIGH | L | ORIGINAL |
| MS-RETAIL-001 | Loyalty Programs | Retail | ⚠️ HIGH | L | ORIGINAL |
| MS-RETAIL-003 | Promotions Builder | Retail | ⚠️ HIGH | L | ORIGINAL |
| MS-RETAIL-006 | Inter-Branch Transfers | Retail | ⚠️ HIGH | L | NEW |
| MS-HR-001 | ATS Jobs Board | HR | ⚠️ HIGH | L | ORIGINAL |
| MS-HR-002 | ATS Candidates | HR | ⚠️ HIGH | L | ORIGINAL |
| MS-HR-005 | Expense Claims (cut-over) | HR | ⚠️ HIGH | L | ORIGINAL |
| MS-HR-009 | Org Chart | HR | ⚠️ HIGH | L | ORIGINAL |
| MS-HR-010 | EOSB Calculator | HR | ⚠️ HIGH | L | ORIGINAL |
| MS-CRM-001 | Customer 360 View | CRM | ⚠️ HIGH | L | ORIGINAL |
| MS-DINE-001 | Aggregator Inbox | Dine | ⚠️ HIGH | L | ORIGINAL |
| MS-DINE-004 | Production Orders | Dine | ⚠️ HIGH | L | ORIGINAL |
| MS-PAY-003 | Reconciliation Deep-Dive | Pay/Accounting | ⚠️ HIGH | L | NEW |
| MS-ACCT-006 | Vendor Debit Notes | Accounting | 📌 NICE | S | ORIGINAL |
| MS-NOTIF-002 | Notification Preferences | Notifications | 📌 NICE | S | ORIGINAL |
| MS-ACCT-004 | Recurring JE | Accounting | 📌 NICE | M | ORIGINAL |
| MS-RETAIL-002 | Gift Cards | Retail | 📌 NICE | M | ORIGINAL |
| MS-RETAIL-004 | Pricing Lists | Retail | 📌 NICE | M | ORIGINAL |
| MS-CRM-002 | Suppliers Standalone | CRM | 📌 NICE | M | ORIGINAL |
| MS-DINE-005 | Recipe Drift | Dine | 📌 NICE | M | ORIGINAL |
| MS-PAY-002 | Pay Reports Dashboard | Pay | 📌 NICE | M | NEW |
| MS-XCUT-004 | Devices Management | Cross-cut | 📌 NICE | M | NEW |
| MS-XCUT-005 | Cost Centers (Dimensions) | Cross-cut | 📌 NICE | M | NEW |
| MS-XCUT-006 | Posting Bridges Config | Cross-cut | 📌 NICE | M | NEW |
| MS-HR-007 | Performance Reviews | HR | 📌 NICE | L | ORIGINAL |
| MS-HR-008 | HR Helpdesk | HR | 📌 NICE | M | ORIGINAL |
| MS-ACCT-009 | Audit Drill | Accounting | 🗓️ V1.1 | M | ORIGINAL |
| MS-ACCT-010 | Multi-Currency FX | Accounting | 🗓️ V1.1 | M | ORIGINAL |
| MS-HELP-002 | Admin Help Editor | Help | 🗓️ V1.1 | L | ORIGINAL |
| MS-HR-003 | LMS Courses | HR | 🗓️ V1.1 | L | ORIGINAL |
| MS-HR-004 | Loans Management | HR | 🗓️ V1.1 | M | ORIGINAL |
| MS-HR-006 | Assets Tracking | HR | 🗓️ V1.1 | M | ORIGINAL |
| MS-DINE-006 | QR Self-Order | Dine | 🗓️ V1.1 | L | ORIGINAL |
| MS-ECOM-001..005 | E-com module (5) | Ecom | 🗓️ V1.1 | XL | ORIGINAL |

**Counts (final):**
- 🚨 V1.0 BLOCKER: 0 (no entries elevated to BLOCKER — all V1.0 needs are HIGH or NICE)
- ⚠️ V1.0 HIGH: 31
- 📌 V1.0 NICE: 12
- 🗓️ V1.1: 11 (incl. 5 ECOM)
- **Total: 49 missing screens** (after dropping MS-CRM-003 [folded] and MS-XCUT-002 [exists])

---

## §4 — File-Level Recommendations

### Where each missing screen should live

| Module | Folder | New files |
|---|---|---|
| Accounting | `front/accounting/` | `accounting-reports-cashflow.jsx` (or extend `accounting-reports`), `customer-statements-tab.jsx`, `accounting-credit-notes.jsx`, `accounting-journal-recurring.jsx`, `accounting-year-end-close.jsx`, `accounting-audit-drawer.jsx`, `accounting-fx-rates.jsx`, `accounting-vat-codes.jsx`, `accounting-bank-reconcile.jsx`, `accounting-posting-bridges.jsx`, `accounting-fiscal-calendar.jsx` |
| Onboarding | `front/onboarding/` | `onboarding-coa-profile.jsx`, `onboarding-branch-setup.jsx`, `onboarding-company-profile.jsx` |
| Retail | `front/retail/` | `loyalty.jsx` (expand), `gift-cards.jsx`, `promotions-list.jsx`, `promotion-builder.jsx`, `pricing-lists.jsx`, `inventory-adjustments.jsx`, `inventory-transfers-receive.jsx` (extend) |
| HR | `front/owner/` | `hr-recruit.jsx`, `hr-candidates.jsx`, `hr-org.jsx`, `hr-eosb.jsx`, `hr-helpdesk.jsx`, `hr-expenses-v2.compiled.js`, `hr-ess` (flip flag) |
| Dine | `front/dine/` | `dine-aggregator-inbox.jsx`, `dine-modifier-groups.jsx`, `dine-combos.jsx`, `dine-production-orders.jsx`, `dine-recipe-drift.jsx` |
| Pay | `front/pay/` | `pay-settlement-exceptions.jsx`, `pay-reports.jsx` |
| CRM | `front/retail/` (CRM lives in retail nav) | `customer-360-drawer.jsx`, `suppliers-standalone.jsx` |
| Help | `front/common/` (drawer is global) | `help-drawer.jsx`; `front/platform/` for admin: `platform-help-editor.jsx` |
| Notifications | `front/common/` | `notifications-inbox.jsx`, `notifications-preferences.jsx` |
| Cross-cut | `front/common/` | `mfa-setup-wizard.jsx`, `devices-management.jsx`, `cost-centers.jsx` |
| Ecom (V1.1) | `front/ecom/` (new module) | `ecom-shell.jsx`, `ecom-orders.jsx`, `ecom-fulfillment.jsx`, `ecom-returns.jsx`, `ecom-tracking.jsx` |

### Reusable patterns (build once, see §2)

`front/common/` should grow `<EntityAuditDrawer>`, `<DocumentLifecycleList>`, `<KsaPhasedWizard>`, `<RolePermissionedAction>`, `<PartnerInbox>`, `<KanbanBoard>`, `<DiffMatchPane>`.

---

## §5 — Cursor Execution Order

Suggested batching for Cursor sessions, ordered by priority × effort:

### Batch 1 — Quick wins (8 screens, all S/M effort, all V1.0 HIGH)
Goal: maximize visible progress; build cross-cutting patterns.
1. **MS-HR-011** ESS wiring (S) — flip flag, 1 endpoint
2. **MS-ACCT-007** Customer write-off (S)
3. **MS-ONBOARD-002** Company profile (S)
4. **MS-XCUT-007** Fiscal calendar (S)
5. **MS-NOTIF-002** Notification preferences (S)
6. **MS-ACCT-006** Vendor debit note (S)
7. **MS-RETAIL-005** Inventory adjustments (M)
8. **MS-ACCT-011** Tax codes (M)

### Batch 2 — Cross-cutting infrastructure (3 screens + 7 reusable components)
Goal: build the `<EntityAuditDrawer>`, `<KsaPhasedWizard>`, `<RolePermissionedAction>`, `<DocumentLifecycleList>` once.
9. Build §2 reusable components
10. **MS-ACCT-009** Audit drill (uses `<EntityAuditDrawer>`)
11. **MS-ACCT-003** Customer statements (uses `<DocumentLifecycleList>`)
12. **MS-ONBOARD-001** Branch wizard (uses `<KsaPhasedWizard>`)

### Batch 3 — Reports & accounting depth (5 screens)
13. **MS-ACCT-001** Cashflow
14. **MS-ACCT-002** CoA profiles
15. **MS-ACCT-005** Credit notes
16. **MS-ACCT-008** Year-end close
17. **MS-PAY-003** Reconciliation deep-dive

### Batch 4 — HR push (5 screens)
18. **MS-HR-009** Org chart
19. **MS-HR-005** Expenses cut-over + approvals
20. **MS-HR-001** ATS jobs
21. **MS-HR-002** ATS candidates
22. **MS-HR-010** EOSB (after BE adds endpoint)

### Batch 5 — Retail depth (4 screens)
23. **MS-RETAIL-001** Loyalty
24. **MS-RETAIL-003** Promotions
25. **MS-RETAIL-006** Transfers receive
26. **MS-CRM-001** Customer 360

### Batch 6 — Dine push (4 screens)
27. **MS-DINE-002** Modifier groups
28. **MS-DINE-003** Combos
29. **MS-DINE-001** Aggregator inbox
30. **MS-DINE-004** Production orders

### Batch 7 — Cross-cutting V1.0 finish (5 screens)
31. **MS-HELP-001** Help drawer
32. **MS-NOTIF-001** Notifications inbox
33. **MS-XCUT-001** Manager override (after BE route)
34. **MS-XCUT-003** MFA wizard
35. **MS-PAY-001** Settlement exceptions

### Batch 8 — V1.0 NICE (8 screens — ship if calendar permits)
MS-ACCT-004, MS-ACCT-010, MS-RETAIL-002, MS-RETAIL-004, MS-DINE-005, MS-PAY-002, MS-XCUT-004, MS-XCUT-005, MS-XCUT-006, MS-CRM-002, MS-HR-007, MS-HR-008

### Batch 9 — V1.1 (post-pilot)
MS-HR-003, MS-HR-004, MS-HR-006, MS-DINE-006, MS-HELP-002, MS-ECOM-001..005

---

## §A — Footnote: Items dropped from the original 36

| Original ID | Reason | Disposition |
|---|---|---|
| MS-CRM-003 (Loyalty Tiers Configuration) | Folded into MS-RETAIL-001 (4-tab loyalty screen includes tiers) | Build as Tiers tab inside MS-RETAIL-001 |
| MS-XCUT-002 (Roles Editor — full RBAC) | Already exists as `RolesHubV2` (1300+ LOC, see `SCREENS-INVENTORY-Common.md §4.3`) | Re-classify as "needs hardening" (write the assign-users diff, fix Quirk 4) — NOT a missing screen |

## §B — Open Uncertainties / Backend Asks for Mohammed

These need answers before some Cursor batches can proceed:

1. **MS-HR-010 EOSB** — backend gap. Need `/hr/eosb/{employeeId}/accrual` route + accrual service. Confirm timeline.
2. **MS-XCUT-001 Manager Override** — backend gap. Need `POST /auth/manager-override` route + capability table mapping. Confirm.
3. **MS-DINE-001 Aggregator Inbox** — verify list endpoint exists (`GET /aggregator/inbox`) — only the webhook ingester is in routes excerpt.
4. **MS-RETAIL-005 Stock Adjustments** — confirm reason-code taxonomy is server-enforced or FE-defined.
5. **MS-RETAIL-001 Loyalty Programs/Tiers** — verify `GET/POST /loyalty/programs`, `/loyalty/tiers` (only redeem + breakage are confirmed in excerpt).
6. **MS-PAY-001 Settlement Exceptions** — confirm route path: `/pay/settlement-exceptions` was flagged but not in routes excerpt.
7. **MS-ACCT-002 CoA Profiles** — confirm "compose" semantics: does `POST /coa-profiles/compose` accept an array of keys, or is it pairwise?
8. **MS-NOTIF-001/002** — confirm preferences shape: channel × event matrix, or simpler flat list?
9. **MS-HR-005 Expenses Approvals** — confirm `PATCH /hr/expenses/{id}/approve` exists (not in excerpt).
10. **MS-XCUT-006 Posting Bridges** — confirm whether bridges are tenant-editable or read-only (instantiated from CoA profile).

---

## Close-Out Report

```
✅ MISSING-SCREENS-INVENTORY.md delivered
Path: docs/handoff/MISSING-SCREENS-INVENTORY.md
Length: ~830 lines · ~52 KB

Summary:
- Total missing screens identified: 49
- V1.0 BLOCKER: 0
- V1.0 HIGH: 31
- V1.0 NICE: 12
- V1.1: 11 (incl. 5 ECOM bundled)

Origin breakdown:
- ORIGINAL (in starting list of 36): 38 retained, 1 folded, 1 dropped (re-classified)
- NEW (discovered while sweeping routes/api.php): 11

Per-module breakdown:
- Accounting: 11 missing screens (10 ORIGINAL + 1 NEW: tax codes)
- Retail/Catalog: 6 missing screens (4 ORIGINAL + 2 NEW: adjustments, transfers receive)
- HR: 11 missing screens (incl. ESS wiring as separate row)
- CRM: 2 missing (1 folded into Retail)
- Pay: 3 missing screens (1 was original-list-of-pay-reports + 2 NEW)
- Dine: 6 missing screens (all ORIGINAL — incl. QR deferred)
- E-commerce: 5 missing screens (entire module; ORIGINAL; all V1.1)
- Help: 2 missing screens (ORIGINAL)
- Notifications: 2 missing screens (ORIGINAL)
- Onboarding: 2 missing screens (ORIGINAL)
- Cross-cutting / Platform-side: 7 (all NEW from prompt's named-area list: manager override, MFA, devices, cost centers, posting bridges, fiscal calendar; one dropped — RBAC editor exists)

Cross-module patterns surfaced (build once, use everywhere):
- <EntityAuditDrawer>
- <DocumentLifecycleList>
- <KsaPhasedWizard>
- <RolePermissionedAction>
- <PartnerInbox>
- <KanbanBoard>
- <DiffMatchPane>

Cursor execution: 9 batches proposed in §5, ordered by priority × effort.

Open uncertainties: 10 backend asks for Mohammed (§B)
- 2 backend gaps blocking FE work (EOSB endpoint, manager-override route)
- 8 spec confirmations (route paths, payload shapes, list endpoints not in excerpt)
```
