【发布时间】:2019-03-11 14:43:10
【问题描述】:
我有一个 PostgreSQL 表,在不同的字段上有两个唯一索引(nickname 和 email)。我正在尝试插入一条违反这两个约束的记录。我希望首先检查并报告nickname。
我观察到首先检查首先创建的索引,所以我首先在nickname 上创建索引并且它有点工作。但是这种行为是指定的,我可以依赖它吗,还是只是偶然?
【问题讨论】:
标签: postgresql unique-constraint
我有一个 PostgreSQL 表,在不同的字段上有两个唯一索引(nickname 和 email)。我正在尝试插入一条违反这两个约束的记录。我希望首先检查并报告nickname。
我观察到首先检查首先创建的索引,所以我首先在nickname 上创建索引并且它有点工作。但是这种行为是指定的,我可以依赖它吗,还是只是偶然?
【问题讨论】:
标签: postgresql unique-constraint
PostgreSQL使用RelationGetIndexList获取索引列表,评论说:
/*
* RelationGetIndexList -- get a list of OIDs of indexes on this relation
[...]
*
* The returned list is guaranteed to be sorted in order by OID. This is
* needed by the executor, since for index types that we obtain exclusive
* locks on when updating the index, all backends must lock the indexes in
* the same order or we will get deadlocks (see ExecOpenIndices()). Any
* consistent ordering would do, but ordering by OID is easy.
[...]
*/
OID(对象标识符)是向上计数的 4 字节无符号整数,因此通常后面的对象将获得更高的 OID。这与您观察到的相符。
但是,一旦 OID 的范围用完,它们就会回绕并从 FirstNormalObjectId (16384) 重新开始,因此不能保证首先创建的索引具有较低的 OID。
您可以使用如下查询:
SELECT 'indexname'::regclass::oid;
查找每个索引的 OID。
要获取表上所有索引的 OID,请使用
SELECT indexrelid AS oid, indexrelid::regclass
FROM pg_index
WHERE indrelid = 'tablename'::regclass;
【讨论】: