aboutsummaryrefslogtreecommitdiffstats
path: root/tools
diff options
context:
space:
mode:
authorAdam Soltys <[email protected]>2026-09-21 11:15:11 -0700
committerAdam Soltys <[email protected]>2026-09-21 11:15:11 -0700
commit01827dd23f29a6e0d6db673f5dc330cd7f4a6f4f (patch)
treef4634d212fe5a81020afcc51fe8a0cb9fa5f20f9 /tools
parent792b15ffbb90b82f1e6c07ce5430bae18f239f1e (diff)
downloadcoinosv3-01827dd23f29a6e0d6db673f5dc330cd7f4a6f4f.tar.gz
coinosv3-01827dd23f29a6e0d6db673f5dc330cd7f4a6f4f.zip
Point of sale: a paid sale opens its payment detail, which now says bill and tip.
The row finds the ln-receive movement by the invoice it recorded and opens the same detail screen the history page shows; the detail asks features for more (arkMoveDetailExtra) and the till adds Bills, Tips (with the percentage) and the note. Co-Authored-By: Claude Fable 5.1 <[email protected]> Claude-Session: https://claude.ai/code/session_01Tmfg8k5f3TbNJS34qiqHAp
Diffstat (limited to 'tools')
-rw-r--r--tools/pos-test.js10
1 files changed, 9 insertions, 1 deletions
diff --git a/tools/pos-test.js b/tools/pos-test.js
index 4882279..6e3d801 100644
--- a/tools/pos-test.js
+++ b/tools/pos-test.js
@@ -24,10 +24,11 @@ const ctx = {
if (name === 'arkLnWatch') { watch = { id: a[0], cb: a[1] }; return true; }
if (name === 'arkLnUnwatch') { if (watch && watch.id === a[0]) watch = null; return true; }
if (name === 'arkLnCancel') { cancelled.push(a[0]); return Promise.resolve(true); }
+ if (name === 'arkMovements') return window.__movements || [];
return null;
},
};
-const feature = posFeature(ctx);
+const feature = posFeature(ctx); window.__feature = feature;
function render() { document.querySelector('#app').replaceChildren(feature.screenView() || h('div', { id: 'closed' }, 'closed')); }
window.test = { open: () => { feature.openPos(); }, init: () => { feature.init(); render(); }, settle: (ok) => { const w = watch; watch = null; w.cb({ step: ok ? 'done' : 'failed' }); }, get watch() { return watch && watch.id; }, get cancelled() { return cancelled; }, get sales() { return (state.pos || {}).sales || []; }, ui };
render();
@@ -81,6 +82,13 @@ try {
check('settlement shows Paid with the breakdown', /Paid/.test(await text()) && /Bill 1,000 \+ tip 150 sats/.test(await text()));
await click('New sale'); await pause(50);
check('the ledger keeps the bill and the tip apart', /Bills 1,000 sats/.test(await text()) && /Tips 150 sats/.test(await text()) && /Total 1,150 sats/.test(await text()) && /Table 4/.test(await text()));
+ await page.evaluate(() => { [...document.querySelectorAll('.pos-sale')].find((r) => /Table 4/.test(r.textContent)).click(); }); await pause(50);
+ check('a sale with no payment record yet says so', await page.evaluate(() => (window.toasts || []).at(-1) === 'No payment record for this sale yet'));
+ await page.evaluate(() => { window.__movements = [{ id: 'mv1', type: 'ln-receive', status: 'complete', amountSat: 1150, invoice: 'lnbc1150n1testinvoice1', ts: Date.now() }]; });
+ await page.evaluate(() => { [...document.querySelectorAll('.pos-sale')].find((r) => /Table 4/.test(r.textContent)).click(); }); await pause(50);
+ check('a paid sale opens the payment detail by its movement', await page.evaluate(() => test.ui.arkMoveDetail === 'mv1'));
+ check('...and the detail knows the bill, the tip and the note', await page.evaluate(() => { const lines = window.__feature.arkMoveDetailExtra(window.__movements[0], null).filter(Boolean).map((n) => n.textContent); return JSON.stringify(lines); }) === JSON.stringify(['Bills1,000 sats', 'Tips150 sats (15%)', 'NoteTable 4']));
+ await page.evaluate(() => { test.ui.arkMoveDetail = null; });
console.log('\n[a custom tip, then a cancelled sale]');
await type('.pos-amount', '2000'); await click('Charge'); await pause(50);