Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1vBWT5-0004v6-SS for pgsql-performance@arkaria.postgresql.org; Wed, 22 Oct 2025 10:53:23 +0000 Received: from localhost ([127.0.0.1] helo=malur.postgresql.org) by malur.postgresql.org with esmtp (Exim 4.94.2) (envelope-from ) id 1vBWT4-00FEgl-Q2 for pgsql-performance@arkaria.postgresql.org; Wed, 22 Oct 2025 10:53:21 +0000 Received: from makus.postgresql.org ([2001:4800:3e1:1::229]) by malur.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1vBPfY-00D4CB-MK for pgsql-performance@lists.postgresql.org; Wed, 22 Oct 2025 03:37:47 +0000 Received: from mail-lj1-x231.google.com ([2a00:1450:4864:20::231]) by makus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 (Exim 4.96) (envelope-from ) id 1vBPfV-0035YB-1r for pgsql-performance@lists.postgresql.org; Wed, 22 Oct 2025 03:37:46 +0000 Received: by mail-lj1-x231.google.com with SMTP id 38308e7fff4ca-376466f1280so65015181fa.0 for ; Tue, 21 Oct 2025 20:37:45 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=conevity-com.20230601.gappssmtp.com; s=20230601; t=1761104263; x=1761709063; darn=lists.postgresql.org; h=to:subject:message-id:date:from:in-reply-to:references:mime-version :from:to:cc:subject:date:message-id:reply-to; bh=L7eChtqeAM6vynvf+c7ipcaqZ+9H82Ih0ru6qOyFcpg=; b=yd0c9O56LunjrOe+FqTJHLl9nNOimDgMq+P2qpq2Ib9LGo++ApZQciw1xGvcNbrajc 1sWhTMFGWPWhsYx4m1iuboJK80vKcY2wY2Q04X/nrKij15JEGkuaAVxrjtBSEmdl67eU wl2Xz0Diafe73IJp1pw28xe7Wg86xYf9NZvwCaTG7LrIlm8fsrWg0tSfebVYShatO3jD VEPmHsTv/oTp7RtsvFNFtqCX07ip7p7S+lvtALzgXocpJgl+T4qwQSH6pzzuEQOc9YLE 1FFQvLJ4VV+oA1RAeSzTcGyezkGt/AL0bjB5HSoh1X0llrnJGdvb3OxZ9fqYD1xS50Md aA8A== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1761104263; x=1761709063; h=to:subject:message-id:date:from:in-reply-to:references:mime-version :x-gm-message-state:from:to:cc:subject:date:message-id:reply-to; bh=L7eChtqeAM6vynvf+c7ipcaqZ+9H82Ih0ru6qOyFcpg=; b=GX9y4nJQtIRdV+cvzHeNc7K4dwjFP0y5DGZ40+kh/KJEvPAj95pNY31RzJfmUrYPIK QJHHsMQ8OI3iabcFws0e/l4YN7uXI7dQN46FyeK2cmJFwNny6mfPcmf2MSeBCjXKQgJx MYEV9Ayk1/f+y12vL4oDIK6V/9PE16Euk7hKOJ+QtCw7UXhTQDyrflfcamJPiZpRj0xb HwvAYH+swiJNsNNjh86/MIN7zT1SnRvqJYhOXmMrr5OU0AbpSDooPSUAMLkyloRcwfSS OroXcSvzlV4M6UdN5LKTvSy0D/sJ4xdsUROBToDCro51uNXISuiuFPK331BYigPfi2ph oa7w== X-Gm-Message-State: AOJu0Ywtndlwt7dufwSSj++KPrTfvCPfvnpHarSKBEqeUPZcOZgY8Mtu W9nl9YKOLV7NJbq+sC+OCWp09Hj8hDchoBrbATeRvhNFF3Qud2zXXrWajezVYrv1WOXRdvRbWj5 T2dnO7K4= X-Gm-Gg: ASbGncvhExyh6Bfl0WBBUvkk+nxpdK2AWlINldI5LeMDogTULE4Z9AdRs8U8eUq2uzg t5VAOWQHGX+sotGjrV3Z5NBe4kcm905FGeJyc1qdQiSnLV2crvmBTvK6xxjDGoIMjNKqnOFAjZM PUZq1Q1oPiq5eol+kuqMj8oEg121jaCIk4EdAzOfFBwEt8sJUk8XYKpHOBj2kXRaF5Dk57UakCR PaOocERQbPlxMegUe6hxcFvldqlBaKn6Qy4B9p9PAb+BPuckH+g2Wn3LfRrDU1EY0XX3opkkqn5 8DEZRFxOkEl7PZ1XNUst4YL9nowIj7N8KJ9o+QTMSPcopfAv9xsMLN57fPd3B1F+rqUvA1IYfst UmAIbKS6zba7Yv+jQVjB3GqjZmxDTSCF3SRr3U4CKSSwy83/O8yPHb47HBalnl732p4makdS29B e6XpT5BEzAZ3Cy55TEeaDIR1XRlMElXXfL/ScZU0HfZ6C7J1xYOA== X-Google-Smtp-Source: AGHT+IHa/HkhrQBpVOx2nZnj/Qx7ldlrmT9R/3s4m7XR1vwc1d5CZJaUqbJUnlFbO6VsQD37ocohyQ== X-Received: by 2002:a05:651c:211c:b0:365:6b40:8656 with SMTP id 38308e7fff4ca-37797948f9bmr54445911fa.35.1761104263271; Tue, 21 Oct 2025 20:37:43 -0700 (PDT) Received: from mail-lf1-f43.google.com (mail-lf1-f43.google.com. [209.85.167.43]) by smtp.gmail.com with ESMTPSA id 38308e7fff4ca-377a95789f1sm33734791fa.41.2025.10.21.20.37.42 for (version=TLS1_3 cipher=TLS_AES_128_GCM_SHA256 bits=128/128); Tue, 21 Oct 2025 20:37:42 -0700 (PDT) Received: by mail-lf1-f43.google.com with SMTP id 2adb3069b0e04-59052926cf9so7120655e87.1 for ; Tue, 21 Oct 2025 20:37:42 -0700 (PDT) X-Received: by 2002:a05:6512:23a2:b0:55b:8afb:e644 with SMTP id 2adb3069b0e04-591d8595fb3mr7848863e87.31.1761104262278; Tue, 21 Oct 2025 20:37:42 -0700 (PDT) MIME-Version: 1.0 References: In-Reply-To: From: Jonathan Reis Date: Tue, 21 Oct 2025 20:37:30 -0700 X-Gmail-Original-Message-ID: X-Gm-Features: AS18NWCN_F_Q85GCHbSjGcHt5ZW6bMsYWGu_z-v76X5cYru8wJ1-AliNWOhtIJE Message-ID: Subject: Performance implications of partitioning by UUIDv7 range in PostgreSQL v18 To: pgsql-performance@lists.postgresql.org Content-Type: multipart/alternative; boundary="000000000000f733a30641b7096a" List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk --000000000000f733a30641b7096a Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable Hello PostgreSQL performance team, I=E2=80=99m evaluating the new UUIDv7 type in PostgreSQL v18 and would like= advice on its suitability for time-based partitioning and related planner behavior= . *Context* I have a large message/event table where each row is identified by a uuidv7 primary key. Because UUIDv7 embeds a timestamp component in its most significant bits, I=E2=80=99m considering using it as the partition key ins= tead of a separate timestamptz column. *Questions* 1. *Partitioning on UUIDv7 ranges* - Is range partitioning by UUIDv7 considered practical or advisable for time-based data? - Will the planner efficiently prune partitions when queries filter by UUIDv7 ranges (e.g., WHERE id BETWEEN uuidv7_floor(timestamp1) AND uuidv7_floor(timestamp2) that align with time periods? - Are there known drawbacks=E2=80=94such as statistics accuracy, correl= ation estimation, or index selectivity=E2=80=94when using UUIDv7 as a surro= gate for timestamptz? 2. *Conversion between timestamptz and UUIDv7* - Is there a built-in or community-recommended method to convert between timestamptz and uuidv7 values? I am currently using this CREATE OR REPLACE FUNCTION uuidv7_floor(ts timestamptz) RETURNS uuid LANGUAGE sql IMMUTABLE AS $$ WITH ms AS ( SELECT floor(extract(epoch FROM ts) * 1000)::bigint AS ms ), h AS ( SELECT lpad(to_hex(ms), 12, '0') AS h FROM ms ) SELECT ( substr(h.h,1,8) || '-' || substr(h.h,9,4) || '-' || '7000' || '-' || -- version 7 + rand_a all zero '8000' || '-' || -- variant '10' + rest zero '000000000000' -- zero node )::uuid FROM h; $$; *Example* CREATE TABLE message ( id uuidv7 PRIMARY KEY, payload jsonb, received_at timestamptz DEFAULT now() )PARTITION BY RANGE (id); I=E2=80=99d appreciate any insight into whether UUIDv7 is a good candidate = for partitioning from a performance standpoint, and how well partition pruning behaves in practice. Best regards, Jon --000000000000f733a30641b7096a Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable
Hello PostgreSQL performance team,

I=E2=80=99m evaluating the new UUIDv7 type in PostgreSQL v1= 8 and would like advice on its suitability for time-based partitioning and = related planner behavior.

Context
I have a large message/event table where each row is identified by a = uuidv7 primary key. Because UUIDv7 embeds a timestamp component in i= ts most significant bits, I=E2=80=99m considering using it as the partition= key instead of a separate timestamptz column.

Questions

  1. Partitioning on UUIDv7 ranges

    • Is range partitioning by UUIDv7 considered practical or advisable for ti= me-based data?

    • Will the planner efficiently prune partitions when queries filter by UUI= Dv7 ranges (e.g., WHERE id BETWEEN=C2=A0uuidv7_floor(tim= estamp1) AND=C2=A0uuidv7_floor(timestamp2)=C2=A0that al= ign with time periods?

    • Are there known drawbacks=E2=80=94such as statistics accuracy, correlati= on estimation, or index selectivity=E2=80=94when using UUIDv7 as a surrogat= e for timestamptz?

  2. Conversion between timestamptz and UUIDv7

    • Is there a built-in or community-recommended method to convert between <= code>timestamptz and uuidv7 values? I am currently usin= g this

      CREATE OR REPLACE FUNCTION uuidv7_floor(ts timestamptz)
      = =C2=A0 RETURNS uuid
      =C2=A0 LANGUAGE sql
      =C2=A0 IMMUTABLE
      AS $$
      = WITH ms AS (
      =C2=A0 SELECT floor(extract(epoch FROM ts) * 1000)::bigint = AS ms
      ),
      =C2=A0 =C2=A0 =C2=A0h AS (
      =C2=A0 =C2=A0 =C2=A0 =C2=A0SEL= ECT lpad(to_hex(ms), 12, '0') AS h FROM ms
      =C2=A0 =C2=A0 =C2=A0)=
      SELECT (
      =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0substr(h.h,1,8) || '-= ' ||
      =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0substr(h.h,9,4) || '-'= ; ||
      =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0'7000' || '-' || = =C2=A0 =C2=A0 =C2=A0 =C2=A0 -- version 7 + rand_a all zero
      =C2=A0 =C2=A0= =C2=A0 =C2=A0 =C2=A0'8000' || '-' || =C2=A0 =C2=A0 =C2=A0 = =C2=A0 -- variant '10' + rest zero
      =C2=A0 =C2=A0 =C2=A0 =C2=A0 = =C2=A0'000000000000' =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0 -- zero nod= e
      =C2=A0 =C2=A0 =C2=A0 =C2=A0 =C2=A0)::uuid
      FROM h;
      $$;

Example

CRE= ATE TABLE message ( id uuidv7 PRIMARY KEY, payload jsonb, received_at timestamptz DEFAULT now() ) PARTITION BY RANGE (id);

I=E2=80=99d appreciate any insight into whether UUIDv7 is a good candida= te for partitioning from a performance standpoint, and how well partition p= runing behaves in practice.

Best regards,
Jon

--000000000000f733a30641b7096a--