At a Glance
Persona: Audit / Config (Inventory Controller + Finance + Sysadmin + Auditor) · Module: store-requisition · Scenarios: ~27
Categories: Happy Path · Permission · Validation · Edge Case
E2E coverage: largely manual / planned; closest automated coverage istests/701-sr.spec.tsTC-SR-060005 (Delegate Approvals) in../carmen-inventory-frontend-e2e/
This page captures the test scenarios that the Audit / Config persona — comprising Inventory Controller (variance, admin void on pre-commit, post-commit adjustment co-author), Finance (closed-period block, journal-entry verification, cost-centre reconciliation, period close), System Administrator (RBAC, workflow / tb_workflow config, SoD-relaxation thresholds, recipe auto-create wiring), and Auditor (read-only SR history review, signature trace, SoD enforcement verification) — directly drives in the store-requisition module. Unlike the four operational personas (Requester, Approver, Fulfiller, Receiver) who work the happy-path lifecycle, the Audit / Config sub-roles act on the periphery: before any SR exists (config), during the flow (variance monitoring, period-close enforcement), and after commit (signoff, audit). Scenarios are grouped into happy paths (variance review, admin void on pre-commit, closed-period block, period close, RBAC / workflow config, audit signature trace), RBAC (admin void only on pre-commit, Finance closed-period authority, Sysadmin workflow config, Auditor read-only), validation (negative tests around mis-routed workflow, SoD breaches detected at audit, recipe auto-create failures), and edge cases around multi-tenant config, period-reopen, large-scale period-end batch, and Auditor sample testing. Cross-persona handoffs that pivot off this persona (Scenarios 7, 10, 11, 13, 14 in the parent overview — discrepancy resolution, closed-period block resolution, admin void, period close, workflow / RBAC config change) live in 04-test-scenarios.md, not here.
| # | Scenario | Pre-condition | Steps | Expected |
|---|---|---|---|---|
| AC-HP-01 | Inventory Controller — variance dashboard review | Mix of completed SRs in current period; some with requested_qty − issued_qty > 0 (variance), some with approved_qty − issued_qty > 0 (fulfilment gap), some clean. |
1. Inventory Controller opens the variance dashboard. 2. Filters by outlet Main-Kitchen, period 2026-05. 3. Drills into an outlier SR with large variance. 4. Reads per-line approved_message (trim reason), system comments (at-issue stock-out, if any), and Receiver comments (delivery discrepancy, if any). 5. Decides outcome: log for trend, raise coaching action, or post compensating adjustment. |
Dashboard surfaces all completed SRs in scope with computed variance_qty and fulfilment_gap per line per SR_CALC_002 / SR_CALC_003; drill-down view shows the full audit chain; the SR module is read-only at this step (no state changes); any corrective action is via separate documents ([inventory-adjustment](/en/inventory/inventory-adjustment) for material gaps, operational reviews for chronic patterns). |
| AC-HP-02 | Inventory Controller — admin void on pre-commit SR | SR SR-A is at doc_status = draft (or early in_progress, before any approver action); audit hold raised on the requester due to a compliance review. |
1. Inventory Controller opens SR-A. 2. Clicks Admin Void. 3. Enters reason "audit hold on requester — compliance review pending". 4. Confirms. |
doc_status = draft → voided (or in_progress → voided) per SR_POST_010 and SR_AUTH_013; reason text persisted; no inventory or GL impact (the SR never posted); SR terminates; requester is notified; the void event is logged in workflow_history and is auditable. Distinct from cancelled (which is the user-initiated retraction path). |
| AC-HP-03 | Finance — closed-period commit block holds line | Period 2026-04 is closed; Fulfiller attempts to commit an SR with last_action_at_date mapping to a date in 2026-04. |
1. Fulfiller hits Commit. 2. SR_VAL_014 blocks server-side. 3. Finance receives the alert ticket. 4. Finance options: (a) reopen 2026-04 briefly with CFO sign-off, (b) ask Fulfiller to advance posting date to 2026-05, (c) authorise admin void if the underlying transaction is no longer correct. |
The closed-period block is the canonical Finance gate; SR stays in_progress; no partial / silent post; Finance's decision determines downstream path; if reopen, the same commit re-tries and posts; if date-advance, the commit re-tries against current period; if void, SR_POST_010 fires. Period-close metric: number of stuck in_progress SRs at period boundary. |
| AC-HP-04 | Finance — period-end reconciliation | All completed SRs in period 2026-05 for outlet Main-Kitchen; outlet food-cost report computed independently. |
1. Finance queries SELECT Σ (issued_qty × cost_per_unit) FROM tb_store_requisition_detail JOIN tb_inventory_transaction WHERE store_requisition.to_location_id = Main-Kitchen AND last_action_at_date IN period 2026-05. 2. Compares with the outlet's food-cost expense from GL. 3. Investigates any gap (missed adjustment, mis-dimension, FX issue, timing). 4. Issues period-close signoff. |
The reconciliation is a read-only verification step; the SR module sees no state change; the signoff (logged outside the SR module) closes the period and locks subsequent commits with posting dates in 2026-05 (SR_VAL_014 future behaviour). Material gaps escalate to Inventory Controller for corrective adjustment co-authoring. |
| AC-HP-05 | Sysadmin — workflow stage configuration | Tenant decides to add a second approval tier above ฿10,000; Sysadmin updates tb_workflow. |
1. Sysadmin opens the workflow config console. 2. Edits the workflow associated with the SR module: adds a second approval stage with role Operations Manager and threshold value > 10000. 3. Saves. 4. Tests via a sample SR with Σ requested_qty × catalog_price = ฿12,000. |
New workflow rule applies prospectively to new SRs from save time onward; existing in-flight SRs are NOT re-routed automatically (Sysadmin coordinates with Inventory Controller if needed); the sample SR enters the second approval stage after first-stage approval; workflow_current_stage advances to approval-stage-2; user_action.execute populated with Operations Manager users. |
| AC-HP-06 | Sysadmin — SoD-relaxation threshold | Sysadmin sets the SoD-relaxation threshold to "Approver = Fulfiller allowed for SRs < ฿5,000". | 1. Sysadmin updates the config. 2. Saves. 3. Tests: a sample SR at total value ฿2,500 with same user as Approver and Fulfiller commits successfully (FUL-HP-06 pattern). 4. Tests: a sample SR at total value ฿15,000 with same user is blocked (FUL-PERM-04 pattern). | Threshold applied at the commit-time SoD check (SR_AUTH_012); below threshold the check is skipped with a system comment recording the relaxation; above threshold the check enforces normally. Auditor can find all SRs that committed under relaxation by querying for the relaxation system comment pattern. |
| AC-HP-07 | Auditor — read-only signature trace | Sample committed SR from period 2026-05; Auditor selects 30 SRs across outlets for the period sample. |
1. Auditor opens each SR in read-only mode. 2. Verifies created_by_id (Requester) ≠ approved_by_id (Approver) per line per SR_AUTH_011. 3. Verifies approved_by_id (Approver) ≠ last_action_by_id at commit (Fulfiller) per SR_AUTH_012, except where SoD relaxation applies. 4. Verifies per-line history JSON timeline matches workflow_history and comment threads. 5. Verifies that material variance has a corresponding investigation comment. |
Audit findings published outside the SR module; the SR is unaffected operationally. Findings may trigger Inventory Controller / Sysadmin / Finance corrective actions: tightening SoD thresholds, re-training, workflow improvements, or escalating specific incidents. The SR audit data (per-line signatures, history, workflow_history, comment threads) is the canonical source. |
| # | Scenario | Expected behaviour (allow/deny + reason) |
|---|---|---|
| AC-PERM-01 | Inventory Controller / Sysadmin voids pre-commit SR | Allow. Per SR_AUTH_013. The Admin Void button is enabled on draft and in_progress SRs for these roles. Reason is mandatory; void writes voided terminal state; no inventory / GL impact. |
| AC-PERM-02 | Inventory Controller attempts to void completed SR |
Deny — terminal state. Per SR_AUTH_013. The Admin Void button is hidden on completed SRs; direct API call rejects with "Cannot void a committed SR; post-commit corrections must use inventory-adjustment." Per SR_POST_010's "Voiding a completed SR is not allowed" rule. |
| AC-PERM-03 | Finance closes a period | Allow. Finance period close locks SR_VAL_014 against subsequent commits with posting dates in the closed period. The period close action lives in the finance module (not in the SR module); the SR module reads the closed-period state at commit time. |
| AC-PERM-04 | Non-CFO user attempts to reopen a closed period | Deny — period reopen authority. Period reopen typically requires CFO / Finance Manager sign-off. The SR module is a downstream consumer of the period state; the authorization is enforced in the finance module. From the SR side, the only visible effect is that SR_VAL_014 continues to block commits until the period reopens. |
| AC-PERM-05 | Sysadmin edits tb_workflow config |
Allow. Sysadmin owns the workflow configuration. Changes apply prospectively from save time; in-flight SRs are NOT re-routed automatically (Sysadmin coordinates with Inventory Controller for re-routing if needed). |
| AC-PERM-06 | Non-Sysadmin user attempts to edit RBAC | Deny. RBAC matrix per location / department is Sysadmin-only. Direct API call rejects with "You are not authorized to modify role assignments." |
| AC-PERM-07 | Auditor attempts to write any column on tb_store_requisition |
Deny — Auditor read-only. Auditor has no write permission on any SR table column. Direct write attempts (via API or UI workarounds) reject with "Auditor role is read-only." Comment writes (e.g. audit findings) are typically logged in a separate audit-findings system, not on the SR comment table. |
| AC-PERM-08 | Inventory Controller attempts to post inventory-adjustment without Finance co-auth (above threshold) | Deny — co-authorisation required. Per SR_XMOD_009, post-commit corrections via [inventory-adjustment](/en/inventory/inventory-adjustment) for material values require co-authorisation by Inventory Controller AND Finance. Below tenant threshold the Inventory Controller may post alone; above threshold the adjustment is held for Finance approval. The block is enforced in the inventory-adjustment module, not the SR module. |
| # | Scenario | Trigger | Expected error |
|---|---|---|---|
| AC-VAL-01 | Admin void without reason | Inventory Controller clicks Admin Void but submits with empty reason text. | Reject — reason is mandatory for SR_POST_010. Server returns "Reason text is required for administrative void." |
| AC-VAL-02 | Period close while there are stuck in_progress SRs |
Finance attempts to close period 2026-05 but there are 3 SRs still at doc_status = in_progress with stale workflow stages. |
Warn — period close anomaly. The period close action may proceed (depending on tenant policy) but Finance is notified of the stuck SRs and asked to coordinate with Inventory Controller (resolve via admin void or push commit). The period close itself is a finance-module action; the SR module's role is to surface the count of stuck SRs to the close dashboard. |
| AC-VAL-03 | Workflow config change creates orphaned in-flight SRs | Sysadmin removes a workflow stage that has in-flight SRs at it; the SRs lose their workflow_current_stage mapping. |
Warn at save — UI surfaces a warning ("This change orphans 7 in-flight SRs at stage <removed-stage>; proceed to migrate them to a different stage?"). Sysadmin either cancels the change, picks a target stage to migrate to, or proceeds and accepts that the orphaned SRs need manual intervention. Per SR_AUTH_014 semantics (stage gating requires a valid stage). |
| AC-VAL-04 | SoD breach detected at audit | Auditor finds an SR where requestor_id = approved_by_id on at least one line (SoD SR_AUTH_011 should have blocked this). |
Audit finding — investigate root cause. The breach indicates a system gap (the SR module's SoD check failed) or a workflow misconfig (the workflow allowed the same user to be in both roles). Auditor publishes the finding; Sysadmin / Inventory Controller investigate the path; corrective action ranges from a system patch (if SoD check was bypassed) to policy reinforcement (if the workflow was intentionally configured permissively). |
| AC-VAL-05 | Recipe auto-create fails for a planned banquet event | [recipe](/en/inventory/recipe) module fails to post the SR draft (recipe-product mapping broken, source-location resolution failed, requester user not found). |
System alert — Sysadmin investigates. The Sysadmin checks the wiring: recipe-product mapping, source-location resolution, requester user lookup, location permission check. Ad-hoc fix posts the SR draft manually with info.recipe_id carried over; the underlying wiring is fixed for subsequent events. |
| # | Scenario | Condition | Expected |
|---|---|---|---|
| AC-EDGE-01 | Bulk period-end reconciliation across many outlets | Period 2026-05 has 50+ outlets, 2,000+ completed SRs; Finance runs the reconciliation across all. |
Performance + correctness. The reconciliation query is server-side, indexed appropriately (per SR_XMOD_004 cost-feed and dimension for cost-centre rollup); runs in tenant-acceptable time; returns per-outlet, per-cost-centre rollups; gaps surfaced as a list of SR-id + outlet + gap-amount for investigation. The SR module performance is dominated by joins to tb_inventory_transaction / tb_inventory_transaction_cost_layer. |
| AC-EDGE-02 | Audit sampling across multi-tenant config | Auditor samples committed SRs across two tenants in the same Carmen deployment; the two tenants have different SoD thresholds. | Per-tenant context preserved. The audit query scopes to one tenant at a time (the x-app-id header / tenant context is part of the auth boundary); per-tenant SoD thresholds and workflow configs are applied to the audit findings; cross-tenant comparisons are operational analytics, not SR audit. |
| AC-EDGE-03 | Period reopen window with re-commit of previously blocked SRs | Period 2026-04 reopened by CFO for 24h to allow 5 stuck SRs to commit; SR Fulfillers re-attempt commit. |
Time-bounded reopen. The 5 SRs commit with last_action_at_date falling in 2026-04; inventory transactions and journal entries are written into 2026-04; outlet food-cost reports for 2026-04 re-roll up. After the 24h window, the period re-closes; SR_VAL_014 reverts to blocking. Audit captures the reopen / re-close events. |
| AC-EDGE-04 | Admin void with a downstream inventory transaction already linked (data anomaly) | An SR is at in_progress; the linked tb_inventory_transaction exists in a pre-staged state (FUL-EDGE-05 pattern). Inventory Controller admin-voids. |
Void cleans up staged inventory transaction. Per SR_POST_010, void on a pre-commit SR must NOT leave a dangling inventory transaction. The void action clears the staged transaction reference; if the staged transaction was inserted but not committed, the void deletes it or marks it voided per tenant policy. Auditor verifies no orphaned tb_inventory_transaction rows with inventory_doc_type = store_requisition and no corresponding tb_store_requisition.id. |
| AC-EDGE-05 | Auditor samples a transfer-type SR for full lifecycle trace | Sample SR is sr_type = transfer; Auditor traces from tb_store_requisition → tb_store_requisition_detail → tb_inventory_transaction (paired OUT + IN rows) → tb_inventory_transaction_detail (lot data at both ends) → cost-layer consumption at source and creation at destination → journal entry Dr destination inventory / Cr source inventory. |
Full audit trace possible. All foreign keys / back-references are explicit (the SR-side inventory_transaction_id has an explicit Prisma @relation); cost-layer linkage is through tb_inventory_transaction_cost_layer; journal entries are joinable via SR sr_no. Auditor finds the trace complete; flags any missing link as an audit gap. |
| AC-EDGE-06 | Workflow re-routing of in-flight SRs after a config change | Sysadmin adds a new approval stage after Stage 1 and before Fulfilment; needs to re-route 12 in-flight SRs currently at "Fulfilment" stage back to the new "Stage 1.5" for the new approval check. | Manual coordinated re-route. The system does NOT auto-re-route (Sysadmin coordinates with Inventory Controller); each in-flight SR is touched individually with workflow_current_stage = 'stage-1.5', user_action.execute repopulated; a system comment notes the re-route; the affected fulfillers and new approvers are notified. Alternatively, the in-flight SRs are allowed to complete under the old workflow, and only new SRs use the new stage (less disruptive). |
| AC-EDGE-07 | Auditor finds variance pattern across multiple SRs from one outlet | Auditor's sample reveals that outlet Banquet-Hall has had requested_qty − approved_qty gap of > 30% on 12 SRs in 2026-05 (chronic over-requesting). |
Operational finding, not a system breach. The SR module is functioning as designed (Approver is trimming as expected); the finding is operational (the outlet's demand planning is poor). Inventory Controller raises a coaching action; Sysadmin may tighten the par-level discipline; Auditor's finding is logged. SR data unchanged. |
SR_VAL_014 (closed-period block at commit); Section 4 — SR_AUTH_009 (Inventory Controller authority), SR_AUTH_010 (Finance authority), SR_AUTH_011–SR_AUTH_012 (SoD rules — Auditor verifies, Sysadmin configures relaxation), SR_AUTH_013 (admin void), SR_AUTH_014 (workflow-stage gating); Section 5 — SR_POST_010 (admin void posting effects), SR_POST_013 (Receiver discrepancy flag); Section 6 — SR_XMOD_009 (post-commit correction via inventory-adjustment).../carmen-inventory-frontend-e2e/tests/701-sr.spec.ts — note: Audit / Config scenarios (AC-HP-01..07, AC-EDGE-01..07) are largely manual / planned at the time of writing. Closest automated coverage: TC-SR-060005 (Delegate Approvals for Unavailable User — touches the delegation aspect of AC-HP-06 / AC-EDGE-06). Other automated tests touch the persona only as a side effect (e.g. Sysadmin-configured workflow gates appear in the requestor@blueledgers.com permission-denial paths).tb_inventory_transaction_cost_layer for unit costs.