search_path
是一个要查找的 schema 列表。search_path
中第一个匹配的表被认为是想要的表。如果 search_path
中没有匹配的表,就会报告错误,即使数据库中其他 schema 中存在匹配的表名。
在 search_path
中添加一个 schema,实际上是信任所有用户对该 schema 有 CREATE 权限。
命令行访问 AnalyticDB for PostgreSQL
psql 是 Greenplum 中比较常用的命令行工具,提供了丰富的命令,其二进制文件在 Greenplum 安装后的 BIN 目录下。
将客户端工具压缩包下载到本地后,需要进行解压并安装,以下内容以 CentOS 7 平台上安装 AnalyticDB PostgreSQL 6.0 版客户端工具为例,其使用方式如下:
- 在客户端工具压缩包目录下,解压文件,命令如下:
tar -xzvf adbpg_client_package.el7.x86_64.tar.gz
- 解压后切换到bin目录下,执行如下命令:
cd adbpg_client_package/bin
-
bin 目录下包括客户端工具 psql、pg_dump 等,按照各工具参考文档,执行命令行
-
配置环境变量
export PATH=$PATH:/home/username/adbpg_client_package/bin
- 通过指定参数的方式进行连接:
psql -h yourgpdbaddress.gpdb.rds.aliyuncs.com -p 5432 -d postgres -U gpdbaccount -h:指定主机地址 -p:指定端口号 -d:指定数据库(默认的数据库是 postgres) -U:指定连接的用户
- 输入密码,进入 psql 的命令行页面
psql (9.4.24) Type "help" for help. postgres=>
注:连接前,需配置网络白名单。
参数描述
search_path
中的第一个 schema 被称为当前 schema。除了是第一个被搜索的 schema 之外,如果 CREATE TABLE 命令没有指定 schema 名称,创建新表的 schema 默认即 search_path
中的第一个 schema。
查看参数
使用如下命令,显示当前的 search_path:
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
第一个值指定一个与当前用户同名的 schema 被搜索。如果不存在这样的 schema,该条目将被忽略。第二个元素指的是我们已经看到的 public schema。
search_path
中存在的第一个 schema 是创建新对象的默认位置。这就是默认情况下(当没有同名 schema 时),对象是在 public schema 中创建的原因。当对象在没有 schema 限定的情况下被引用时(表修改、数据修改或查询命令),search_path
被遍历,直到找到一个匹配的对象。因此,在默认配置中,任何未经限定的访问都只能引用 public schema。
设置参数
使用如下命令,可以将新的 schema 放在 search_path 中:
testadb=> set search_path to public, testsa; SET
我们在这里省略了 "$user",因为我们没有立即需要它,然后我们可以在没有 schema 限定的情况下访问 testsa 模式下的某张表。
-- 查看表结构 testadb=> \d dim_ann_poc; Table "testsa.dim_ann_poc" Column | Type | Modifiers ------------+-------------------------+----------- vc_type | character varying(1000) | vc_detaile | character varying(1000) | f_price | numeric | Distributed by: (vc_type)
另外,由于 testsa 是路径中的第一个元素,新的对象将默认在其中创建。
我们也可以这样写:
testadb=> set search_path to testsa; SET testadb=> show search_path; search_path ------------- testsa (1 row)
在当前会话下,我们就不能够在没有明确限定的情况下访问 public schema 了。
注:
- 当不同的 schema 中存在同名的对象,将使用在
search_path
中首先找到的对象 - 系统目录模式
pg_catalog
始终被搜索,无论是否在路径中提及 - 如果有 schema 存在大写字母,要用双引号,例如 "My_Schema"
search_path 持久性
针对会话修改
在连接中直接使用 set search_path to xxx
是可以针对本连接生效的,但是弊端就是仅对当前连接生效,重新连接数据库则被还原了。
- 查看当前数据库的 search_path
testadb=> show search_path; search_path ---------------- "$user",public (1 row)
- 针对会话修改
testadb=> set search_path to public, testsa; SET
- 查看修改后的 search_path
testadb=> show search_path; search_path ---------------- public, testsa (1 row)
- 重新登录数据库,再次查看 search_path
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
重新登录,针对会话修改的 search_path 失效。
针对数据库修改
- 查看当前数据库的 search_path
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
- 针对数据库修改
testadb=> alter database testadb set search_path to public, testsa; ALTER DATABASE
- 查看修改后的 search_path(需重新登录数据库)
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
- 重新登录数据库,再次查看 search_path
testadb=> show search_path; search_path ---------------- public, testsa (1 row)
重新登录,针对数据库修改的 search_path 永久生效。
案例使用
存在与用户名同名的 schema
注:此处的用户名,指登录数据库时的用户名。
环境说明:
- search_path 为 "$user", public
- 连接用户为 testzw
- 存在与用户名相同的 testzw schema
- 创建表 t1
操作示例:
- 查看当前用户
testadb=> select current_user; current_user -------------- testzw (1 row)
- 查看当前 search_path
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
- 创建与用户名同名的 schema
testadb=> create schema testzw; CREATE SCHEMA
- 查看当前数据库下的所有 schema
testadb=> \dn List of schemas Name | Owner ---------------+------------ IMV_delta | adbpgadmin adbpg_restore | adbpgadmin adbpg_toolkit | adbpgadmin gp_toolkit | adbpgadmin public | adbpgadmin testsa | testzw testzw | testzw (7 rows)
- 创建表(不指定模式)
testadb=> create table t1 (id int, name varchar(10)) distributed by (id); CREATE TABLE testadb=> \d t1; Table "testzw.t1" Column | Type | Modifiers --------+-----------------------+----------- id | integer | name | character varying(10) | Distributed by: (id)
- 创建表(指定 public 模式)
testadb=> create table public.t1 (id int, name varchar(10), age varchar(10)) distributed by (id); CREATE TABLE testadb=> \d t1; Table "testzw.t1" Column | Type | Modifiers --------+-----------------------+----------- id | integer | name | character varying(10) | Distributed by: (id) testadb=> \d public.t1; Table "public.t1" Column | Type | Modifiers --------+-----------------------+----------- id | integer | name | character varying(10) | age | character varying(10) | Distributed by: (id)
结论:
- 表 t1 的 schema 自动为 search_path 的第一选择 "$user",即 testzw
- 此时,对表 t1 的任何无前缀操作均在 testzw.t1 上
- 使用 \d t1 显示表结构时,优先显示 testzw schema 中的表
不存在与用户名同名的 schema
环境说明:
- search_path 为 "$user", public
- 连接用户为 testzw
- 不存在与用户名相同的 testzw schema
- 创建表 t1
操作示例:
- 查看当前用户
testadb=> select current_user; current_user -------------- testzw (1 row)
- 查看当前 search_path
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
- 删除与用户名同名的 schema
testadb=> drop schema testzw cascade;
- 查看当前数据库下的所有 schema
testadb=> \dn; List of schemas Name | Owner ---------------+------------ IMV_delta | adbpgadmin adbpg_restore | adbpgadmin adbpg_toolkit | adbpgadmin gp_toolkit | adbpgadmin public | adbpgadmin testsa | testzw (6 rows)
- 创建表(不指定模式)
testadb=> create table t2 (id int, name varchar(10)) distributed by (id); CREATE TABLE testadb=> \d t2; Table "public.t2" Column | Type | Modifiers --------+-----------------------+----------- id | integer | name | character varying(10) | Distributed by: (id)
结论:
- 表 t2 的 schema 自动为 search_path 的第二选择 public
- 此时,对表 t2 的任何无前缀操作均在 public.t2 上
修改 search_path
环境说明:
- 创建 schema myschema
- 设置 search_path 为 myschema(会话级)
- 无前缀创建表 t3
- 无前缀查看表 t3
操作示例:
- 查看当前用户
testadb=> select current_user; current_user -------------- testzw (1 row)
- 查看当前 search_path
testadb=> show search_path; search_path ----------------- "$user", public (1 row)
- 创建 schema
testadb=> create schema myschema; CREATE SCHEMA
- 查看当前数据库下的所有 schema
testadb=> \dn; List of schemas Name | Owner ---------------+------------ IMV_delta | adbpgadmin adbpg_restore | adbpgadmin adbpg_toolkit | adbpgadmin gp_toolkit | adbpgadmin myschema | testzw public | adbpgadmin testsa | testzw (7 rows)
- 修改 search_path
testadb=> set search_path to myschema; SET testadb=> show search_path; search_path ------------- myschema (1 row)
- 创建表(不指定模式)
testadb=> create table t3 (id int, name varchar(10)) distributed by (id); CREATE TABLE testadb=> \d t3; Table "myschema.t3" Column | Type | Modifiers --------+-----------------------+----------- id | integer | name | character varying(10) | Distributed by: (id)
结论:
- 根据 search_path 的设置,无前缀创建及查看的表 t3 的 schema 均为 myschema
参考资料
超详细 VMware 虚拟机下 CentOS 7 安装教程(图文详解)
云原生数据仓库 AnalyticDB PostgreSQL 版客户端连接
原创文章,转载请注明出处:http://www.opcoder.cn/article/56/