[HN Gopher] Payment systems while working at a pizza place
       ___________________________________________________________________
        
       Payment systems while working at a pizza place
        
       Author : nickjj
       Score  : 175 points
       Date   : 2023-07-18 16:27 UTC (6 hours ago)
        
 (HTM) web link (nickjanetakis.com)
 (TXT) w3m dump (nickjanetakis.com)
        
       | squeaky-clean wrote:
       | I worked at Domino's from about 2011-2013. Their digital system
       | was really impressive to me. The POS was pretty good for fast-
       | food. But what really impressed me was the station management
       | system, aka the pizza tracker.
       | 
       | An order had to be keyed in/out of each station to the next by
       | employee pin. Each station had a screen displaying the pending
       | and in-progress orders. It was connected to the "pizza tracker",
       | so when it said "John is adding your toppings" it really meant
       | someone else had keyed it out of the sauce/cheese station and
       | "John" had keyed it into the toppings station. Orders came in
       | from the cashier or online, then went to dough/sauce/cheese,
       | toppings, oven, prep (cutting and garlic crust sauce, dipping
       | addons), then delivery.
       | 
       | Of course on things like superbowl Sunday "John" was just the
       | manager keying in every station and deligating orders manually,
       | because that was still slightly faster.
       | 
       | But what really impressed me, after a few other years of various
       | fast food jobs, was that it was not tied to any financial
       | incentives. Managers couldn't view the historical data in any
       | way. There were no bonuses or rewards based on it. So there was
       | no reason to lie and send it to a new station screen early.
       | 
       | I had worked at Burger King and Taco Bell prior. At both of those
       | locations there was a similar, but simplified system. You keyed
       | in an order as taken. Then as done. Then as served. From what I
       | could tell, management bonuses were based on certain metrics on
       | these times. The burger king actually had a single 8 segment
       | display hanging in the kitchen showing us our current letter
       | grade (A-F) for performance in the past hour. We were told to
       | just key in any order that would take longer than normal as
       | instantly done.
       | 
       | Domino's must have had some great data to optimize their kitchens
       | on. While BK and Taco Bell have their kitchens telling them
       | everything is fine, because they will be punished if they say
       | some new specialty sandwich takes too long to prepare.
        
       | samrolken wrote:
       | As someone who has built the tech behind an online ordering
       | platform just for pizzerias (Slice), this is all exactly on
       | point.
        
         | nickjj wrote:
         | Hah, it's a small world. That's the system we're using. I
         | wonder if you could tell based on the terms I used in the post.
        
       | johanneskanybal wrote:
       | Klarna has none of those issues. disclaimer: used to consult for
       | a bit at Klarna. But payment sure is a solved problem.
        
         | toyg wrote:
         | I recently tried to use Klarna, and I can only say that _of
         | course_ payment is a solved problem _when you just lie to
         | customers until it 's too late in the checkout process to
         | cancel it_. Never again.
        
       | mschuster91 wrote:
       | > You would still want that free pie to be put through the
       | workflow and tracked. The only difference is you wouldn't collect
       | a payment.
       | 
       | In some jurisdictions you don't just _want_ to put the pie
       | through the POS system, you have to for both tax reasons and to
       | make sure your employees don 't ring up their friends on "faked"
       | coupons.
       | 
       | The rest of the article is really nice as well and reflects with
       | my personal experiences in bartending... indeed having experience
       | in hospitality jobs is a major plus for _anyone_ working in IT or
       | design, simply because you learn to value first hand how
       | important performance and good UX is at some of the highest-
       | stress jobs there are.
        
         | sowbug wrote:
         | Lots of retail businesses have a sign that reads "If you don't
         | receive a receipt, your purchase is free!" It enlists the
         | customer as an auditor to make sure the employee uses the POS
         | system, rather than pocketing the customer's payment. If the
         | cash in the till doesn't match receipts at the end of the day,
         | the proprietor knows something's wrong.
         | 
         | (Just in case you're one of today's lucky 10,000.)
        
           | WeylandYutani wrote:
           | Wouldn't it just be easier to stop accepting cash? Dominos is
           | card/internet only.
        
             | sowbug wrote:
             | If the merchant had another means to accept payment, sure.
             | The sign has been around since the invention of the cash
             | register, possibly even earlier.
        
             | pc86 wrote:
             | Some people (a vanishingly small minority, admittedly) will
             | only use cash. But some more realistic reasons for
             | accepting cash:
             | 
             | - 3% credit card fees aren't nothing when your entire
             | business operates on 4-5% margins
             | 
             | - It's much harder to launder money if you're 100% cashless
             | - if you have even a small proportion of legitimate cash
             | buyers you can now funnel more illicit money through that
        
               | kevincox wrote:
               | FWIW handling cash isn't free either. It can be 2-3% as
               | well (depending on a lot of things like volume, change
               | requirements and typical patterns, insurance can be less
               | if you have no cash on premises, ...)
               | 
               | In many cases the cost of credit cards and cash are
               | surprisingly similar. Especially in Europe with capped
               | fees.
        
           | morelisp wrote:
           | Unless you know the owner is a Mensch, don't be a narc. Let
           | the underpaid overworked employee pocket whatever. Whole
           | Foods doesn't fucking care.
           | 
           | Temporarily embarrassed millionaires eat my ass.
        
             | bitwize wrote:
             | If you see someone stealing food, no you didn't.
        
             | pc86 wrote:
             | Until you have a problem, and don't have a receipt, and now
             | you're out your money with a defective product and nothing
             | to do except - buy a new one, I guess?
             | 
             | And I'm not sure what makes you think the person buying the
             | thing is doing any better financially than the person
             | ringing them up. Working class people shop too. You're
             | letting your Poli Sci 101 take on class and economics cloud
             | the fact that it's most likely another working class person
             | getting taken advantage of.
        
               | sowbug wrote:
               | The relevant parties aren't the cashier and the buyer.
               | They're the cashier and the business owner. The whole
               | scheme is meant as a deterrent, not as a remedy. If the
               | buyer observes that the cashier isn't ringing up the
               | sale, and the buyer challenges the cashier, the cashier
               | will say "oops!" and proceed to ring it up correctly.
               | That's because the cashier has nothing to gain by
               | continuing the deceit at that point; either he's just
               | letting people walk out without paying (thus risking
               | being fired for no gain), or he's back to doing his job
               | of collecting revenue in exchange for his wage. In any
               | rational play of this game, the buyer ends up the same --
               | paying what he owed for the sale.
               | 
               | This assumes, of course, that everyone is behaving
               | rationally. If you believe grocery stores are evil, as
               | the parent comment suggests, I suppose you also believe
               | you have license to make up your own rules.
        
             | arcanemachiner wrote:
             | A memetic formula for societal decay has never been
             | expressed so succinctly.
             | 
             | It's "Fuck you, got mine" all the way down.
        
           | hanniabu wrote:
           | But you don't receive a receipt until after you pay, so you'd
           | already given them the money before you realize if you're
           | getting a receipt or not. That means you have to then
           | escalate the issue, cause a scene, take up your time, deal
           | with the whole your word vs theirs, etc.
        
             | sowbug wrote:
             | I'm probably missing your point. The cops don't show up to
             | every crime scene, but the chance they will is enough to
             | deter crime.
        
         | ilyt wrote:
         | Or really in any job in general where you _actually_ use the
         | tool for longer periods of time.
         | 
         | So that "eh, it's not _that_ slow " and "It's only extra click"
         | will bother you to no end when you have to constantly waste
         | time on it.
        
           | aquariusDue wrote:
           | The value of domain expertise in combination with technical
           | expertise cannot be overstated.
        
       | weard_beard wrote:
       | 20 years as an eCommerce developer/architect.
       | 
       | This is really good for a first take. It covers quite a lot of
       | what we document in most of our initial pre-project planning
       | sessions. A couple considerations not covered here that we would
       | dig into are:
       | 
       | .05) Integrations! A Point of Sale and a Website an Enterprise
       | Record System, a Product Information Management tool, A content
       | management and authoring tool, A digital image and media
       | management tool, Warehouse management and Order management
       | software, and Business Intelligence Data Lake, Customer Data
       | Platform, Email Marketing Platform, Ratings and Reviews Service,
       | Search, and a rainbow of minor 3rd party web based services don't
       | really help much unless they all talk to each other. Nowadays,
       | you also need a way to mix the data from all these services
       | together to provide unified data management and a unified user
       | experience. To achieve this we usually build a dedicated
       | orchestration layer to handle the services that merge data from
       | all these sources.
       | 
       | 1) Products. Bundles, Groups, Configurables, Packs that can or
       | cannot be split, special pricing (distinct from discounts), add-
       | ons, virtual products, inventory, stocking from warehouse, resale
       | through market places or other omnichannel availability,
       | attributes that affect pricing or shipping or purchase
       | availability, etc.
       | 
       | 2) Order Management. Order modification and workflows for
       | different types of returns and exchanges. How long/can orders be
       | modified between placement and delivery. How are chargebacks and
       | price differences handled? What's the workflow? How is
       | manufacturing/warehouse/shipping notified?
       | 
       | 3) Sales channels. Specifically BOPIS (Buy Online, Pickup In
       | Store) inter-store transfers for sales, or inventory stocking),
       | delivery types (freight, refrigerated, courier, plus the usual
       | UPS/USPS/FedEx options). Return and delivery tracking services
       | and customer assistance programs.
       | 
       | 4) Reporting. Financial, marketing, service and technical
       | performance, Data Warehousing and Cross functional Business
       | Intelligence, taxes, refunds, breakage, etc.
       | 
       | 5) Customer service integrations, customer management, customer
       | support, ticketing and tracking through customer data platforms
       | like Salesforce.
       | 
       | 6) Loyalty and reward programs including virtual and physical
       | ledgers of points and campaigns to earn points. Loyalty as
       | payment type. Ratings and reviews. Social media engagement. Gift
       | cards.
       | 
       | 7) Transactional communications systems such as email, text, and
       | social media integrations, mailing lists, newsletters, and push
       | notifications.
       | 
       | 8) Multi-language and international sales considerations. There
       | is a LOT to consider here. From tax to payment types, to product
       | availability and shipping.
       | 
       | 9) There is a mention of payment types, but payments get so much
       | more complex than what is covered here. Who is your merchant
       | bank? What payment gateway to use? International payments get
       | even more complex. When to auth and capture. Services to tokenize
       | and preserve payment info for future purchases or changing order
       | amounts.
       | 
       | 10) Fraud detection for payments. Mitigating carding attacks and
       | other fraud attempts through monitoring and 3rd party
       | integration.
       | 
       | 11) Recurring payments/subscriptions.
        
         | monksy wrote:
         | For the love of god don't forget taxes.. fucking taxes.
         | 
         | Federal, state, local, type, etc.
        
           | weard_beard wrote:
           | I include that mostly under integrations. These days most
           | companies are smart enough to use a centralized service
           | instead of rate tables. The services are pretty good and
           | provide pre-built integrations for most common frameworks. A
           | security audit, install, and QA and you're 90% done.
        
           | joshstrange wrote:
           | I hope your taxes system has a concept of only applying to
           | certain item groups and/or certain specific items. Some
           | places have food taxed, others do not, water isn't taxed,
           | alcohol is taxed differently, food with enough sugar is taxed
           | differently than just "food", and the list goes on.
           | 
           | Also your clients might want to be able to add their own
           | "taxes" (aka service charges) for certain days/weeks of the
           | year or by the channel that the order was placed.
           | 
           | POS system are incredibly complicated and even more-so if
           | they span multiple restaurant industries or types. Think
           | table service vs drive thru vs carryout vs curbside and
           | things like pizza vs coffee. A lot of what you build will not
           | transfer over. Your logic to handle half and half pizza
           | probably isn't going to be reusable in other industries.
           | 
           | I will say one thing, it's never dull.
        
             | monksy wrote:
             | Service charge isn't a tax. It's the POS's flexbility with
             | autograting.
             | 
             | It maybe considered to be taxable.
        
             | datavirtue wrote:
             | Delivery is taxed if the food is taxed...in most
             | jurisdictions. You could easily have any variation apply in
             | edge cases. Your software has to do it all.
        
             | datavirtue wrote:
             | I'm building an online ordering system right now. Just for
             | pizzerias. Generalized systems suck hard.
        
             | sebastianlay wrote:
             | Your coffee in a cafe in Germany is taxed differently based
             | on the amount and type of milk in your coffee. Oh and of
             | course the tax rate is different depending on whether you
             | consume it in the cafe or take it to go.
        
               | leblancfg wrote:
               | I seriously thought you had to be joking. But no! Ok I
               | figure, the carbon footprint of milk is massive[0], it
               | must be taxed at a higher rate?
               | 
               | > In some European countries, plant-based milk is
               | subjected to a significantly higher VAT than cow's milk.
               | 
               | Still haven't understood this one yet though. Some kind
               | of protectionist tax rate for the farmers?
               | 
               | [0](https://www.co2everything.com/co2e-of/milk)
        
               | monksy wrote:
               | This is 100% normal and happens in America. It's a huge
               | reason why hard seltzers took off. (They're brewed
               | instead of distilled)
               | 
               | On top of this, you can have local based taxes or tax
               | breaks. (I.e. Chicago has a bag tax, leave the city.. no
               | bag tax)
               | 
               | https://www.efile.com/unusual-strange-funny-taxes-
               | throughout...
        
       | hot_gril wrote:
       | So if I'm familiar with databases in general and slightly
       | familiar with financial transactions, what's the most surprising
       | thing about the pizza payment systems in particular?
        
         | andix wrote:
         | There are no big surprises. There are hundreds of tiny ones.
         | You need to identify them, keep track of them and don't miss
         | any.
        
       | retrocryptid wrote:
       | In my day we didn't have a fancy computer to calculate change. We
       | had to count up change, just like my grandpappy did in nineteen-
       | aught-three. And change! MEH! All we had were sheets of zinc and
       | steel and copper foil. We had to manually pound out pennies in
       | the back of the shop in a mold stolen from the mint in DC. And
       | even if we did get a computing device, all we had were zeros. We
       | had to pound half of 'em into ones manually. AND WE LIKED IT THAT
       | WAY!
        
       | sky_rw wrote:
       | If anybody here is suddenly considering a startup in the PoS
       | industry, please just turn around and run as fast as you can in
       | the other direction. It's an endless pit of hell.
        
         | [deleted]
        
       | tolien wrote:
       | > For example, if a pie costs $16.95 right now and you have 1,000
       | orders that happened in the past at that price and then bump your
       | pie to $17.95 you can't go back and adjust all of those previous
       | orders to have $17.95.
       | 
       | > Just about everything about that receipt should be
       | denormalized, AKA. the details about the receipt are all self
       | contained in that 1 row.
       | 
       | The way I'd probably model this would be to mark the $16.95 pie
       | as deleted/deprecated/no longer for sale and create a duplicate
       | entry with the price changed to $17.95, rather than creating
       | copies of all of the product details each time I record a sale.
        
         | heywire wrote:
         | Traditional point of sale systems generally have the notion of
         | a "transaction log" or "tlog" which is a sequence of events
         | within the transaction including items sold and their price at
         | the time.
        
         | duskwuff wrote:
         | > The way I'd probably model this would be to mark the $16.95
         | pie as deleted/deprecated/no longer for sale...
         | 
         | That technically works, but it plays hell with reporting and
         | stockkeeping. The latter of which isn't a problem for pizza, of
         | course, but can be significant in other sectors. (Nobody wants
         | to have to keep track of a stock of "$16.95 widgets" separate
         | from a stock of identical "$17.95 widgets".)
         | 
         | But there's enough other data in a receipt/invoice which needs
         | to not change after the invoice is created, like tax rates,
         | that it really is best to make the whole thing self-contained
         | and immutable. Being able to confidently make statements like
         | "yes, this is exactly the same invoice that we presented to the
         | customer 3 years ago, and nothing about it has changed" can be
         | incredibly important as well.
        
         | scottcodie wrote:
         | You could also use a temporal table.
        
         | evrimoztamur wrote:
         | Just as the receipts are immutable, you should preferably have
         | your products be immutable too. From the user's point of view,
         | the foreign keys are a part of a separate layer: They will only
         | see the products by a shortcode/name. In turn, having a
         | modification on a product (or any other object) 'archiving' the
         | existing version and creating a new copy can be made seamless
         | while avoiding normalisation.
         | 
         | Is it a better way to do it than an audit log for changes?
         | Maybe!
        
           | kevincox wrote:
           | That works great until you want to see how many pizzas you
           | sold of each size last year then you realize that you
           | presented wrong data to the CEO because small pizzas changed
           | price in January and large pizzas changed price in July. Your
           | reporting only included the "current" products so the counts
           | were all off.
           | 
           | The ideal schema would probably have some sort of "product"
           | and "product revision". Orders would reference a particular
           | revision and menu/reporting would use the product (joining in
           | the revision).
           | 
           | But in this case since there are likely legal requirements to
           | have exact copies of receipts it may also be smart to just
           | archive a "fully rendered" copy as well to ensure that a code
           | cleanup doesn't change rounding and accidentally modify the
           | data on old orders.
        
       | addisonj wrote:
       | What an interesting and timely article.
       | 
       | My extended family recently opened a pizza place which just
       | happened to be at the same time as me wanting to take a break
       | from startup grind. I worked at a pizza place in high school, and
       | have continued to make pizza at home, and loved the idea of being
       | able to combine that knowledge with the experience of building
       | software startups, so I have been heavily involved in the last 6
       | weeks on everything from ordering, to kitchen layout, to POS and
       | other IT systems, to marketing.
       | 
       | In short, the experience has been super interesting, not only in
       | terms getting to learn tons of new things and get familiar with
       | how the tech side is done (spoiler alert, not that well) but also
       | just generally how much of an opportunity there is to take the
       | sort of thinking and skills required to build tech products and
       | to apply them to a quick-serve restaurant (and I would guess lots
       | of other small business).
       | 
       | I have been planning on writing something up, but this article is
       | giving me good motivation to actually do it :)
        
         | Freedom2 wrote:
         | I wouldn't be surprised if the author visited your newly opened
         | place and was inspired to write the article based off their
         | experiences! It's a small world, after all.
        
       | [deleted]
        
       | glonq wrote:
       | Early in my career, I learned that it's possible to accidentally
       | _credit_ thousands of dollars to people 's credit cards instead
       | of _charging_ them.
       | 
       | On the bright side, I learned a valuable lesson and did not get
       | fired.
        
       | user83849492 wrote:
       | What are the best POS systems out there?
        
         | quickthrower2 wrote:
         | Anecdotally (in Australia), as a customer I found the square
         | readers [1] linked to ipads were the smoothest and quickest.
         | And I use a mix of cards - credit, prepaid gift cards, debit.
         | 
         | [1] Probably this thing:
         | https://squareup.com/shop/hardware/au/en/products/chip-credi...
        
         | aaronax wrote:
         | Any that are text/TUI/"green-screen"-based are often lauded for
         | speed once you are familiar with them, so there is that kind of
         | best. And if they are still in use even today, then that
         | survival is a strong point in favor of them being "the best".
         | 
         | As far as specific products, NCR Counterpoint is one that
         | stands out amongst those I have used. Fast and flexible, kind
         | of easy to figure out most things on your own.
         | 
         | The Costco cafeteria self-service kiosk seems to be an amazing
         | POS (customer perspective). Incredibly optimized in every
         | regard. The receipt seems to print out before you have even
         | finished removing your card from the chip reader.
        
       | mprovost wrote:
       | Back in college we ordered pizza and when the driver arrived
       | there was some confusion finding money for a tip and after he was
       | gone we realised that three of us had given him cash. After that
       | every time we ordered it seemed like the pizza arrived in
       | minutes. We assumed that someone had put a note in their system
       | next to our phone number like "amazing tippers".
        
         | hot_gril wrote:
         | There are a few nice restaurants where I've given a normal tip
         | but in cash, which isn't common there, and it seems like
         | waiters remember me (in a good way) just because of that.
        
       | JohnFen wrote:
       | When they first started calling these systems "POS", I thought
       | that it was an unfortunate coincidence that they used the common
       | acronym for "piece of shit". But later, I began to wonder if it
       | wasn't intentional, a kind of inside joke.
        
         | robotnikman wrote:
         | Some people on the IT side where I work who deal with these
         | things on a daily basis do that. Even I sometimes see POS as
         | "piece of shit" now, even though whatever documentation I'm
         | reading is obviously referring to 'Point of Sale'
        
         | Verdex wrote:
         | Regan faced the engineers and fought to keep the annoyance from
         | reaching his face. "What did you call it?"
         | 
         | "POS." Brenda's bubbly demeanor was reflected in a little dance
         | that she did while saying each letter in an almost singsong
         | pattern.
         | 
         | "You ..." Regan stops fighting his instincts, takes off his
         | glasses, bows his head, and pinches his nose. "All of you
         | understand that we can't call it that."
         | 
         | The rest of the engineers stood silently and without movement.
         | They have to have planned it this way. He should have known
         | something was up from the moment he walked in here.
         | 
         | "Why's that?" Brenda tilts her head to the side.
         | 
         | "Because it stands for piece of ..."
         | 
         | "Point of sale." Brenda blurts out before Regan can finish.
         | 
         | Regan slowly puts his glasses back on. "Is the POS going to be
         | completed by the deadline?" He forces the words out through a
         | clenched jaw.
         | 
         | Brenda remains still with wide eyes and a frozen smile on her
         | face. The rest of the room nods that the deadline will be met.
         | 
         | "Then fine." Regan leaves; they can make the deadline then they
         | can have their stupid little name.
        
       | joshu wrote:
       | > That means you shouldn't have something like a reference to a
       | product's foreign key to dynamically grab the price when you
       | render the receipt.
       | 
       | This is vastly underrated principle that is rarely understood and
       | should be much broadly applicable. My data is separate from other
       | people's data. In Carta, I have had my startup investments leave
       | the system (die, acquired, etc) and I am left taking screenshots
       | of everything because my records are just foreign keys into some
       | other data store. If they had mailed me PDFs even paper or
       | something, I would be fine.
        
         | shortcake27 wrote:
         | I feel like this is one of those cases where people take a
         | mantra too seriously.
         | 
         | Storing values that could otherwise be derived results in
         | complexity and discrepancy.
         | 
         | This may lead people to the conclusion that all values which
         | can be derived should be derived, but in the case of a
         | receipt/invoice, this is not the right call. Discretion must be
         | applied.
        
           | joshu wrote:
           | your comment doesn't provide when to decide one way or the
           | other, which makes it more warning and less useful.
           | 
           | when the data is stuff that could be paperwork - you get a
           | copy, i get a copy - it should not be the case that one side
           | gets to unilaterally decide if the data is deleted or
           | modified.
        
             | shortcake27 wrote:
             | I am in agreement with you.
             | 
             | I'm just saying that developers need to apply discretion
             | rather than following arbitrary "rules" or "patterns". When
             | to store or derive depends on the use case, of which are
             | infinite.
        
             | mrighele wrote:
             | I think it is not difficult to decide: sometimes you want
             | to reference an entity with its current state, some other
             | times you mean with the properties that it has at a
             | specific point in time.
             | 
             | For example if I don't pay yearly tax on my car I will
             | receive a fine. The fine may arrive one or two year later,
             | but it should be sent to me even if I sold the car
             | meanwhile, because what matters is that I was the owner at
             | the time. On the other side, the fine should be sent to my
             | current address, not the one I had when I forgot to pay.
             | 
             | There a number of ways to handle this. The simplest is to
             | make a copy of the data, but you can also decide to keep
             | all the historical data and reference the state during a
             | certain time interval. Both can be valid choices, depending
             | on the context, frequency of change, number of
             | references....
        
           | squeaky-clean wrote:
           | I think the biggest deciding factor in this particular
           | situation is what the article says in the sub heading. 'A
           | "Receipt" is immutable'. You don't care about the consistency
           | guarantees of normalization. You don't care about being able
           | to re-derive it with new logic or additional features. And in
           | all likelihood the storage savings from not storing the final
           | generated output is going to be miniscule.
           | 
           | If some data is meant to be truly immutable, and storing it
           | separately won't impact your storage costs, store it
           | separately. Because otherwise that immutability needs to be
           | somewhere else in the system.
           | 
           | If you normalize your data and dynamically derive receipts,
           | your logic needs to include all receipt logic you have ever
           | used, cordoned by timerange. Was the price of a large Pizza
           | changed in 2018? Your receipt logic and data has to reflect
           | that forever. Did you allow stacking coupons but in March
           | 2017 you started limiting it to 1 coupon per customer? Your
           | receipt logic and data has to reflect that forever. Did you
           | have a week where prices were rounding in the wrong direction
           | when a certain coupon code was used? That has to be in your
           | receipt handling forever.
           | 
           | There's just so much additional effort, so much potential to
           | go wrong, and so little to gain.
        
         | hot_gril wrote:
         | The general way I'd do this _is_ to have the foreign key, but
         | not to a  "current prices" table, rather to an "all prices"
         | table containing present and past prices. Which goes back to
         | immutability. Maybe over-engineered for a small pizza shop that
         | could get by fine with $ values copy-pasted everywhere, but
         | we're talking about general principles.
         | 
         | It's not like the customers' data is meant to be separate, like
         | they're all paying the same price that we decided for the day,
         | other than promotions which would be a separate table or misc
         | adjustments that would just be a col directly on the sales
         | table.
        
           | andix wrote:
           | There are a lot of things that can change, not only the
           | price. The name of the product can change. What was "Medium
           | crispy crusted pepperoni pizza" yesterday, may be called
           | "Extra large pepperoni pizza" today. If you re-print the
           | invoice, it should look the same as on the first print.
           | Otherwise you may get some issues with the authorities
           | (manipulating your copy of the invoices).
           | 
           | There may also be a lot of related tables for finding the
           | price (in the system I worked it was about 10 joins to get
           | from the article to the price). It can be done in an
           | immutable way, but it is possible that the way of calculating
           | prices may change after an update. There may even have been a
           | bug in the first place (like incorrect rounding, issuing
           | rebates that shouldn't have been issued, incomplete sync of
           | the prices table from the main server to the cash register,
           | ...). Once you fix it all the previously issued invoices
           | would show a different price. Which means you "lost" your
           | copy of the invoice. Authorities don't like that. Credit card
           | companies don't like it, if the customer disputes the charge
           | and you show them an invoice with a different amount. Your
           | bookkeeper doesn't like it, if a lot of payments don't match
           | the invoices exactly, ...
           | 
           | Edit: Example for rounding: Two people split a pizza for
           | 19,99$. Version 1.0 creates two invoices with 10,00$ each.
           | Version 2.0 creates one invoice with 9,99$ and a second one
           | with 10,00$. Then the authorities pass a law that rounding
           | prices must always floor them. So Version 3.0 creates two
           | invoices for 9,99$.
        
             | hot_gril wrote:
             | Right, other things can change, and you record those
             | changes as immutable rows in a table too. You don't forget
             | that the "super pizza" used to be called "uber pizza," so
             | you can print the same exact receipt again, but you know
             | they're the same product.
        
               | andix wrote:
               | Sure, you can do that. But if you do some changes in your
               | data model or logic you need to be extremely careful that
               | all existing invoices still show exactly the same data.
               | You probably need to use immutable price calculation
               | logic for that too. Keep the old logic after an update
               | and only use the new logic for new invoices. Because over
               | the years there will be braking changes in your price
               | calculation logic.
               | 
               | A lot of effort for not so much added value. The systems
               | I worked on put the calculated price of every item on
               | every invoice into the database. So it can't "drift" over
               | time. Off course they still keep the reference to the
               | article too.
               | 
               | It's also much easier/faster to calculate sums and
               | statistics one one table column instead of doing many
               | joins every time you need the price.
        
               | lmm wrote:
               | > A lot of effort for not so much added value.
               | 
               | It's not a lot of effort; in fact I'd argue it's free, or
               | even negative cost. If you're in the habit of following
               | that paradigm then it's no harder than the mutate-
               | everything-in-place paradigm.
               | 
               | > It's also much easier/faster to calculate sums and
               | statistics one one table column instead of doing many
               | joins every time you need the price.
               | 
               | WTF? Did 1970 call and ask for their hardware back?
        
               | hot_gril wrote:
               | Maybe I'm not thinking of a complicated enough case, but
               | I don't see why there'd be so many breaking changes. Say
               | you add a new table for some special kind of promo, that
               | doesn't affect the old receipts. At least this wasn't an
               | issue in the last few e-commerce sites I dealt with. In
               | any case, I would stay far away from having to preserve
               | multiple versions of logic.
               | 
               | It's also fine to denormalize a bit by copying the final
               | price somewhere for performance, convenience, or sanity
               | checking, but that's the kind of thing you bolt on after.
               | If you're managing account balances, you actually need
               | this for concurrency control alone.
        
           | throwaway7337 wrote:
           | I made an online store where I just stored the price in the
           | order itself, as an immutable snapshot of the price at the
           | time of purchase. I also included the product title and SKU,
           | just in case someone decided to reuse an old product instead
           | of creating a new one (it happened several times)
           | 
           | Alternatively you could go "all in" and create some form of
           | versioning system, where you store the version number of the
           | product
        
       | Doches wrote:
       | I'll chime in with a lesson learned from my own experience in
       | niche POS systems: it can be amazingly valuable (in certain
       | contexts) to let clerks pause sales and put them off to one side
       | (think "git stash", but for sales). Customers wander in and out,
       | run back for one more thing, or put things on hold while they go
       | out to get cash out of an ATM. Letting a clerk wrap up a whole
       | sale with context (some items rung up, payments created but not
       | processed, etc.) and put it on a shelf to restore later is a
       | superpower for POS systems.
       | 
       | And that's not even _starting_ on the nonsense and bizarre home-
       | rolled systems that small businesses concoct around layaways.
        
         | craftkiller wrote:
         | I used to work in a supermarket without this feature and when a
         | customer would run away mid-order, my options were either stand
         | there awkwardly while another potentially irate customer stares
         | at me or call over a manager to get the override key to let me
         | cancel the order (any voids/cancels over a certain dollar
         | amount required a manager override key). Neither option was
         | good. Both wasted time and created a bad experience for the
         | customers. I occasionally see cashiers these days doing these
         | `git stash` maneuvers and honestly I get jealous every time.
        
           | Jcampuzano2 wrote:
           | In the store I worked in, which was a notable spot for people
           | attempting credit card/gift card fraud and/or theft, the
           | manager literally just gave me the override code because it
           | happened so often I'd have him coming over like every 15
           | minutes to cancel something. We were also a super busy store
           | at the same time as this so it would just leave a bunch of
           | hyper-angry customers in line.
        
           | ec109685 wrote:
           | The psychology of this is funny. The right thing with such a
           | POS is to have customer pay for everything so far, move their
           | cart to the side, let them run and get their item, and then
           | let them be front of line at that point to finish their full
           | set of purchases.
        
           | Arrath wrote:
           | It was an option in the register when I was a cashier during
           | the crash of '08 and I couldn't find a gig elsewhere.
           | 
           | But it was against policy to use the feature, since previous
           | cashiers had worked out a way to scam the system somehow and
           | pocket some of the cash being exchanged. I'm cloudy on the
           | exact details after so long, but it was very, very annoying
           | to have such a useful feature sitting there mocking me and a
           | write up if I dared hit the button.
        
             | michaelmrose wrote:
             | Presumably suspend your partner in crimes transaction
             | receipt is printed walk away. Partner slips you some money
             | later.
             | 
             | Solution: don't hire scummy people, pay enough that you can
             | afford decent folks, watch for a friend that always comes
             | to a certain cashier especially while alone, watch for
             | cashier being nervous when observed, watch for partner to
             | break off transaction if observed, "forget card", or return
             | goods shortly.
             | 
             | It's also obviously trivial to catch with the receipt but
             | they will probably refuse to show it. A transaction log
             | will also trivially show it if matched with register and
             | time.
             | 
             | Anyone could potentially get away with this once but any
             | dishonest person is going to want to do this repeatedly.
             | 
             | There is basically no excuse for not catching this as a
             | manager and I see no reason to deny associates this useful
             | feature.
        
             | mgkimsal wrote:
             | Instead of dealing with the offenders... punish everyone -
             | workers _and_ customers (with delayed /crappy checkout
             | experiences). That's great management, sure. Situations
             | like these - which I noticed as a kid - contributed to my
             | early-onset cynicism.
        
               | wccrawford wrote:
               | If it's too hard to detect, management doesn't have much
               | choice.
               | 
               | It would be smarter for that feature to require a
               | manager's key, and then the manager could actively
               | monitor the situation. But since the manager can't
               | implement that feature, they have to work with what they
               | have.
        
               | zdragnar wrote:
               | Solving personnel problems with policy is unfortunately
               | common at companies in the small-medium space. Very small
               | companies tend to be more person oriented, and very large
               | companies tend to have outgrown it (though they may still
               | do it at the department level).
               | 
               | It is also one of the most annoying mistakes I see
               | frequently repeated at startups and young businesses.
        
               | michaelmrose wrote:
               | It's incredibly easy to detect.
        
               | lowercased wrote:
               | It read like they DID know how to spot it, and the
               | reaction was... "never again for anyone under any
               | circumstances".
               | 
               | Blanket bans like the one described are always wrong. ;)
               | 
               | If there's a problem, monitor it after every shift, or
               | every day, or weekly. You know who worked what registers;
               | monitor/scan/review, then take action against the
               | offenders.
               | 
               | I worked food service with POS; we had to review things
               | every drawer change, and discrepancies were noted.
               | Repeated discrepancies (either money or between food
               | usage and money) would be tied to someone (or multiple
               | people) and action was taken. It's not always that hard,
               | just a bit time consuming, but... it's part of the job
               | (or was for me).
        
           | badwolf wrote:
           | The store I managed had a suspend/recall. Cart full of
           | groceries only to realize you left your wallet (at home, in
           | the car, whatever) suspend the transaction and print a slip
           | with a barcode on it. Move the cart out of the way and take
           | the next customer. The customer comes back and scans the slip
           | at any register to recall the transaction, pay and collect
           | their cart and leave without having to hold up lines/etc...
           | Was a nice convenience many appreciated.
        
             | dylan604 wrote:
             | This very thing happened to me, and I was very pleasantly
             | surprised with how this worked. It definitely took some of
             | the embarrassment away from being a dolt
        
             | c22 wrote:
             | I worked at a store that had this feature except if you
             | reloaded the transaction on a different register it still
             | got attributed to the originating register and caused a
             | headache at closing :(
        
         | andix wrote:
         | We called that feature "parking" the invoice. It's pretty
         | standard on every good POS system.
         | 
         | It can also become a challenge if you have a lot of those and
         | want to find the right one. We had some users that prepared a
         | lot of orders in advance into bags, so they can hand them to
         | the customers right away when they come. Best solution was to
         | print a delivery note for every order, attach them to the bag
         | and then scan a barcode on the bag when the customer comes for
         | pick up/payment. And you also need to be able to add or remove
         | items before the customer pays, people often change their mind.
        
         | monksy wrote:
         | Honestly, to add on to what you said, it's amazing about the
         | lack of domain knowledge that developers and product owners
         | have in making systems for people.
         | 
         | For the clerks and workers using the POS, it's often more of a
         | hinderence than it is a help. When you look at less technically
         | reliant societies (i.e. market places in Asia) you'll see this
         | more often. Prices are negotiated, they can be their own
         | warehouse, smaller companies work together (your package
         | getting from maker, middleman, aliexpress to your door is
         | incredibly complex but they can make it happen within 2-3
         | weeks).
        
           | retrocryptid wrote:
           | To be fair, though, the "customers" aren't the customers. In
           | modern software companies, you don't sell products to be
           | profitable, you sell them to be plausible. As a software
           | company, your value to a venture investor is much greater
           | than it could possibly be to a potential customer. The
           | objective of the startup is to look plausible until the
           | current round of investors sells their stake to the next
           | round of investors. Part of they way _those_ investors value
           | the company is whether or not they think they can sell the
           | company to a greater set of fools.
           | 
           | In the modern software company there is only one customer,
           | the next early stage investor. I can assure you, your execs
           | know how to pitch to them, otherwise they wouldn't have
           | received their A round.
        
           | selalipop wrote:
           | I always like to say something meaningful before plugging my
           | project, but that's exactly why I started working on
           | https://notionsmith.ai
           | 
           | Overall I'm really excited about LLMs being integrated deeper
           | into product development, there are a lot of insights already
           | captured in their output that people building products could
           | use
        
           | smelendez wrote:
           | It's always much faster to check out with a couple of things
           | in a New York bodega/deli, even while making small talk with
           | the clerk, than to check out with the same items at the chain
           | drugstore down the street.
        
           | esel2k wrote:
           | Isn't the reason rather that management will say: Is this
           | absolutely necessary and will it increase sales?
           | 
           | And often the answer is no unless you can demonstrate the
           | time gain and emotion of your customer. When the margins are
           | super thight anything that won't help margings is left away
           | and home delivery /online shopping will be prioritised for
           | the tech team/budget.
        
             | monksy wrote:
             | Of course they'll say no. It presents a version of the
             | technology that is not commonly done. Justification for
             | their stubborn resistance to support the customer and the
             | users is not relivant here.
             | 
             | We're still stuck filling out forms and passing validation
             | to complete transactions.
             | 
             | My complaint here is that arrogance that POs and devs have
             | in how humans operate with the software is way off. What
             | happens if you want to buy out Aldi's entire stock of brie?
             | Is it reasonable that you should be paying
             | stockprice*quantity? (The answer outside of technology
             | enforced rules is no.. Additionally to aldi corp, theres no
             | reason not to offer a discount here) [Also, in practice
             | they try to hack their way arround it by overriding the
             | price]
        
         | crmd wrote:
         | I was really impressed when the cashier at my neighborhood
         | supermarket recently transferred my order in progress over to
         | an empty lane so that I could deal with a credit card issue
         | without delaying the people behind me. Seems like an obvious
         | function but it had never even occurred to me!
        
         | EvanAnderson wrote:
         | > ...let clerks pause sales and put them off to one side...
         | 
         | I dreamed about just such a feature when I worked at a
         | convenience store back in high school. That was 30 years ago.
         | Such progress... >sigh<
        
         | ghaff wrote:
         | >And that's not even _starting_ on the nonsense and bizarre
         | home-rolled systems that small businesses concoct around
         | layaways.
         | 
         | There are a number of things that even many just modestly-paid
         | developers don't grok because they obviously make no sense.
         | 
         | Many years ago I remember asking a then-gf why such and such a
         | store customer service accepted utility payments. And she was
         | "Umm. Some people don't have checking accounts." Layaways are
         | different but in the same general category.
        
         | tecleandor wrote:
         | That's a bit like opening a tab in a bar, isn't it?
         | 
         | I think it depends a lot in the country or the business, in
         | some places is so easy, but in others is so difficult.
         | 
         | I remember at least 20 years ago, in the grocery store with the
         | most basic digital scales, every clerk would have their "tab",
         | shared between all the scales. So each one could use the scale
         | nearest to the fruit they were weighing in that moment, then
         | switch to a different one... And finally print the whole ticket
         | without interfering with the other clerks.
         | 
         | Something like this...
         | https://cdn.wallapop.com/images/10420/5j/p7/__/c10420p335420...
        
         | LeonB wrote:
         | I maintained a POS for a retail chain for a few years.
         | 
         | Our suspend/resume sale feature assumed that a suspended sale
         | could only be resumed on the machine that suspended it. Then we
         | had to change it to be resumable on any machine in the store.
         | But only show a flashing notification that there's a suspended
         | sale, on the original machine.
         | 
         | (Thanks for storing that knowledge for me for the last decade,
         | neurons. I doubt you'll be asked to recall it again.)
        
           | alexeldeib wrote:
           | Why only the light on the original machine? Why bother
           | showing the light at all?
        
       | joshstrange wrote:
       | I work for a POS company and yeah, it's crazy how much more
       | complex something like this is than you think at first.
       | 
       | Another wrinkle that wasn't covered in this post: variable
       | pricing.
       | 
       | What I mean by that can best be explained with this example: You
       | have a S/M/L pizza but the additional toppings are priced
       | differently for the S vs M vs L ($0.50, $1, $2). But you probably
       | want a "Toppings" option set with choices like "Sausage,
       | Tomatoes, etc" that's reusable across all your pizzas (for
       | stock/reporting purposes). Also you want to be able to mark a
       | topping as out of stock and have it apply to all your pizzas. So
       | how do you handle the price differences? Remember this 1 option
       | (Size) modifying the pricing for a totally different option
       | (Toppings). Also you might want to set this on a per-pizza basis,
       | since you also need to modify the "Toppings" option to include
       | "Beef, Sausage, and Pepperoni" for free on the "Meat Lovers" and
       | you also need to have some kind of handling for "2-Topping pizza"
       | where you get 2 toppings for free then have to pay for any
       | extras.
       | 
       | Another fun concepts is bundles. Maybe you want to offer a
       | pizza+2-Liter or 2 2-Toppings pizza deal. All of it gets
       | extremely complicated very quickly. Even more fun is finding a
       | way to translate your internal menu structure into something
       | DoorDash/etc can understand and let me tell you, it will /not/ be
       | a 1-to-1 mapping.
       | 
       | Sure, for something like variable pricing you could just say
       | "screw it" and make all additional toppings $2/each (let's
       | pretend that's what they cost on the Large) that way you are
       | always doing as good or better than your normal POS or you could
       | "flatten" all your menu items so you end up shipping "Small
       | Pizza", "Medium Pizza", etc over to DoorDash (Don't forget, you
       | have to do that for every pizza then unflatten it on the way back
       | into your system). Don't get me started on how DoorDash does
       | testing, they literally use their live site for testing. There is
       | a town in Alaska where they add your demo location to and they
       | give you a login with a card on file that they just refund at the
       | end of the day or something like that. It's super janky.
        
         | nickjj wrote:
         | That's a good point about the toppings being different,
         | especially on different types of pies or slices. For example on
         | their personal pizza, there isn't an option for half toppings,
         | it's full or nothing.
         | 
         | We do have bundles, such as multiple lunch or dinner combos.
         | They are a distinct menu item in the POS system as "Dinner
         | combo 1" with a description of what's included.
         | 
         | What was really fun was helping design a printed menu where we
         | wanted to display 25 different pies in S / M / L variants as
         | well as having gluten free options for most of them. We opted
         | for a 3 column price layout for the 3 sizes and put gluten free
         | in its own little section with a different way to associate the
         | prices to at least 20 different pies since the size and price
         | was the same for all gluten free options.
         | 
         | It was a good lesson in dealing with "actual constraints".
         | Especially when the font size couldn't be reduced and we
         | couldn't use more than 1.2 pages for listing all of the pies.
        
       | andix wrote:
       | I developed POS software, and it is an extremely challenging job.
       | The workflow described in this article is still rather simple,
       | there are so many more possibilities (some apply more to shops
       | than restaurants).
       | 
       | One hypothetical example: a tiramisu with coffee has a special
       | price, but you still need to put them separately on the invoice,
       | either because you track if the tiramisus are out of stock and
       | want to stop people ordering more. Or coffee and tiramisu may
       | have different sales taxes (very common in Europe to have a lower
       | tax for food).
       | 
       | Different prices for take away and eating in the restaurant,
       | happy hours. Payment in different currencies, some articles may
       | have fixed prices in a foreign currency, others need conversion
       | with the current exchange rate.
       | 
       | The possibility to split or join invoices.
       | 
       | Usability and speed is crucial at the POS, the users go crazy if
       | they are busy and their software is too slow or has too many
       | submenus. It has to be easy to learn too, often they hire people
       | that fill in for a few days, and they need to be able to use it.
       | A lot of people using it are also not very skilled with
       | computers, or have no interest in learning how to use the
       | software.
       | 
       | The owner may restrict some features to some users, so they can't
       | cheat the system (taking cash payments, cancelling the invoice
       | and keeping the money). There may be some tax fraud prevention
       | laws to be implemented, vastly varying on the region, like
       | digitally signed invoices or the need to report every issued
       | invoice to the authorities in real time.
        
       | tennisflyi wrote:
       | Has Undercover Boss taught nothing. Things are never how you
       | think they'll be with boots on the grounds. DoorDash was so right
       | making devs do like an hour of actual gigging. Yeah, shit is
       | really pretty and seamless from your Herman Miller chair and
       | Uplift desk...
        
         | tracerbulletx wrote:
         | Yeah builders should understand the domain they're building for
         | as well as humanly possible. On the topic of chairs, imagine
         | the difference between a chair built by someone who has never
         | sat in one, and someone who is absolutely passionate about
         | sitting in chairs and is looking to build the perfect most
         | comfortable one. It's actually deranged that such a large
         | portion of the software industry has built up an insane game of
         | telephone between the builders and the users and convinced
         | people that it's an essential practice for success.
        
         | jsight wrote:
         | This is also true for regulatory regimes. I've been shocked at
         | how cavalierly some regulators will treat decisions that have
         | career altering consequences for those being regulated.
         | 
         | It doesn't just affect the regulations, it also means their
         | entire mental model of how the regulated will behave can be
         | wrong.
        
           | pc86 wrote:
           | This is what happens when you view your job as "make
           | regulations" (or even worse, enforce the ideological will of
           | $PERSON on $INDUSTRY) instead of "make $INDUSTRY safer and
           | better for consumers and the public."
        
         | extragood wrote:
         | I knew an early dev at DoorDash, and he _hated_ that policy.
         | 
         | That said, I personally agree with that approach. It's the
         | practical vs academic argument: the ideal is both. Anecdotally,
         | the most productive dev on my team was hired from a customer of
         | ours where he personally used and integrated with our software.
        
       | mmackh wrote:
       | Began my coding career because of the family hotel business.
       | Started coding websites, progressed onto building status boards
       | (vertically mounted tvs) for the today's Programm, dabbled in
       | document management (instapdf.com), employee management
       | (baseping.com) and worked my way up to actually implementing 3
       | different versions of iOS apps interfacing with different POS
       | systems (ordervisto.com). Getting live feedback from these
       | systems was invaluable and really helped with finding out what
       | works and what doesn't instantly.
       | 
       | The hotel is sold now and I'm wondering if I'll ever work in such
       | a challenging and multifaceted environment again.
        
       ___________________________________________________________________
       (page generated 2023-07-18 23:01 UTC)