我如何定义一个 plpgsql 函数,它接受一个没有模式限定且尚未创建的类型的参数

How can I define a plpgsql function that accepts a parameter of a type that is not schema qualified and is not yet created

我的数据库是根据每个应用程序用户的架构构建的。在每个模式中,都有一个相同的 table 命名为“条目”,具有完全相同的 DDL。我还有一个通用架构,其中包含一些对这些“条目”table 进行操作的函数,并且在执行期间,搜索路径定义了该函数在哪个架构的条目table 上运行。在创建任何用户架构之前,我在定义这些函数时遇到了问题,因为它们引用了用户架构中尚未创建的 table。该问题已使用 set check_function_bodies = off; 解决,但现在我遇到了一个类似的问题,该函数将那些 table 引用为 inout 参数。我无法创建该函数,因为它接受的参数是“条目”类型,并且我收到“类型条目不存在”的错误。 set check_function_bodies = off 没有解决这个问题。有没有办法解决这个问题? 函数签名是

create or replace function common.reconcile_user_entry(inout e entries) returns void

我真的不想在每个用户模式中定义这个函数,因为它总是相同的,而且我不想在需要进行更改时必须在每个模式中重新编译它。

你可以使用 inheritance

像所有其他 entries table 一样定义一个 table common.entries 并更改其他 entries table 以继承自它:

ALTER TABLE schema1.entries INHERIT common.entries;

然后定义函数以 common.entries 作为参数或 return 类型,您可以将它与任何继承的 table 一起使用。

我想你可以使用 table 继承。

您必须在通用架构中为用户架构中的每个 table 创建一个“父级”table。然后从他们那里继承用户table。定义函数参数时使用“parent”table 名称。参见示例:

CREATE TABLE parent(id integer);

CREATE TABLE child() INHERITS (parent);
INSERT INTO child(id) VALUES (1);

CREATE FUNCTION get_id(IN prm_row parent) RETURNS integer
LANGUAGE SQL
AS $$
  SELECT prm_row.id;
$$;

SELECT get_id((SELECT (child) FROM child WHERE id = 1));

请注意,父 table 将包含所有子 table 的记录,因此您应该使用权限来防止用户访问父 table。

我没有使用继承,而是通过像这样绕过问题来解决它:

而不是将函数签名定义为

create or replace function common.reconcile_user_entry(inout e entries) returns void

我定义为

create or replace function common.reconcile_user_entry(inout r record) returns void

并且在函数代码中我声明了一个变量e entries;然后将记录分配给变量:

declare 
 e entries;
begin
 select into e r.*
...

关于继承的解决方案,它有效,但我发现上面的解决方案更简单。 我知道我的解决方案一定有注意事项和隐藏的问题,如果有人可以指出,请指出。