From fb153f35bf1699cddc531202b79e0e5673c62079 Mon Sep 17 00:00:00 2001 From: jbranchaud Date: Fri, 18 Oct 2024 17:43:46 -0500 Subject: [PATCH] Add Postgre Does Not Support Unsigned Integers as a PostgreSQL TIL --- README.md | 3 +- ...gres-does-not-support-unsigned-integers.md | 30 +++++++++++++++++++ 2 files changed, 32 insertions(+), 1 deletion(-) create mode 100644 postgres/postgres-does-not-support-unsigned-integers.md diff --git a/README.md b/README.md index bbfa08d..3675e95 100644 --- a/README.md +++ b/README.md @@ -10,7 +10,7 @@ pairing with smart people at Hashrocket. For a steady stream of TILs, [sign up for my newsletter](https://crafty-builder-6996.ck.page/e169c61186). -_1473 TILs and counting..._ +_1474 TILs and counting..._ --- @@ -796,6 +796,7 @@ _1473 TILs and counting..._ - [Max Identifier Length Is 63 Bytes](postgres/max-identifier-length-is-63-bytes.md) - [Open Heroku Database In Postico From Terminal](postgres/open-heroku-database-in-postico-from-terminal.md) - [pg Prefix Is Reserved For System Schemas](postgres/pg-prefix-is-reserved-for-system-schemas.md) +- [Postgres Does Not Support Unsigned Integers](postgres/postgres-does-not-support-unsigned-integers.md) - [Prepare, Execute, And Deallocate Statements](postgres/prepare-execute-and-deallocate-statements.md) - [Pretty Print Data Sizes](postgres/pretty-print-data-sizes.md) - [Pretty Printing JSONB Rows](postgres/pretty-printing-jsonb-rows.md) diff --git a/postgres/postgres-does-not-support-unsigned-integers.md b/postgres/postgres-does-not-support-unsigned-integers.md new file mode 100644 index 0000000..1431ca6 --- /dev/null +++ b/postgres/postgres-does-not-support-unsigned-integers.md @@ -0,0 +1,30 @@ +# Postgres Does Not Support Unsigned Integers + +PostgreSQL has a variety of sizes of integer types, from `smallint` (2 bytes) +to `integer` (4 bytes) to `bigint` (8 bytes), as well as [other numeric +types](https://www.postgresql.org/docs/current/datatype-numeric.html). + +It does _not_ however support unsigned versions of these numeric types. + +That means, with an `integer` for instance, we can store numbers between +`-2147483648` and `+2147483647`. That's everything that can fit into 4 bytes. +In a system that supported 4 byte unsigned integers we'd be able to represent +from `0` all the way up to `4294967295`. + +In PostgreSQL, we're limited to these _signed_ numeric types. + +That means if we were hoping that the data type could essentially enforce a +non-negative restriction on the data in one of our columns, we're going to have +to be more creative. The obvious choice to me is to consider adding a [check +constraint](https://www.postgresql.org/docs/current/ddl-constraints.html#DDL-CONSTRAINTS-CHECK-CONSTRAINTS) +(e.g. `quantity integer check (quantity > 0)`). + +Another option, as pointed out by [this StackOverflow +answer](https://stackoverflow.com/a/31833279/535590), is to create [a +user-defined _domain +type_](https://www.postgresql.org/docs/current/domains.html) that restricts +valid values. To me, the ergonomics of using a domain type are a bit awkward +and not worth the effort. + +With either of these solutions, we are only approximating an unsigned integer +and do not actually have the same range of values available.