dev to main - #839
Merged
Merged
dev to main#839
Conversation
Owner, holding a printed bill from Azure: "Table number, order type, covers, total quantity all these information can organize better as per international standards and may be two column or moving total quantity to bottom." Two different mistakes, and he is right about both. FOUR FACTS TOOK FOUR LINES. Table, order type and covers are read at a glance, not down a list, and stacked one per line they pushed the items further down the paper than the things a guest is actually checking. They now sit two to a line with a two-character gutter, because without one the left value runs straight into the right label and prints "6AOrder type". Narrow paper keeps one to a line on purpose. A 58mm roll is 32 characters; halved that turns "Order type" into "Order ty.", and losing a word to save a line is the wrong trade on the document the guest keeps. THE COUNT WAS IN THE WRONG PLACE ENTIRELY. Total quantity is not a fact about the table, it is part of the arithmetic: how many things, what they came to. It sat in the header beside the table number, which is where the restaurant looks and not where the guest does. It now prints immediately above the subtotal, and the test pins that nothing is allowed between the two. 7 new tests, driven through the real renderer and read back out of the bytes with escpos-preview. The switch-liveness test learned where the count went rather than being loosened - it still refuses a switch that changes nothing, it just no longer assumes every switch writes a header row. 2809 desktop tests pass. Two api suites fail to load on main already, from an earlier merge, and are untouched by this.
It asserted the exact contents of serviceRows, including
{ label: 'Total Qty', value: '5' }, so moving the count down to the
totals read as a deletion.
Taught rather than loosened. It still pins every other service row
exactly, and now also asserts the count is on the payload as totalQty,
is NOT in serviceRows, and actually prints - so the row cannot quietly
disappear altogether, which is the thing the original assertion was
there to prevent.
Four failures on develop, none of them from a feature, all of them the same shape: a thing that is generated or counted, and a change that did not regenerate it. tests/unit/routes/items.routes.test.js mocked the validation middleware and did not list validateSoldOut, so the route got `undefined` where a handler belongs. router.post throws "argument handler must be a function" at REQUIRE time, which fails the whole suite before a single test runs - 2 suites, 0 tests. The route itself is fine and is serving in production. tests/unit/middleware/items.validation.test.js fakes the express-validator chain link by link, and the sold-out validator uses isBoolean, which the fake did not have. Same failure mode: not at the assertion, at require. The fake now carries every link the real chain offers, so the next validator does not do this again. languages/server/_english.json was out of date; the tool that writes it says so by name in the failure message. The README's REST badge said 658 and there are 659 routes. Whitespace, a generated file, a number and two test fakes. No behaviour. All four are the cost of the same missing habit: when a change adds a route, a message or a validator, something generated has to be regenerated, and nothing says so until CI does.
Develop is green again, for the third time
The bill reads like a bill
Owner: "whenever new KOT received one tink sound with full sound i want.
need to place in kitchen. if possible read the items. Example Table 5 new
order. Ting! one chicken briyani, one chicken tikka masala."
A printer in a kitchen is silent and a ticket is small. A cook with their
hands in a pan does not see one arrive, and the first anybody knows is a
waiter asking where the food is. A speaker says it across the room
without anybody having to look at anything.
Table 5, new order. One Chicken Biryani. One Chicken Tikka Masala.
THE TING FIRST, AND THE WORDS WAIT FOR IT rather than starting on a
timer. A speaker still ringing while it talks loses its first two words,
and the first two words are the table number - the one part nobody can
work out from the rest. A third tone, deliberately not either of the
existing two: a cook must never have to decide whether that was their
ticket or the counter's online order.
SAID WHEN THE TICKET IS CLAIMED, not after it prints. A jammed or empty
printer is exactly when a kitchen most needs to hear that a table
ordered; the silent failure this exists for is a ticket nobody knows
about. Behind the same claim that stops a ticket printing twice, so a
poll that sees the job again does not say it again.
SIX LINES, THEN HOW MANY ARE LEFT. Six courses from a table of six
arrive within seconds - kot-manager already debounces printing for that
reason. Read in full it is a minute of talking, and a kitchen that has
stopped listening does not hear the next one either. The paper still has
the detail.
NAMES AND COUNTS ONLY. Not notes, not descriptions, not prices. What
makes announcements fail is never that they said too little.
OFF BY DEFAULT AND PER MACHINE, not per shop. Only the machine at the
pass has the speaker. A shop-wide switch would make the counter talk in
front of customers, somebody would mute the counter, and on many installs
that is the same Windows volume the kitchen speaker is on. A till that
started announcing orders after an update is a support call.
English, by the owner's choice: "All english as of now."
A test caught a real mistake: bracketed text was being stripped from
names to drop decoration like "(Half)", which turned "Gobi (65)" into
"Gobi" - a different dish. The shop's name is the shop's.
Twelve tests, on the sentence and the switch, because those are the parts
that can be wrong without anybody noticing until service. The tone and
the speech engine belong to a sound card and a Windows voice, which a
test cannot stand in for honestly - this needs one try on the kitchen
machine before anybody trusts it.
A shop changed its address and its till kept printing the old one on
every bill. Not for a moment - for ten months. Its branch document still
carried updated_date equal to created_date, and every settings change it
had ever made was correct in the cloud, correct on the web, and invisible
to the machine at the counter.
Nothing had failed. The sync gateway offers a device only the rows whose
watermark has moved:
{ updated_date: { $gt: since.ts } }
{ $expr: { $gt: ['$updated_date', '$_syncMeta.at'] } }
and the settings write goes through the NATIVE driver, so the schema's
timestamps: { updatedAt: 'updated_date' } never fires. Nothing else set
it either. The row was simply never eligible to travel, and there is no
error for that.
Two lines, on both branch writes - the feature switches and the
locale/currency block. Fixing one and not the other would be worse than
fixing neither, because half a settings screen that syncs looks like a
settings screen that works.
5 tests, and they assert on what actually reaches updateOne rather than
on a helper the save path might not call. One of them pairs every write
with the collection it opened, so a new branch write that forgets the
stamp fails rather than joining the pattern. Checked by deleting one of
the two stamps and watching it fail.
This is the family this codebase keeps producing: a thing written,
correct, and read by nobody. Same as the module packaged where nothing
could require it, and the guard whose regex could never match.
Found because a shop's own bill printed the wrong address after the
cloud had been right for an hour.
The kitchen hears a ticket arrive
A setting that reaches the till
Owner: "whenever market price or quick sale we want print the price in the KOT... lets customer wants to have fish for rs500 so that kitchen will prepare according to that." Five hundred rupees of fish is a particular fish. For a dish priced at the table the price IS the specification, and a kitchen cannot pick the right one from the name alone. For an ordinary dish off the card it is noise. A cook does not choose a biryani differently because it costs 220, and a ticket with money on every line is one where the line that matters stops standing out. So the till marks two kinds of line and no others: a dish priced at the table, and a one-off invented for this bill. A quick sale needed naming separately. It HAS a catalogue price - it was created a moment ago - so the dynamic test alone would have missed it, and its price was still agreed with a guest rather than chosen on a card. A dish whose daily price was set this morning prints no price, because then the card prices it like any other dish. That is the whole point of a shop updating it when they open. NOT IN THE NOTE, though that was the suggestion. The note is what a waiter typed. Putting anything else in it is exactly the bug that printed a marketing paragraph to a kitchen this morning, and it would be the same mistake with a different field. "Rs" rather than the rupee sign: a kitchen printer that lacks the glyph prints a box or a random character, and a wrong number on a ticket is worse than a plain one. Bold, because on these lines the amount is part of what to cook. Eleven tests. One of them caught my own test helper eating the double E in SEER: it stripped the letters ESC/POS uses as command parameters, which are the same letters dishes are spelled with.
…is-worth The kitchen is told what it is worth, where that matters
The packaging check caught this on the promotion PR, which is exactly
where it is meant to: the three files added for the kitchen announcement
were required at runtime and absent from build.files.
src/order-alert.js requires src/kitchen-call.js
src/kot-manager.js requires src/kitchen-announce.js
src/main.js requires src/kitchen-announce.js
A packaged installer would have started and then failed with "Cannot find
module" on a customer machine, and nowhere else - not here, not in CI,
not on any machine running from source. That is the whole reason this
check exists, and the reason it runs before a release rather than after
one.
Found the night this was going to a client.
The kitchen files are packaged, or the installer cannot find them
Three things the owner asked about, and one he did not, which was the one that would have kept the speaker silent. A PAUSE BETWEEN DISHES. Owner: "little pause between line items." The announcement was one sentence with full stops in it. A full stop is a shorter gap than a kitchen needs, so it is now one utterance per line and the engine leaves a real gap between them - long enough to hold one dish in your head before the next arrives. INDIAN ENGLISH. Owner: "its indian english. not so fluent." An American voice reads biryani, paneer and kuzhambu like somebody who has never ordered one. Windows ships en-IN voices, Heera and Ravi, so one is preferred where the machine has it, then en-GB, then any English. Chosen once and remembered: getVoices() fills in asynchronously, and asking per ticket is how the first announcement of a service comes out in the wrong accent. It also listens for onvoiceschanged, because asking at load usually returns an empty list. AND THE ONE THAT MATTERED MOST. Chromium refuses to play audio until somebody has interacted with the page. On a counter till that is invisible - it is clicked all day. On the machine at the pass it is the whole problem: it sits untouched for hours, which is exactly when a ticket needs announcing, and the chime would have been refused with nothing in any log to say why. The switch is set before the app is ready, because afterwards it is ignored. I also claimed the script only loaded on one page of ten and "fixed" it. That was wrong: `dashboard` is not a screen, it is the shell the fifty seven modules run inside. The change was reverted rather than left in as churn. Twenty one tests. They still do not cover the speaker or the voice: that needs the kitchen machine, a Bluetooth speaker and one real ticket.
Owner: "KOT total items also print and voice read please. so that chef's
can hear well."
------------------------------------------------
TOTAL ITEMS 4
and, before the list rather than after it:
Table 5, new order.
Three items.
One Chicken Biryani.
Two Butter Naan.
BEFORE, because a number heard first is one you can count against. A chef
told three plates are coming notices when they have heard two. After the
list it is a fact nobody can act on.
PLATES, NOT LINES. One biryani and two naan is three things to cook and
two lines on the ticket. A kitchen works in plates, and the printed total
and the spoken one count it the same way on purpose - a cook checking the
paper against what they heard must not find two different numbers.
The count is the whole ticket even when the announcement is cut to six
lines and summarised. That is precisely when it earns its place.
Four older tests changed expectations rather than failed: they asserted
the exact sentence, and the sentence now carries the count. The other 64
tests around the ticket renderer pass unchanged.
The kitchen can actually hear it: a voice, real pauses, and no gesture
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What does this PR do?
Acceptance criteria covered
How was it tested?
npm startfor the desktop app, ornpm run devfor a browser at http://localhost:3000)npm run build) if build/packaging was toucheddocs/CONTRIBUTOR_QUICKSTART.mdChecklist
git commit -s, DCO)