Re: RFC: Additional Directory for Extensions - Mailing list pgsql-hackers

From Craig Ringer
Subject Re: RFC: Additional Directory for Extensions
Date
Msg-id CAGRY4nxP6A5Dz23g+aGD-agdVwUj_qrG6szd-mWc0E5OFMBg4w@mail.gmail.com
Whole thread Raw
In response to Re: RFC: Additional Directory for Extensions  (Gabriele Bartolini <gabriele.bartolini@enterprisedb.com>)
Responses Re: RFC: Additional Directory for Extensions
Re: RFC: Additional Directory for Extensions
Re: RFC: Additional Directory for Extensions
List pgsql-hackers
On Thu, 22 Aug 2024 at 08:00, Gabriele Bartolini
<gabriele.bartolini@enterprisedb.com> wrote:
>
> Hi everyone,
>
> Apologies for only starting to look into this now. Thanks, David, for pushing this forward.


 100%. I've wanted this for some time but never had time to cook up a patch.

> I want to emphasize the importance of this patch for the broader adoption of extensions in immutable container
environments,such as those used by the CloudNativePG operator in Kubernetes. 


It's also very relevant for local development and testing.

Right now postgres makes it impossible to locally compile and install
an extension for a distro-packaged postgres (whether from upstream
repos or PGDG repos) without dirtying the distro-managed filesystem
subtrees with local changes under /usr etc, because it cannot be
configured to look for locally installed extensions on non-default
paths.

> To provide some context, one of the key principles of CloudNativePG is that containers, once started, cannot be
modified—thisincludes the installation of Postgres extensions and their libraries. This restriction prevents us from
addingextensions on the fly, requiring them to be included in the main PostgreSQL operand image. As a result, users who
needspecific extensions must build custom images through automated pipelines (see:
https://cloudnative-pg.io/blog/creating-container-images/).


It may be possible to weaken this restriction somewhat thanks to the
upcoming https://kubernetes.io/blog/2024/08/16/kubernetes-1-31-image-volume-source/
feature that permits additional OCI images to be mounted as read-only
volumes on a workload. This would still only permit mounting at
Pod-creation time, not runtime mounting and unmonuting, but means the
base postgres image could be supplemented by mounting additional
images for extensions.

For example, one might mount image "postgis-vX.Y.Z" image onto base
image "postgresql-16" if support for PostGIS is desired, without then
having to bake every possible extension anyone might ever want into
the base image. This solves all sorts of messy issues with upgrades
and new version releases.

But for it to work, it must be possible to tell postgres to look in
_multiple places_ for extension .sql scripts and control files. This
is presently possible for modules (dynamic libraries, .so / .dylib /
.dll) but without a way to also configure the path for extensions it's
of very limited utility.

> We’ve been considering ways to improve this process for some time. The direction we're exploring involves mounting an
ephemeralvolume that contains the necessary extensions (namely $sharedir and $pkglibdir from pg_config). These volumes
wouldbe created and populated with the required extensions when the container starts and destroyed when it shuts down.
Tomake this work, each extension must be independently packaged as a container image containing the appropriate files
fora specific extension version, tailored to the architecture, distribution, OS version, and Postgres version. 


Right. And there might be more than one of them.

So IMO this should be a _path_ to search for extension control files
and SQL scripts.

If the current built-in default extension dir was exposed as a var
$extdir like we do for $libdir, this might look something like this
for local development and testing while working with a packaged
postgres build:

    SET extension_search_path = $extsdir, /opt/myapp/extensions,
/usr/local/postgres/my-custom-extension/extensions;
    SET dynamic_library_path = $libdir, /opt/myapp/lib,
/usr/local/postgres/my-custom-extension/lib

or in the container extensions case, something like:

    SET extension_search_path = $extsdir,
/mnt/extensions/pg16/postgis-vX.Y/extensions,
/mnt/extensions/pg16/gosuperfast/extensions;
    SET dynamic_library_path = $libdir,
/mnt/extensions/pg16/postgis-vX.Y/lib,
/mnt/extensions/pg16/gosuperfast/lib;

For safety, it might make sense to impose the restriction that if an
extension control file is found in a given directory, SQL scripts will
also only be looked for in that same directory. That way there's no
chance of accidentally mixing and matching SQL scripts from different
versions of an extension if it appears twice on the extension search
path in different places. The rule for loading SQL scripts would be:

* locate first directory on path contianing matching extension control file
* use this directory as the extension directory for all subsequent SQL
script loading and running actions

--
Craig Ringer
EnterpriseDB



pgsql-hackers by date:

Previous
From: Peter Smith
Date:
Subject: Re: CREATE SUBSCRIPTION - add missing test case
Next
From: Michael Harris
Date:
Subject: Re: ANALYZE ONLY