wxin 发表于 2016-11-21 10:44:20

对PostgreSQL中 pg_各表的RelationId的认识

  读取普通的table或者系统表,都会调用heap_open函数:



/* ----------------
*      heap_open - open a heap relation by relation OID
*
*      This is essentially relation_open plus check that the relation
*      is not an index nor a composite type.(The caller should also
*      check that it's not a view or foreign table before assuming it has
*      storage.)
* ----------------
*/
Relation
heap_open(Oid relationId, LOCKMODE lockmode)
{
//fprintf(stderr,"++++++++++++++++++++ In heap_open start by process %d....relationId is:%d\n",
      getpid(),relationId);
Relation    r;
r = relation_open(relationId, lockmode);
if (r->rd_rel->relkind == RELKIND_INDEX)
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
errmsg("\"%s\" is an index",
RelationGetRelationName(r))));
else if (r->rd_rel->relkind == RELKIND_COMPOSITE_TYPE)
ereport(ERROR,
(errcode(ERRCODE_WRONG_OBJECT_TYPE),
errmsg("\"%s\" is a composite type",
RelationGetRelationName(r))));
//fprintf(stderr,"++++++++++++++++++++ In heap_open end by process %d\n\n",getpid());
return r;
}
  对于普通表而言,RelationId就是在base目录下的某个子目录里面的文件名。
  但是对于系统表而言,则不同。
比如 pg_tablespace 的RelationId为 1213(这已经写死在PostgreSQL源代码中),
但是其对应的文件的名称为 12587(对应global/12587文件)。
  经过一番测试,发现其对应关系如下:




pg_default_acl
826


pg_pltemplate
1136


pg_tablespace
1213


pg_shdepend
1214


pg_type
1247


pg_attribute
1249


pg_proc
1255


pg_class
1259


pg_authid
1260


pg_auth_members
1261


pg_database
1262


pg_foreign_server
1417


pg_user_mapping
1418


pg_foreign_data_wrapper
2328


pg_shdescription
2396


pg_aggregate
2600


pg_am
2601


pg_amop
2602


pg_ampro
2603


pg_attrdef
2604


pg_cast
2605


pg_constraint
2606


pg_conversion
2607


pg_depend
2608


pg_description
2609


pg_index
2610


pg_inherits
2611


pg_language
2612


pg_largeobject
2613


pg_namespace
2615


pg_opclass
2616


pg_operator
2617


pg_rewrite
2618


pg_stastic
2619


pg_trigger
2620


pg_opfamily
2753


pg_db_role_setting
2964


pg_largeobject_metadata
2995


pg_extension
3079


pg_foreign_table
3118


pg_collation
3456


pg_enum
3501


pg_seclabel
3596


pg_ts_dict
3600


pg_ts_parser
3601


pg_ts_config
3602


pg_ts_config_map
3603


pg_ts_template
3764


  然后,我还可以进一步,观察 ,把上述表格补充完整:



/* ----------------
*      relation_open - open any relation by relation OID
*
*      If lockmode is not "NoLock", the specified kind of lock is
*      obtained on the relation.(Generally, NoLock should only be
*      used if the caller knows it has some appropriate lock on the
*      relation already.)
*
*      An error is raised if the relation does not exist.
*
*      NB: a "relation" is anything with a pg_class entry.The caller is
*      expected to check whether the relkind is something it can handle.
* ----------------
*/
Relation
relation_open(Oid relationId, LOCKMODE lockmode)
{
fprintf(stderr,"___________________ In relation_open start by process %d\n",getpid());
Relation    r;
Assert(lockmode >= NoLock && lockmode < MAX_LOCKMODES);
/* Get the lock before trying to open the relcache entry */
if (lockmode != NoLock)
LockRelationOid(relationId, lockmode);
/* The relcache does all the real work... */
r = RelationIdGetRelation(relationId);
fprintf(stderr,"In relation_open ,the relNode is:%d....\n\n",r->rd_node.relNode);
if (!RelationIsValid(r))
elog(ERROR, "could not open relation with OID %u", relationId);
/* Make note that we've accessed a temporary relation */
if (RelationUsesLocalBuffers(r))
MyXactAccessedTempRel = true;
pgstat_initstats(r);
fprintf(stderr,"___________________ In relation_open end by process %d\n",getpid());
return r;
}
  加入了调试代码后,我可以看到,pg_tablespace 的 RelationId是 1213,而它的对应文件名是 12587。
  下面,补充完整:

   


system table name
RelationId
FileName


pg_default_acl
826
12642


pg_pltemplate
1136
12591


pg_tablespace
1213
12587


pg_shdepend
1214
12598


pg_type
1247
12442


pg_attribute
1249
12446


pg_proc
1255
12458


pg_class
1259
12465


pg_authid
1260
12450


pg_auth_members
1261
12594


pg_database
1262
12692


pg_foreign_server
1417
12635


pg_user_mapping
1418
12454


pg_foreign_data_wrapper
2328
12631


pg_shdescription
2396
12602


pg_aggregate
2600
12525


pg_am
2601
12505


pg_amop
2602
12509


pg_ampro
2603
12514


pg_attrdef
2604
12469


pg_cast
2605
12549


pg_constraint
2606
12476


pg_conversion
2607
12562


pg_depend
2608
12567


pg_description
2609
12543


pg_index
2610
12489


pg_inherits
2611
12485


pg_language
2612
12518


pg_largeobject
2613
12571


pg_namespace
2615
12558


pg_opclass
2616
12501


pg_operator
2617
12493


pg_rewrite
2618
12528


pg_stastic
2619
12436


pg_trigger
2620
12535


pg_opfamily
2753
12497


pg_db_role_setting
2964
12581


pg_largeobject_metadata
2995
12522


pg_extension
3079
12627


pg_foreign_table
3118
12639


pg_collation
3456
12652


pg_enum
3501
12553


pg_seclabel
3596
12646


pg_ts_dict
3600
12615


pg_ts_parser
3601
12619


pg_ts_config
3602
12608


pg_ts_config_map
3603
12612


pg_ts_template
3764
12623


  如果进一步查看,还可以发现:
  只有如下几个系统表的对应文件位于 global目录,其余的系统表的对应文件则是base目录下的每个子目录中都有(一个子目录对应一个数据库):

   


system table name
RelationId
FileName


pg_pltemplate
1136
12591


pg_tablespace
1213
12587


pg_shdepend
1214
12598


pg_authid
1260
12450


pg_auth_members
1261
12594


pg_database
1262
12692


pg_shdescription
2396
12602


pg_db_role_setting
2964
12581


页: [1]
查看完整版本: 对PostgreSQL中 pg_各表的RelationId的认识