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 1uETml-008jMO-9t for pgsql-performance@arkaria.postgresql.org; Mon, 12 May 2025 14:05:39 +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 1uETmj-00GM9T-Lz for pgsql-performance@arkaria.postgresql.org; Mon, 12 May 2025 14:05:37 +0000 Received: from magus.postgresql.org ([2a02:c0:301:0:ffff::29]) by malur.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_256_GCM_SHA384 (Exim 4.94.2) (envelope-from ) id 1uETmj-00GM9L-Ac for pgsql-performance@lists.postgresql.org; Mon, 12 May 2025 14:05:37 +0000 Received: from mail-yb1-xb33.google.com ([2607:f8b0:4864:20::b33]) by magus.postgresql.org with esmtps (TLS1.3) tls TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256 (Exim 4.96) (envelope-from ) id 1uETmg-001WEe-2e for pgsql-performance@lists.postgresql.org; Mon, 12 May 2025 14:05:37 +0000 Received: by mail-yb1-xb33.google.com with SMTP id 3f1490d57ef6-e694601f624so3320974276.1 for ; Mon, 12 May 2025 07:05:35 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20230601; t=1747058734; x=1747663534; darn=lists.postgresql.org; h=cc:to:subject:message-id:date:from:in-reply-to:references :mime-version:from:to:cc:subject:date:message-id:reply-to; bh=ZKNkOf+ilXl0Tk68CEFijl79pXrbyIj8gpS0CV1aauU=; b=LSIGPht2Vr0/XRnNsMjdiQoU9Nutt+cqpapXn3YvhcCXGrkAWBIoPK1PtffbZudG35 jilr6CQaVJzyWpBZ1ghw8wySplRW8JGzFbaNaDonspyFagFhGO+C8Zc1oU0vaFVWAhNv hPR5K9wzZ749Rei5Y7GoY51yyHN1fzsI/Ypm2iDwBaZZRp8mECY/vaCCJPS4FcxLAgPm Zb3SudCJxRi4ysLUMtV8+UFg1T+OBIYTFWnS4/ede2G9o9UeMV+cCO3l38j0kQ1jbNMS Wsw8JU17rXdh6k3yMauSAjNDUI3DleOU85moz/+g38Jl0UU6QGXTTfuMgygGoJHV954o SwSQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1747058734; x=1747663534; h=cc: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=ZKNkOf+ilXl0Tk68CEFijl79pXrbyIj8gpS0CV1aauU=; b=AWVkXcZANNStPxXhp0zG8xaoR90YsYtLS2XPsX58YlR/MG0E8gFSVFkEwkY4GhT59s 7dxVFjf3Lch13nsIkgTyHbhh9Ty34B1XYDVR4mA7rcS7FIeqtc+Vdv7Os2J5BcijYJzn BK6z38zuNU4YdiP/oW3SfZ6QBqu9C4tJeWIjY4AJlwaPIqoS95N4Y0w0lZVjLN1UHVVP Qvp21h6v+BE6EumJ9TnbG1cNS9Qzu9PgRQNJhM3LYJpgMEm1XspzenlmvEderrpnxoua UfoayHHixtB4yaa5hvl5qZsR6L3ahjo43j4RmMmIxrmWMk9dLb9VeREvx1CtDFzV4Spz tn8Q== X-Gm-Message-State: AOJu0YzM2IWU8zbK4d51rYRMuJgg6liGyk75bN5gWeohji1ZlOrTKk3O PH3A6XFsCM5wnSWlvmDzoV1eDuQ4Fzi0/ZL+UZohJLuHLnqk+zyoYvGy0XUnCHRlGWirNgWvovw 0/E2AhMGt96LO2juV0A9tBsq1TFyPTcOcnbk= X-Gm-Gg: ASbGncv9CHlxnwX67Ru1rxwKxLOzSg8Bz+XOXBDqHZmTpXLl8n3uf/rGhKE7jA8RBTE yM0RAztYli2C/Ewq/ftmUY+lVsr/81aON3CjQC8TXTcQzyqOFFFiPzpqjy2U9JdxQ6D35s19SJL hh8+TN0WfJMRzNI6kiDsJerYi6BezPtcI= X-Google-Smtp-Source: AGHT+IGsjXL/3/a+KBau3TO0o++asZjx2oIeiXBhb5MiZ5nwrCiS2bLoYNn5EeiHM7GbXuwKNPIANREy25R/M41ixwQ= X-Received: by 2002:a05:6870:8a29:b0:2d6:103e:e43d with SMTP id 586e51a60fabf-2dba4358e85mr6441267fac.20.1747058722967; Mon, 12 May 2025 07:05:22 -0700 (PDT) MIME-Version: 1.0 References: <8480be46-6e2a-4b12-9f80-78ba3db79dfb@gmail.com> In-Reply-To: <8480be46-6e2a-4b12-9f80-78ba3db79dfb@gmail.com> From: Maxim Boguk Date: Mon, 12 May 2025 17:04:45 +0300 X-Gm-Features: AX0GCFsGPlDAFDiEVG1moiPjXXetZJemHCME78Wzx9eSIJqUAje3rXW0q-3jfaY Message-ID: Subject: Re: inefficient/wrong plan cache mode selection for queries with partitioned tables (postgresql 17) To: Andrei Lepikhov Cc: pgsql-performance@lists.postgresql.org Content-Type: multipart/alternative; boundary="00000000000095950a0634f0ce49" List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk --00000000000095950a0634f0ce49 Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable On Mon, May 12, 2025 at 4:48=E2=80=AFPM Andrei Lepikhov = wrote: > On 5/12/25 15:08, Maxim Boguk wrote: > > PS: problem not with difference between custom and generic planning tim= e > > but with prepared statements > > generic plan plans only once, but custom plan plan every call (and plan > > time cost 95% on total query runtime). > Ah, now I got it. > I'm aware of this problem from at least two sources of regular complaints= . > What can you do here? Let's imagine a palliative solution: > Having pg_stat_statements data and the list of prepared statements (see > pg_prepared_statement) and queryId enabled, there is a way to force a > custom or generic plan in specific cases only: look up into min/max > query execution time. If no big difference exists and planning time is > sufficient, setting force_generic_plan for this plan makes sense. In > another case, if the planning time is too short or the generic plan is > unstable - switch to force_custom_plan. > > It is not hard to write such a tiny extension. As I see, the only extra > stored "C" procedure is needed to set up force-plan-type flag employing > FetchPreparedStatement(). The rest of the code - querying > pg_stat_statements and switching between plan types may be written in > plpgsql. > > If I'm not mistaken, it will work with all PG versions that are > currently in support. What do you think? Such extension would be very useful (and in general - the solution based on the actual execution data - seems more stable/predictable than the plan cost based selection which is currently used by postgresql). --=20 Maxim Boguk Senior Postgresql DBA Phone UA: +380 99 143 0000 Phone AU: +61 45 218 5678 --00000000000095950a0634f0ce49 Content-Type: text/html; charset="UTF-8" Content-Transfer-Encoding: quoted-printable


On Mon, May 12, 2025 at 4:48=E2=80=AFPM Andrei Lepikhov <lepihov@gmail.com> wrote:
On 5/12/25 15:08, Maxim Boguk wro= te:
> PS: problem not with difference between custom and generic planning ti= me
> but with prepared statements
> generic plan plans only once, but custom plan plan every call (and pla= n
> time cost 95% on total query runtime).
Ah, now I got it.
I'm aware of this problem from at least two sources of regular complain= ts.
What can you do here? Let's imagine a palliative solution:
Having pg_stat_statements data and the list of prepared statements (see pg_prepared_statement) and queryId enabled, there is a way to force a
custom or generic plan in specific cases only: look up into min/max
query execution time. If no big difference exists and planning time is
sufficient, setting force_generic_plan for this plan makes sense. In
another case, if the planning time is too short or the generic plan is
unstable - switch to force_custom_plan.

It is not hard to write such a tiny extension. As I see, the only extra stored "C" procedure is needed to set up force-plan-type flag emp= loying
FetchPreparedStatement(). The rest of the code - querying
pg_stat_statements and switching between plan types may be written in
plpgsql.

If I'm not mistaken, it will work with all PG versions that are
currently in support. What do you think?

Such extension would be very useful (and in general - the solutio= n based on the actual execution data - seems more stable/predictable than t= he plan cost based selection which is currently used by postgresql).
<= br>
=C2=A0
-- <= /span>
=
Maxim Boguk
Senior Postgresql DBA

Phone= UA: +380 99 143 0000
Phone AU: +61=C2=A0 45 218 5678

<= /div>
--00000000000095950a0634f0ce49--