feat: change email template + add list of items

This commit is contained in:
2026-10-09 09:30:26 +02:00
parent 6f237a937a
commit 5246aeabc1
17 changed files with 474 additions and 55 deletions
+48 -12
View File
@@ -17,12 +17,38 @@ let token = '';
let cursor: string | null = null;
let venueId = '';
let registrationCode = '';
const openTabs: Map<string, { customerName: string; version: number; totalInCents: number; itemCount: number }> = new Map();
type TabLine = { productName: string; quantity: number; unitPriceInCents: number };
type SimTab = { customerName: string; version: number; items: TabLine[] };
const openTabs: Map<string, SimTab> = new Map();
let pendingCommands: Array<{ id: string; type: string; tabId: string; expectedVersion: number; paymentMethod: string }> = [];
let tabCounter = 0;
let plannedNames: string[] = [];
let plannedIndex = 0;
// A small bar menu to fill tabs with
const MENU: Array<{ productName: string; unitPriceInCents: number }> = [
{ productName: 'Cola', unitPriceInCents: 250 },
{ productName: 'Jupiler', unitPriceInCents: 280 },
{ productName: 'Duvel', unitPriceInCents: 450 },
{ productName: 'Spa rood', unitPriceInCents: 230 },
{ productName: 'Koffie', unitPriceInCents: 250 },
{ productName: 'Chips', unitPriceInCents: 200 },
];
const tabTotal = (tab: SimTab) => tab.items.reduce((sum, line) => sum + line.quantity * line.unitPriceInCents, 0);
const tabItemCount = (tab: SimTab) => tab.items.reduce((sum, line) => sum + line.quantity, 0);
const euro = (cents: number) => `€${(cents / 100).toFixed(2)}`;
/** 1 to 3 different products, 1 to 4 of each. */
function randomLines(): TabLine[] {
const shuffled = [...MENU].sort(() => Math.random() - 0.5);
return shuffled.slice(0, Math.floor(Math.random() * 3) + 1).map((product) => ({
...product,
quantity: Math.floor(Math.random() * 4) + 1,
}));
}
// ── API helpers ──────────────────────────────────────────
async function api<T = any>(endpoint: string, options: RequestInit = {}): Promise<T> {
const { headers: customHeaders, ...rest } = options;
@@ -42,7 +68,12 @@ async function api<T = any>(endpoint: string, options: RequestInit = {}): Promis
// The server treats openTabs as the complete set: tabs left out are considered closed
function buildTabsPayload() {
return Array.from(openTabs.entries()).map(([id, t]) => ({
id, customerName: t.customerName, version: t.version, totalInCents: t.totalInCents, itemCount: t.itemCount,
id,
customerName: t.customerName,
version: t.version,
totalInCents: tabTotal(t),
itemCount: tabItemCount(t),
items: t.items,
}));
}
@@ -100,10 +131,10 @@ function addTab() {
const names = plannedNames.length > 0 ? plannedNames : fallbackNames;
const name = names[plannedIndex % names.length];
plannedIndex++;
const items = Math.floor(Math.random() * 5) + 1;
const total = items * (Math.floor(Math.random() * 10) + 5) * 100;
openTabs.set(tabId, { customerName: name, version: 1, totalInCents: total, itemCount: items });
console.log(` 📋 Tab added: ${name} — €${(total / 100).toFixed(2)} (${items} items) [${tabId.substring(0, 8)}]`);
const tab: SimTab = { customerName: name, version: 1, items: randomLines() };
openTabs.set(tabId, tab);
const lines = tab.items.map((line) => `${line.quantity}x ${line.productName}`).join(', ');
console.log(` 📋 Tab added: ${name} — ${euro(tabTotal(tab))} (${lines}) [${tabId.substring(0, 8)}]`);
}
async function sync() {
@@ -151,11 +182,13 @@ async function ackAll() {
});
console.log(` ✅ Acked ${cmd.id.substring(0, 8)} as ${status}`);
// If completed, remove the tab from local state
if (status === 'completed') {
openTabs.delete(cmd.tabId);
console.log(` Removed tab ${cmd.tabId.substring(0, 8)} from local state`);
} else {
// Like the real app, closing settles the tab: its lines are cleared but the tab stays open
const settled = openTabs.get(cmd.tabId);
if (status === 'completed' && settled) {
settled.items = [];
settled.version++;
console.log(` Settled tab ${cmd.tabId.substring(0, 8)} (now empty, v${settled.version})`);
} else if (status !== 'completed') {
// Bump version on failed close
const tab = openTabs.get(cmd.tabId);
if (tab) {
@@ -177,7 +210,10 @@ function listTabs() {
}
console.log(`\n 📋 Open Tabs (${openTabs.size}):`);
Array.from(openTabs.entries()).forEach(([id, t]) => {
console.log(` ${id.substring(0, 8)} — ${t.customerName} — €${(t.totalInCents / 100).toFixed(2)} (v${t.version})`);
console.log(` ${id.substring(0, 8)} — ${t.customerName} — ${euro(tabTotal(t))} (v${t.version})`);
for (const line of t.items) {
console.log(` ${line.quantity}x ${line.productName} ${euro(line.quantity * line.unitPriceInCents)}`);
}
});
}