Store credit
Store credit is financial, not promotional.
Operations
Fixing 403 on store-credit endpoints
If GET /store-credit/balance or POST /store-credit/issue returns 403 Forbidden:
- Restart the backend after any change to
packages/global/policies/src/rules/business.rules.ts(StoreCredit is granted to Administrator, StoreManager, Cashier, SalesAssociate, CustomerServiceRepresentative). - Your user’s role for the current business must be one of the above (or Owner). If the JWT does not contain
current_business_idorrole_by_business_id, the backend will resolve them when possible:- For
POST /store-credit/issue, sendinglocationIdin the body lets the backend resolvebusinessIdfrom the location and the user’s role from thebusiness_usertable, so the request can succeed without token custom claims. - For other endpoints, include
businessIdin the body/query when the token has no business context, or log out and log back in so the JWT gets fresh claims.
- For
How to add store credit to a customer
- Customer profile (PWA): Open the customer → Store Credit tab. Use the “Issue store credit” section: enter amount, click “Add credit”. Requires a location to be selected in the app.
- Return flow (PWA): Process a return, identify the customer, check “Issue as Store Credit”, then commit. The refund amount is issued as store credit to that customer.
- API (manual issue):
POST /store-credit/issuewith body:Use the same{
"customerId": "<uuid>",
"locationId": "<uuid>",
"amount": 50.00,
"sourceType": "manual",
"referenceNote": "Goodwill credit"
}Authorization: Bearer <token>as in the app. Requires StoreCredit Create permission. This is very important. Loyalty = marketing incentive Store credit = money the business owes the customer So store credit must behave like a wallet with accounting impact. Here’s what to add for Customer Management → Store credit. What “Store credit” means (business meaning) Store credit is a balance a customer can use instead of cash. Typical sources: returns without refund canceled layaway refunds goodwill compensation gift credit manual adjustment Store credit must: 👉 reduce revenue when issued 👉 behave like payment when used 👉 be fully auditable Core concept (very important) Store credit = Wallet + Ledger Never only store a balance. You must record: issuance usage adjustments expiration (later) Same philosophy as loyalty — but financial. What you must track Store credit account customer balance status Transactions issued used refunded (rare but possible) adjusted expired (later) Source linkage return id sale id layaway id manual reason This is critical for audits. Database additions (recommended)
- store_credit_account Fields: id business_id customer_id balance status created_at Balance is derived but stored for performance.
- store_credit_transaction (critical) Fields: id store_credit_account_id type (issue | use | adjust | expire) amount (money) source_type (return | sale | layaway | manual) source_id reference_note created_at created_by Never delete rows.
- Payment integration (very important) When using store credit in checkout: You must create: payment record with method = store_credit store_credit_transaction (use) They must match. This ensures reconciliation works. Backend functionality you need Issue credit (core) Triggered by: return without cash refund cancel layaway manual credit Flow: create transaction (issue) update balance Use credit in POS Flow: check available balance allow partial use create payment record create store_credit_transaction (use) Adjust credit (admin) Manual corrections: require reason audit logged role restricted Endpoints get balance issue credit use credit history admin adjustment Frontend screens (PWA) POS flow (critical) Customer attached → show: store credit balance “Use store credit” option allow partial usage Must be simple and safe. Customer profile → Store credit tab Show: balance history timeline source references (return, layaway, etc.) adjustments Transparency is very important. Reports (Metabase — financially important) total store credit liability (very important) issued vs used credit credit aging credit by source (returns, goodwill, etc.) unused credit risk employee-issued credit (fraud control) Store credit appears on balance sheet as liability. Retail vs Restaurant usage Retail: very common (returns) layaway cancellations goodwill credits Restaurant: less common but used for refunds, complaints, gift credit Same architecture works. MVP vs Phase 2 ✅ MVP store credit store_credit_account store_credit_transaction ledger issue from return use in POS as payment history UI partial usage audit 🚀 Phase 2 expiration rules cross-location usage rules gift card unification multi-currency credit transfer between customers fraud alerts credit policies Biggest edge cases (very important) Return funded by store credit → restore credit Exchange with store credit involved Split payments (credit + cash) Credit issued after discount Negative balance prevention Refund after credit usage Multi-location restrictions Offline mode reconciliation These must be defined clearly. Strategic insight for FlowPOS (important) Store credit connects: returns layaway payments accounting customer relationship It is one of the most sensitive financial features. If you model store credit with ledger now → audits become easy later. If you want, next I can give you: Minimal Kysely schema for store credit ⭐ recommended Gift card vs store credit architecture (very important distinction) Payment architecture (critical POS core) Refund engine design (ties many things together) Liability reporting model (Metabase) How store credit interacts with loyalty ⭐ important