目录
PostgreSQL使用很多不同的系统目录来跟踪数据库对象(例如表和函数)的存在以及属性。系统目录和普通用户表之间在物理上没有什么不同,但是后端的C代码知道每一个目录的结构和属性,并且能够在较低的层次上直接操纵它们。因此,不建议尝试在运行中修改目录的结构,那样做会破坏内建在C代码中对目录行如何放置的设想。但是目录的结构可能会在主版本之间发生变化。
目录的结构声明在特殊格式的C头文件中,它们位于源码树的src/include/catalog/
目录中。特别地,对每一个目录都有一个以其名称命名的头文件(例如,pg_class
的头文件是pg_class.h
),头文件定义了目录具有的列集合,以及一些其他的基本属性(例如OID)。其他定义目录结构的重要文件包括indexing.h
和toasting.h
,前者定义所有系统目录上的索引,而后者为需要TOAST表的目录定义TOAST表。
很多目录都有初始数据,这些数据必须在initdb的“bootstrap”阶段装载到对应的目录中,这样才能让系统达到能够执行SQL命令的状态点(例如,pg_class.h
必须包含表示其自身的一个项,还要为每个系统目录和索引都分别包含一项)。这些初始数据以可编辑的形式保存在src/include/catalog/
目录下的数据文件中。例如,pg_proc.dat
描述了所有必须被插入到pg_proc
目录的初始行。
为了创建目录文件并且将这些初始数据载入其中,一个以bootstrap模式运行的后端会读取包含着命令和初始数据的BKI(后端接口)文件。这种模式中用到的postgres.bki
文件正是在编译PostgreSQL时从前述的头文件和数据文件准备而来,这一过程由名为genbki.pl
的Perl脚本负责。尽管postgres.bki
与特定PostgreSQL发行版相关,但它是平台无关的并且被安装在安装树的share
子目录中。
genbki.pl
还会为每个目录产生一个头文件,例如为pg_class
生成的头文件是pg_class_d.h
。这个文件含有自动生成的宏定义,并且可能包含其他的宏、枚举声明,因此对于读取特定目录的客户端C代码很有用。
大部分Postgres的开发者不需要直接与BKI文件打交道,但是几乎在后端中增加任何非平凡的特性都需要修改目录头文件或者初始数据文件。本章的剩余部分会给出一些相关的信息,并且将会完整地描述BKI文件格式。