在 postgresql 中将模式添加到路径

Posted

技术标签:

【中文标题】在 postgresql 中将模式添加到路径【英文标题】:add schema to path in postgresql 【发布时间】:2011-01-31 18:58:22 【问题描述】:

我正在将应用程序从公共架构中的所有应用程序转移到每个都有自己的架构的过程。对于每个应用程序,我都有一个小脚本,它将创建架构,然后为该架构创建表、函数等。是否有自动将新创建的模式添加到 search_path?目前,我看到的唯一方法是找到用户当前路径SHOW search_path;,然后将新架构添加到其中SET search_path to xxx,yyy,zzz;

我想以某种方式说,将架构 zzz 附加到 users_search 路径。这可能吗?

【问题讨论】:

【参考方案1】:

像这样使用set_config() 函数:

SELECT set_config(
    'search_path',
    current_setting('search_path') || ',zzz',
    false
) WHERE current_setting('search_path') !~ '(^|,)zzz(,|$)';

【讨论】:

我相信这只会为 当前 会话设置 search_path,而不会持续存在。 我在使用该正则表达式时遇到问题,因为我的路径在逗号后有一个空格。我改用'(^|,\s?)zzz(,|$)'【参考方案2】:

在理论答案的基础上,以下是您将架构永久附加到另一个用户的 search_path 的方法。对于设置只读用户和在不同的 .sql 文件中拆分各种模式的设置很有用。

create or replace function prepend_search_path(
    role_name text, schema_name text
) returns void as $$
declare
    current_search_path text;
begin
    -- First, we get the current search_path for that user
    select  replace(sc.configval,'search_path=','')
    from    pg_db_role_setting rs
    left 
    join    pg_roles r
    on      r.oid = rs.setrole,
    lateral unnest(rs.setconfig) as sc(configval)
    where   sc.configval like 'search_path=%'
    and r.rolname = role_name
    into current_search_path;

    -- It is possible that a new user is not in pg_roles. To fix this,
    -- we find the default search_path values.
    if not found then
        select boot_val
        from pg_settings
        where name='search_path'
        into current_search_path;
    end if;

    -- Prepend the schema_name to search_path
    if current_search_path !~ ('(^|, )' || schema_name || '(,|$)') then
        current_search_path := schema_name || ', ' || current_search_path;
    end if;


    -- Make the changes
    execute format('alter role %I set search_path = %s', role_name, current_search_path);
end
$$ language plpgsql;

为什么要前置?取决于您的用例。 IMO,为每个存储过程提供模式很有用。这意味着如果您更改存储过程,您只需在单独的架构中定义它并覆盖使用它的用户的 search_path。

【讨论】:

以上是关于在 postgresql 中将模式添加到路径的主要内容,如果未能解决你的问题,请参考以下文章

在 Laravel 中将 Public 添加到资产路径

在python中将标头添加到子进程的stdout

在 Tomcat 8 中将外部资源添加到类路径

如何在Rails中将服务目录添加到加载路径?

在 Linux 中将路径添加到 Qt Creator 中的库时出错

在Linux系统中将指定路径添加到环境变量中