Doc: clarify that CREATE TABLE discards redundant unique constraints.

The SQL standard says that redundant unique constraints are disallowed,
but we long ago decided that throwing an error would be too
user-unfriendly, so we just drop redundant ones.  The docs weren't very
clear about that though, as this behavior was only explained for PRIMARY
KEY vs UNIQUE, not UNIQUE vs UNIQUE.

While here, I couldn't resist doing some copy-editing and markup-fixing
on the adjacent text about INCLUDE options.

Per bug #16767 from Matthias vd Meent.

Discussion: https://postgr.es/m/16767-1714a2056ca516d0@postgresql.org
This commit is contained in:
Tom Lane 2020-12-08 13:09:47 -05:00
parent 9a2641911a
commit f2a69b352d
1 changed files with 36 additions and 22 deletions

View File

@ -878,15 +878,17 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
<varlistentry> <varlistentry>
<term><literal>UNIQUE</literal> (column constraint)</term> <term><literal>UNIQUE</literal> (column constraint)</term>
<term><literal>UNIQUE ( <replaceable class="parameter">column_name</replaceable> [, ... ] )</literal> <term><literal>UNIQUE ( <replaceable class="parameter">column_name</replaceable> [, ... ] )</literal>
<optional> INCLUDE ( <replaceable class="parameter">column_name</replaceable> [, ...]) </optional> (table constraint)</term> <optional> <literal>INCLUDE ( <replaceable class="parameter">column_name</replaceable> [, ...])</literal> </optional> (table constraint)</term>
<listitem> <listitem>
<para> <para>
The <literal>UNIQUE</literal> constraint specifies that a The <literal>UNIQUE</literal> constraint specifies that a
group of one or more columns of a table can contain group of one or more columns of a table can contain
only unique values. The behavior of the unique table constraint only unique values. The behavior of a unique table constraint
is the same as that for column constraints, with the additional is the same as that of a unique column constraint, with the
capability to span multiple columns. additional capability to span multiple columns. The constraint
therefore enforces that any two rows must differ in at least one
of these columns.
</para> </para>
<para> <para>
@ -895,10 +897,10 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
</para> </para>
<para> <para>
Each unique table constraint must name a set of columns that is Each unique constraint should name a set of columns that is
different from the set of columns named by any other unique or different from the set of columns named by any other unique or
primary key constraint defined for the table. (Otherwise it primary key constraint defined for the table. (Otherwise, redundant
would just be the same constraint listed twice.) unique constraints will be discarded.)
</para> </para>
<para> <para>
@ -911,10 +913,15 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
<para> <para>
Adding a unique constraint will automatically create a unique btree Adding a unique constraint will automatically create a unique btree
index on the column or group of columns used in the constraint. index on the column or group of columns used in the constraint.
The optional clause <literal>INCLUDE</literal> adds to that index </para>
one or more columns on which the uniqueness is not enforced.
Note that although the constraint is not enforced on the included columns, <para>
it still depends on them. Consequently, some operations on these columns The optional <literal>INCLUDE</literal> clause adds to that index
one or more columns that are simply <quote>payload</quote>: uniqueness
is not enforced on them, and the index cannot be searched on the basis
of those columns. However they can be retrieved by an index-only scan.
Note that although the constraint is not enforced on included columns,
it still depends on them. Consequently, some operations on such columns
(e.g., <literal>DROP COLUMN</literal>) can cause cascaded constraint and (e.g., <literal>DROP COLUMN</literal>) can cause cascaded constraint and
index deletion. index deletion.
</para> </para>
@ -924,7 +931,7 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
<varlistentry> <varlistentry>
<term><literal>PRIMARY KEY</literal> (column constraint)</term> <term><literal>PRIMARY KEY</literal> (column constraint)</term>
<term><literal>PRIMARY KEY ( <replaceable class="parameter">column_name</replaceable> [, ... ] )</literal> <term><literal>PRIMARY KEY ( <replaceable class="parameter">column_name</replaceable> [, ... ] )</literal>
<optional> INCLUDE ( <replaceable class="parameter">column_name</replaceable> [, ...]) </optional> (table constraint)</term> <optional> <literal>INCLUDE ( <replaceable class="parameter">column_name</replaceable> [, ...])</literal> </optional> (table constraint)</term>
<listitem> <listitem>
<para> <para>
The <literal>PRIMARY KEY</literal> constraint specifies that a column or The <literal>PRIMARY KEY</literal> constraint specifies that a column or
@ -942,27 +949,34 @@ WITH ( MODULUS <replaceable class="parameter">numeric_literal</replaceable>, REM
<para> <para>
<literal>PRIMARY KEY</literal> enforces the same data constraints as <literal>PRIMARY KEY</literal> enforces the same data constraints as
a combination of <literal>UNIQUE</literal> and <literal>NOT NULL</literal>, but a combination of <literal>UNIQUE</literal> and <literal>NOT
NULL</literal>. However,
identifying a set of columns as the primary key also provides metadata identifying a set of columns as the primary key also provides metadata
about the design of the schema, since a primary key implies that other about the design of the schema, since a primary key implies that other
tables can rely on this set of columns as a unique identifier for rows. tables can rely on this set of columns as a unique identifier for rows.
</para> </para>
<para> <para>
<literal>PRIMARY KEY</literal> constraints share the restrictions that When placed on a partitioned table, <literal>PRIMARY KEY</literal>
<literal>UNIQUE</literal> constraints have when placed on partitioned constraints share the restrictions previously decribed
tables. for <literal>UNIQUE</literal> constraints.
</para> </para>
<para> <para>
Adding a <literal>PRIMARY KEY</literal> constraint will automatically Adding a <literal>PRIMARY KEY</literal> constraint will automatically
create a unique btree index on the column or group of columns used in the create a unique btree index on the column or group of columns used in the
constraint. The optional <literal>INCLUDE</literal> clause allows a list constraint.
of columns to be specified which will be included in the non-key portion </para>
of the index. Although uniqueness is not enforced on the included columns,
the constraint still depends on them. Consequently, some operations on the <para>
included columns (e.g., <literal>DROP COLUMN</literal>) can cause cascaded The optional <literal>INCLUDE</literal> clause adds to that index
constraint and index deletion. one or more columns that are simply <quote>payload</quote>: uniqueness
is not enforced on them, and the index cannot be searched on the basis
of those columns. However they can be retrieved by an index-only scan.
Note that although the constraint is not enforced on included columns,
it still depends on them. Consequently, some operations on such columns
(e.g., <literal>DROP COLUMN</literal>) can cause cascaded constraint and
index deletion.
</para> </para>
</listitem> </listitem>
</varlistentry> </varlistentry>