Live data from Hacker News

Twenty five thousand dollars of funny money

rachelbythebay.com

61–70 of 175 posts

Re: Twenty five thousand dollars of funny money

#61
I encountered a similar bug at the same company with far worse results.

Won't say any specifics about the product impact, but our backend passed around two different kinds of user IDs. Each user had two different IDs, and the ID spaces overlapped. User Alice could have an ID in space 1 that is the same as Bob's ID in space 2.

At some point, at least one function expected a "space 1" ID but was being passed a "space 2" ID. This meant that content meant for Alice was shown to Bob and vice versa. None of the data was private in this case, so there was no legal problem, but it was pretty embarrassing. I suggested using strong types for the ID spaces instead of `int`, but left the company before implementing any of that.

Re: Twenty five thousand dollars of funny money

#62

I'm gonna be honest, I had never understood the "strict type" argument until right now. Seriously, since everything I work in is denoted as "cents" from backend to frontend, I personally had never understood the need so I'm part of today's lucky 10,000th.

Seriously, since everything I work in is denoted as "cents" from backend to frontend, I personally had never understood the need This matches my experience. Obviously actual strict typing has its benefits, but as far as developer ergonomics are concerned, IME you can get about 95% of the benefits just by following a convention of including unit names in identifier names. It's easy to see why this Ruby code might fail…

here it is with Go:

    package main

    type km int

    func (distance km) launch_rocket() {}
    
    func main() {
       distance_miles := 42
       // type int has no field or method launch_rocket
       // distance_miles.launch_rocket()
       
       // this works, but is obviously wrong:
       km(distance_miles).launch_rocket()
    }

Re: Twenty five thousand dollars of funny money

#63
post #41

Had exactly that bug in production, was using ruby on rails & active merchant, and some version change in ActiveMerchant switched from cents to dollars for one of the integrations. Our test harness didn't catch it (weird combination of reasons, too long ago for me to remember the details) & it rolled out. Shortly thereafter I get an anxious customer call that we'd charged their debit card $2500.00 instead of $25.00 a…

I made an account just to tell you that I was able to almost feel & experience what you 're describing just by reading your comment. There should be a market for this hah

Re: Twenty five thousand dollars of funny money

#64

Earlier quoted context omitted.

You don't need "strict typing" to handle money; in the old (COBOL) days, we used BCD to represent monetary amounts with arbitrary precision. When they took away BCD, we were stuck, if we wanted to build a system that could represent a large sum correctly in both dollars and yen. COBOL was pretty good for dealing with money.

BCD doesn't really make it easier. Fixed point can, but that's ultimately a typing thing that works just fine in binary as well.

You're right; but COBOL BCD types allowed arbitrary precision, and it was super-easy to debug data; the hex represention was the same as the decimal representation.

Re: Twenty five thousand dollars of funny money

#65

Earlier quoted context omitted.

People writing unit tests for internal tools? A lot of companies don't even having tests for production code.

Especially yes. A unit test would have caught this instantly. It is code that deals with $'s... something you'd really want to test, since it'll cost the company money. Instead, you've got multiple engineers writing code multiple times (my euphemism for fixing buggy code), which also costs the company money.

I'm just saying people don't do it in practice.

Re: Twenty five thousand dollars of funny money

#66
Critical things come with critical stickers:

Transformer boxes, Nuclear waste, Highly acidic compounds, High energy lasers, choking hazards.

The oldest debate: should there be a money primitive in the type system?

I mean, availability breeds use, use breeds awareness, awareness breeds or enforces proper use. A currency/money type would be a pretty clear label to ward off a whole suite of stupid bugs like the one described in this post.

Re: Twenty five thousand dollars of funny money

#67
post #57

Earlier quoted context omitted.

Seriously, since everything I work in is denoted as "cents" from backend to frontend, I personally had never understood the need This matches my experience. Obviously actual strict typing has its benefits, but as far as developer ergonomics are concerned, IME you can get about 95% of the benefits just by following a convention of including unit names in identifier names. It's easy to see why this Ruby code might fail…

> [follow] a convention of including unit names in identifier names. appending units to identifiers helps, but it relies on a developer's eyeballs to spot any errors. It would be infinitely preferable if the type system would simply enforce this for you and developers not have to expend cycles reasoning about this stuff themselves.

If you stick to just a few units throughout the system (ideally, use a consistent base unit everywhere and convert any external measurements to it), you can avoid the rest of the problems.

Static typing is great, of course, I just don't agree that this can't be solved to almost the same level with languages with dynamic typing.

Re: Twenty five thousand dollars of funny money

#69

I encountered a similar bug at the same company with far worse results. Won't say any specifics about the product impact, but our backend passed around two different kinds of user IDs. Each user had two different IDs, and the ID spaces overlapped. User Alice could have an ID in space 1 that is the same as Bob's ID in space 2. At some point, at least one function expected a "space 1" ID but was being passed a "space 2…

Oof, I'm happy it was just non-private data!

Regardless, this makes an excellent case for strongly typed wrappers as you mention at the end.

Our general approach is to use UUIDv4 for identifiers (so the chance of mistaking-one-for-another instantly leads to "not found"), but sometimes you don't have a choice. In those cases it's super-important to have strongly typed wrappers.

Re: Twenty five thousand dollars of funny money

#70

I'm gonna be honest, I had never understood the "strict type" argument until right now. Seriously, since everything I work in is denoted as "cents" from backend to frontend, I personally had never understood the need so I'm part of today's lucky 10,000th.

Seriously, since everything I work in is denoted as "cents" from backend to frontend, I personally had never understood the need This matches my experience. Obviously actual strict typing has its benefits, but as far as developer ergonomics are concerned, IME you can get about 95% of the benefits just by following a convention of including unit names in identifier names. It's easy to see why this Ruby code might fail…

Nope, this will lead to the same problem that the OP has discovered, viz., that a dependency update creates silent errors. Unless the argument is a keyword, but everyone is too lazy for that.
Post reply on HN