| ▲ | MBCook a day ago |
| Not only can you make a good guess at how many customers/etc exist, you can guess individual ones. World’s easiest hack. You’re looking at /customers/3836/bills? What happens if you change that to 4000? They’re a big company. I bet that exists. Did they put proper security checks EVERYWHERE? Easy to test. But if you’re at /customers/{big-long-hex-string}/bill the chances of you guessing another valid ID are basically zero. Yeah it’s security through obscurity. But it’s really good obscurity. |
|
| ▲ | neya 17 hours ago | parent | next [-] |
| This advice assumes /customers/:id/bills is public. Protected routes shouldn't expose sensitive information such as bills anyway, so this is more of an authorization issue (who can access which resource) more than privacy concerns. So this means, if you can access customes/4000/bills, then that's an application logic issue more than the type of ID itself. In a well designed application, you shouldn't be able to guess whether a record exists or not simply by accessing a protected URL.
As a counter argument - normal BIGINT or serial PKs are performant and are more than enough for most applications. |
| |
| ▲ | andrewjf 9 hours ago | parent [-] | | You describe a world where human skill is required to prevent these class of bugs, time and time again we've proven that people are people and bugs happen. Systems must be _structurally architected_ with security in mind. Security is layered, using a random key with 128-bit space makes guessing UUIDs infeasible. But _also_ you should be doing AuthZ on the records, and also you should be doing rate limiting on API so they can't be brute forced, either. |
|
|
| ▲ | morshu9001 a day ago | parent | prev [-] |
| You normally aren't supposed to expose the PK anyway. |
| |
| ▲ | bruce511 a day ago | parent [-] | | That advice was born primarily _because_ of the bigint/serial problem. If the PK is UUIDv4 then exposing the PK is less significant. In some use cases it can be possible to exclude, or anonymize the PK, but in other cases a PK is necessary. Once you start building APIs to allow others to access your system, a UUIDv4 is the best ID. There are some performance issues with very large tables though. If you have very large tables (think billions of rows) then UUIDv7 offers some performance benefits at a small security cost. Personally I use v4 for almost all my tables because only a very small number of them will get large enough to matter. But YMMV. | | |
| ▲ | morshu9001 13 hours ago | parent [-] | | It's not about table size so much as number of joins. You don't need to trade off between security and performance if you simply expose a uuid4 secondary col on a serial PK'd table. |
|
|