針對于unique索引在主外鍵上的表現,o和PG的行為確實不一致,測試樣例:
PG:
測試1:
test=# CREATE TABLE gdb_editingtemplates ( objectid INTEGER NOT NULL, globalid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, type SMALLINT NOT NULL, name VARCHAR(255) NOT NULL, defaulttool VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, datasetguid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, subtype INTEGER NULL, description VARCHAR(1024) NULL, tags VARCHAR(2000) NULL, visible SMALLINT NOT NULL, hash VARCHAR(64) NOT NULL, useridentity VARCHAR(255) NULL, status INTEGER NULL);
CREATE TABLECREATE UNIQUE INDEX EdTemplates_Globalid_idx ON gdb_editingtemplates (globalid );
CREATE INDEXCREATE TABLE gdb_editingtemplaterelationships ( objectid INTEGER NOT NULL, type SMALLINT NOT NULL, originid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, destid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL);
CREATE TABLE
test=# ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid);
ALTER TABLE
test=# select version();version
---------------------------------------------------------------------------------------------------------PostgreSQL 11.5 on x86_64-pc-linux-gnu, compiled by gcc (GCC) 4.8.5 20150623 (Red Hat 4.8.5-39), 64-bit
(1 行記錄)
test=# drop table gdb_editingtemplaterelationships;
DROP TABLE
test=# drop table gdb_editingtemplates;
DROP TABLE
test=# CREATE TABLE gdb_editingtemplates ( objectid INTEGER NOT NULL, globalid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, type SMALLINT NOT NULL, name VARCHAR(255) NOT NULL, defaulttool VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, datasetguid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, subtype INTEGER NULL, description VARCHAR(1024) NULL, tags VARCHAR(2000) NULL, visible SMALLINT NOT NULL, hash VARCHAR(64) NOT NULL, useridentity VARCHAR(255) NULL, status INTEGER NULL);
CREATE TABLE
test=# alter table gdb_editingtemplates add constraint gdb_editingtemplates_global_uniq unique(globalid);
ALTER TABLE
test=# CREATE TABLE gdb_editingtemplaterelationships ( objectid INTEGER NOT NULL, type SMALLINT NOT NULL, originid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, destid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL);
CREATE TABLE
test=# ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid);
ALTER TABLE
test=# select version();version
---------------------------------------------------------------------------------------------------------PostgreSQL 11.5 on x86_64-pc-linux-gnu, compiled by gcc (GCC) 4.8.5 20150623 (Red Hat 4.8.5-39), 64-bit
(1 行記錄)
華為GaussDB for openGauss:
test_temp=> select version();
-[ RECORD 1 ]--------------------------------------------------------------------------------------------------------------
version | gaussdb (GaussDB Kernel 503.1.0 build f53b4ed8) compiled at 2023-03-27 00:43:20 commit 5356 last mr 10743 releasetest_temp=> select * from pg_database where datname=current_database();
-[ RECORD 1 ]----+----------
datname | test_temp
datdba | 18389
encoding | 0
datcollate | C
datctype | C
datistemplate | f
datallowconn | t
datconnlimit | -1
datlastsysoid | 12810
datfrozenxid | 0
dattablespace | 1663
datcompatibility | A
datacl |
datfrozenxid64 | 14613
datminmxid | 2
dattimezone | PRCtest_temp=> CREATE TABLE gdb_editingtemplates ( objectid INTEGER NOT NULL, globalid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, type SMALLINT NOT NULL, name VARCHAR(255) NOT NULL, defaulttool VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, datasetguid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, subtype INTEGER NULL, description VARCHAR(1024) NULL, tags VARCHAR(2000) NULL, visible SMALLINT NOT NULL, hash VARCHAR(64) NOT NULL, useridentity VARCHAR(255) NULL, status INTEGER NULL);
CREATE TABLE
test_temp=>
test_temp=> CREATE UNIQUE INDEX EdTemplates_Globalid_idx ON gdb_editingtemplates (globalid );
CREATE INDEX
test_temp=> CREATE TABLE gdb_editingtemplaterelationships ( objectid INTEGER NOT NULL, type SMALLINT NOT NULL, originid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, destid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL);
CREATE TABLE
test_temp=> ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid);
ALTER TABLE
test_temp=> drop table gdb_editingtemplaterelationships;
DROP TABLE
test_temp=> drop table gdb_editingtemplates;
DROP TABLE
test_temp=> CREATE TABLE gdb_editingtemplates ( objectid INTEGER NOT NULL, globalid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, type SMALLINT NOT NULL, name VARCHAR(255) NOT NULL, defaulttool VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, datasetguid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, subtype INTEGER NULL, description VARCHAR(1024) NULL, tags VARCHAR(2000) NULL, visible SMALLINT NOT NULL, hash VARCHAR(64) NOT NULL, useridentity VARCHAR(255) NULL, status INTEGER NULL);
CREATE TABLE
test_temp=> alter table gdb_editingtemplates add constraint gdb_editingtemplates_global_uniq unique(globalid);
NOTICE: ALTER TABLE / ADD UNIQUE will create implicit index "gdb_editingtemplates_global_uniq" for table "gdb_editingtemplates"
ALTER TABLE
test_temp=> CREATE TABLE gdb_editingtemplaterelationships ( objectid INTEGER NOT NULL, type SMALLINT NOT NULL, originid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, destid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL);
CREATE TABLE
test_temp=> ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid);
ALTER TABLE
PG和華為 gaussDB for openGauss(兼容o模式)??,在主表的關聯鍵上建unique索引或者unique的constraint都可以。
O:
SQL> CREATE TABLE gdb_editingtemplates ( objectid INTEGER NOT NULL, globalid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, type SMALLINT NOT NULL, name VARCHAR(255) NOT NULL, defaulttool VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, datasetguid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NULL, subtype INTEGER NULL, description VARCHAR(1024) NULL, tags VARCHAR(2000) NULL, visible SMALLINT NOT NULL, hash VARCHAR(64) NOT NULL, useridentity VARCHAR(255) NULL, status INTEGER NULL);Table created.SQL> CREATE UNIQUE INDEX EdTemplates_Globalid_idx ON gdb_editingtemplates (globalid );Index created.SQL> CREATE TABLE gdb_editingtemplaterelationships ( objectid INTEGER NOT NULL, type SMALLINT NOT NULL, originid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL, destid VARCHAR(38) DEFAULT '{00000000-0000-0000-0000-000000000000}' NOT NULL);Table created.SQL> ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid);
ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid)*
ERROR at line 1:
ORA-02270: no matching unique or primary key for this column-listSQL> alter table gdb_editingtemplates add constraint gdb_editingtemplates_gid_unique unique(globalid);Table altered.SQL> ALTER TABLE GDB_EditingTemplateRelationships ADD CONSTRAINT EdTemplateRlships_OriginID_fk FOREIGN KEY (originid) REFERENCES GDB_EditingTemplates (globalid);Table altered.
在主表上的關聯鍵上建unique索引,在建關聯的時候會報錯,需要建一個unique的constraint才可以,也就是說o上不認unique索引,只認constraint。
個人認為,PG的兼容性更好些。
有些國產數據廠商的兼容O模式,為了兼容Oracle,也會是這樣的行為。