温馨提示×

温馨提示×

您好,登录后才能下订单哦!

密码登录×
登录注册×
其他方式登录
点击 登录注册 即表示同意《亿速云用户服务条款》

PostgreSQL系统表及其TOAST是怎么定义的

发布时间:2021-06-30 16:20:23 来源:亿速云 阅读:285 作者:chen 栏目:大数据

本篇内容主要讲解“PostgreSQL系统表及其TOAST是怎么定义的”,感兴趣的朋友不妨来看看。本文介绍的方法操作简单快捷,实用性强。下面就让小编来带大家学习“PostgreSQL系统表及其TOAST是怎么定义的”吧!

本文只是讲PG怎样定义系统表,而不是修改系统表甚至是定义自己的系统表。

PG系统表,比如:pg_class、pg_attribute、pg_type 等等
这几个表相互关联,后两者要在pg_class记录自己的表定义,而pg_class又需要在后两者记录自己的字段和类型,看起来是个死扣。

关于它们怎么定义,有兴趣可以阅读:
System Catalog Declarations and Initial Contents
比以前的文档更加细致和明确,dat文件的定义方式也比以前更清晰。

1、系统表数据结构定义,打开 pg_class.h

CATALOG(pg_class,1259,RelationRelationId) BKI_BOOTSTRAP BKI_ROWTYPE_OID(83,RelationRelation_Rowtype_Id) BKI_SCHEMA_MACRO
{
  NameData  relname;    /* class name */
  Oid      relnamespace;  /* OID of namespace containing this class */
  Oid      reltype;    /* OID of entry in pg_type for table's
                 * implicit row type */
  Oid      reloftype;    /* OID of entry in pg_type for underlying
                 * composite type */
...

pg_class 表结构

flying=# \d pg_class
                     Table "pg_catalog.pg_class"
       Column        |     Type     | Collation | Nullable | Default
---------------------+--------------+-----------+----------+---------
 relname             | name         |           | not null |
 relnamespace        | oid          |           | not null |
 reltype             | oid          |           | not null |
 reloftype           | oid          |           | not null |
...

是不是一一对应,事实上建表脚本就是由这里抽取生成,所以它们才如此一致。

2、src/backend/catalog/genbki.pl脚本

这个Perl脚本负责抽取定义并生成postgres.bki,有兴趣可以结合上边的文档理解它。

BKI脚本由一个单独的语法引擎支持,不是我们常说的SQL,它在bootstrap下,有兴趣可以自己看,以后有机会再讲。

3、代码

我们这里只是看看PG怎么做,并不是修改,每个定义都有其相应代码,它们在commands和catalog下。

后边我会单独写一篇如何新增自己的系统字段。

4、TOAST表

像text类型的字段需要toast存储,系统表的OID都是预置并且不允许修改,所以它们的TOAST同样需要预设。

来看 src/include/catalog/toasting.h,以 pg_proc为例:

DECLARE_TOAST(pg_proc, 2836, 2837);

这个preprocessor是这样定义的:

#define DECLARE_TOAST(name,toastoid,indexoid) extern int no_such_variable

看起来毫无意义对吧,其实它并不是真的给PG代码用,而是genbki,看过代码就知道怎么回事。

5、索引

系统表也是需要索引的,定义在 src/include/catalog/indexing.h,还是以 pg_proc为例:

DECLARE_UNIQUE_INDEX(pg_proc_oid_index, 2690, on pg_proc using btree(oid oid_ops));
#define ProcedureOidIndexId  2690
DECLARE_UNIQUE_INDEX(pg_proc_proname_args_nsp_index, 2691, on pg_proc using btree(proname name_ops, proargtypes oidvector_ops, pronamespace oid_ops));
#define ProcedureNameArgsNspIndexId  2691

它有两个索引,上边的定义包括:名字、OID、am、字段。

这些预处理符同样不是给C代码准备的,只有genbki用得上。

6、初始数据

它们定义在同名的dat文件里,比如 pg_proc.dat。

7、字段可选值

这个并不算表定义,但也是放在一起的,比如pg_proc的provolatile只允许:

#define PROVOLATILE_IMMUTABLE	'i' /* never changes for given input */
#define PROVOLATILE_STABLE		's' /* does not change within a scan */
#define PROVOLATILE_VOLATILE	'v' /* can change even within a scan */

到此,相信大家对“PostgreSQL系统表及其TOAST是怎么定义的”有了更深的了解,不妨来实际操作一番吧!这里是亿速云网站,更多相关内容可以进入相关频道进行查询,关注我们,继续学习!

向AI问一下细节

免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。

AI