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 1tRGMD-008Mbn-PC for pgsql-general@arkaria.postgresql.org; Fri, 27 Dec 2024 19:50:50 +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 1tRGMB-00CYhe-En for pgsql-general@arkaria.postgresql.org; Fri, 27 Dec 2024 19:50:47 +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 1tRGMB-00CYhW-2h for pgsql-general@lists.postgresql.org; Fri, 27 Dec 2024 19:50:46 +0000 Received: from gaoxing.magnetkern.de ([2a01:4f8:c012:f130::1]) by makus.postgresql.org with esmtp (Exim 4.96) (envelope-from ) id 1tRGM8-000qbG-31 for pgsql-general@lists.postgresql.org; Fri, 27 Dec 2024 19:50:45 +0000 Received: from titanium.fritz.box (unknown [IPv6:2003:c2:6f20:ef00:264b:feff:fe54:b09c]) by gaoxing.magnetkern.de (Postfix) with ESMTPSA id 7950972789 for ; Fri, 27 Dec 2024 20:51:49 +0100 (CET) Date: Fri, 27 Dec 2024 20:50:25 +0100 From: Jan Behrens To: pgsql-general@lists.postgresql.org Subject: search_path for PL/pgSQL functions partially cached? Message-Id: <20241227205025.1d059f72c7c08d23c9648c26@magnetkern.de> X-Mailer: Sylpheed 3.7.0 (GTK+ 2.24.33; amd64-portbld-freebsd14.1) Mime-Version: 1.0 Content-Type: text/plain; charset=US-ASCII Content-Transfer-Encoding: 7bit List-Id: List-Help: List-Subscribe: List-Post: List-Owner: List-Archive: Archived-At: Precedence: bulk Hello, I'm experiencing some weird issues when running the following code in a psql session: ============ CREATE TABLE "tbl" ("col" NUMERIC(15, 0)); CREATE FUNCTION "foo"() RETURNS TEXT LANGUAGE plpgsql AS $$ BEGIN RETURN '2.4'; END; $$; BEGIN; CREATE SCHEMA "myschema"; SET LOCAL search_path TO 'myschema'; CREATE TABLE "tbl" ("col" NUMERIC); CREATE FUNCTION "foo"() RETURNS TEXT LANGUAGE plpgsql AS $$ BEGIN RETURN '5.4'; END; $$; CREATE FUNCTION "run"() RETURNS TEXT LANGUAGE plpgsql AS $$ DECLARE "variable" "tbl"."col"%TYPE; BEGIN "variable" := "foo"(); RETURN "variable"; END; $$; COMMIT; SELECT "myschema"."run"(); -- returns '2.4' (when run in the same session) -- reconnect to database here: \c SELECT "myschema"."run"(); -- returns '2' SET search_path TO 'myschema'; SELECT "myschema"."run"(); -- returns '5' -- reconnect to database again: \c SET search_path TO 'myschema'; SELECT "myschema"."run"(); -- returns '5.4' SET search_path TO 'public'; SELECT "myschema"."run"(); -- returns '2.4' again ============ I'm using PostgreSQL verison 16.4. Is this the expected behavior? If yes, where is this documented? If no, what would be the expected behavior? Of course, I could fix this by fully qualifying the table name "tbl" in the function. Nonetheless, I'm not really sure what's going on here. It seems that it matters *both* how the search_path was set during the *first* invocation of the function within a session *and* how it is set during the actual call of the function. So even if there are just two schemas involved, there are 4 possible outcomes for the "run" function's result ('2.4', '2', '5', and '5.4'). To me, this behavior seems to be somewhat dangerous. Maybe it is even considered a bug? Or is it documented somewhere? I remember running into some problems like that in the past already, but unfortunately, I don't remember details. I suppose this is because there is some caching mechanism in place. But apparently it only caches the "tbl"."col"%TYPE and not the "foo"() function call expression. Can someone explain to me what's going on, and what is the best practice to deal with it? Is there a way to avoid fully qualifying every type and expression? Which parts do I have to qualify or is this something that could be fixed in a future version of PostgreSQL? Many thanks and kind regards, Jan Behrens