
POS Retail
Offline-first Point of Sale & Back Office
A point-of-sale and back-office built for a real Cambodian retail shop. Prices are Riel-native, a can, a six-pack and a case are sold as one product, customers can run a tab, and the till keeps working without a connection, syncing sales back to the server once it is online again.
3
Roles: Admin, Manager, Cashier
KHR / USD
Dual currency display
Offline
Sales queue and sync
13
Screenshots
Features
Offline-first till
Sales rung up without a connection are queued on the device and replayed to the server when it is back online.
Riel-native pricing
Prices are stored in the shop currency with its own minor factor, so Riel never assumes cents. Toggle USD or KHR display with a configurable exchange rate.
Pack sizes as one product
A can, a six-pack and a case are the same product with different prices, so the grid shows one card with a price range.
Customer debt tabs
Put all or part of a bill on a named customer. Record payments as money comes in; a debt settles once paid in full.
Myself
Stock taken for own use goes down without counting as a sale, valued at shelf price for the week, month and year.
Public QR menu
A no-login mobile menu customers reach by scanning a QR code, grouped by category with every pack size.
Per-store stock
Stock lives per store, not on the product. Order numbers encode store and register (S1-R1-β¦).
One permission path
Every feature is gated by a Permission enum, route middleware and a policy. Roles are only bundles of permissions.
Audit trail
Model changes and money, auth and access events are logged with an explicit field list, so secrets never reach the activity log.
Reports and dashboard
Today versus yesterday, average basket, sales for the last 7 days, owed to you, and per-cashier activity.
Branding and dark mode
Upload a logo and favicon, set the order number prefix, and switch between light and dark themes.
Khmer and English
Bilingual product and category names throughout the till, menu and back office.
Architecture
Enums first
Permission, Role, Action, OrderStatus, PaymentMethod and SaleType define the vocabulary the whole app agrees on.
Inertia pages
Web controllers return Inertia pages mapped straight to resources/js/pages; shared props carry auth.can to every screen.
Services
OrderTotals, OrderSyncService for offline replay, and SalesReporter keep business rules out of controllers.
Policies
Per-model authorisation, all routed through hasPermission, never a role check.
shadcn-vue UI
A primitive component layer under components/ui with typed composables such as usePermissions and useCurrency.
Tests and CI
PHPUnit suite plus lint run on every push to main and develop via GitHub Actions.
Core Models
REST API for integrators
The token API reuses the same permission gates as the web app, so there is one authorisation path. Docs generate from controller annotations and ship with an integrator walkthrough.
Screenshots β Point of Sale
The till: search or scan, pack-size prices, cart, and the three ways a sale can end β paid, on a customer tab, or taken for yourself.





Screenshots β Back Office
Dashboard, catalogue and shop settings. Light and dark themes.





Screenshots β Authentication
Staff accounts are created by an administrator. Password reset uses a 6-digit emailed code.


Screenshots β Public QR Menu
Customers scan a QR code and browse the shelf on their phone, with every pack size and price.

Source code
The full Laravel + Vue codebase, migrations, seeders, tests and API docs are public on GitHub.
github.com/koeuk/POS-retail