Hello Tom,
07.09.2026 00:00, Alexander Lakhin wrote:
06.09.2026 22:07, Tom Lane wrote:
@@ -794,8 +794,10 @@ transformColumnDefinition(CreateStmtContext *cxt,
ColumnDef *column)
if (constraint->conname &&
notnull_constraint->conname &&
strcmp(notnull_constraint->conname,
constraint->conname) != 0)
- elog(ERROR, "conflicting not-null constraint names \"%s\" and
\"%s\"",
- notnull_constraint->conname, constraint->conname);
+ ereport(ERROR,
+ errcode(ERRCODE_SYNTAX_ERROR),
+ errmsg("conflicting not-null constraint names \"%s\" and
\"%s\"",
+ notnull_constraint->conname,
constraint->conname));
This does not seem like a "syntax error". Perhaps
ERRCODE_INVALID_OBJECT_DEFINITION would serve?
Yeah, I considered this, but the same errmsg in
AddRelationNotNullConstraints() uses ERRCODE_SYNTAX_ERROR. I found it
more consistent to emit the same code. Maybe it would make do the opposite
-- change the errcode in AddRelationNotNullConstraints() (there are two
instances there, though)... Moreover, ERRCODE_SYNTAX_ERROR is chosen for
many other similar messages in transformColumnDefinition(), so I'm not
sure if it makes sense to change all of those or just report "syntax error"
for consistency while keeping the patch focused.
I've changed that occurrence to ERRCODE_INVALID_OBJECT_DEFINITION, but as
I mentioned above, transformColumnDefinition() has many other SYNTAX_ERRORs
(originating from a56ff9a0b), besides AddRelationNotNullConstraints().
Please find attached a patch to correct these too, for consistency, if you
find this appropriate. There are other similar errors in parse_utilcmd.c,
but I'd stop here unless we want to start a new campaign not to define,
but correct error codes according to some convention.
We'd be well advised to make those two messages more consistent,
whether they're worth translating or not. Also I guess a sweep
for other "unreachable" errors in typmodout functions might be
useful
Changed three occurrences to use the same errmsg and errcode.
Please look at the attached v3-Define-...patch, where I think I addressed
all of your comments.
Thank you for your time!
Best regards,
Alexander
diff --git a/src/backend/catalog/objectaddress.c b/src/backend/catalog/objectaddress.c
index b08e076e65f..c1b2e84146b 100644
--- a/src/backend/catalog/objectaddress.c
+++ b/src/backend/catalog/objectaddress.c
@@ -4064,7 +4064,9 @@ getObjectDescription(const ObjectAddress *object, bool missing_ok)
}
default:
- elog(ERROR, "unsupported object class: %u", object->classId);
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("unsupported object class: %u", object->classId)));
}
/* an empty buffer is equivalent to no object found */
diff --git a/src/backend/commands/tablecmds.c b/src/backend/commands/tablecmds.c
index 8dc70bfa0f1..5a2c9f02bf6 100644
--- a/src/backend/commands/tablecmds.c
+++ b/src/backend/commands/tablecmds.c
@@ -9621,6 +9621,7 @@ ATPrepAddPrimaryKey(List **wqueue, Relation rel, AlterTableCmd *cmd,
tup = findNotNullConstraint(childrelid, strVal(column));
if (!tup)
ereport(ERROR,
+ errcode(ERRCODE_INVALID_TABLE_DEFINITION),
errmsg("column \"%s\" of table \"%s\" is not marked NOT NULL",
strVal(column), get_rel_name(childrelid)));
/* verify it's good enough */
diff --git a/src/backend/parser/parse_utilcmd.c b/src/backend/parser/parse_utilcmd.c
index f838311090b..f0c7755b8fb 100644
--- a/src/backend/parser/parse_utilcmd.c
+++ b/src/backend/parser/parse_utilcmd.c
@@ -805,8 +805,10 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (constraint->conname &&
notnull_constraint->conname &&
strcmp(notnull_constraint->conname, constraint->conname) != 0)
- elog(ERROR, "conflicting not-null constraint names \"%s\" and \"%s\"",
- notnull_constraint->conname, constraint->conname);
+ ereport(ERROR,
+ errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
+ errmsg("conflicting not-null constraint names \"%s\" and \"%s\"",
+ notnull_constraint->conname, constraint->conname));
if (notnull_constraint->is_no_inherit != constraint->is_no_inherit)
ereport(ERROR,
diff --git a/src/backend/storage/ipc/shmem.c b/src/backend/storage/ipc/shmem.c
index f971ee24192..f78c34daee1 100644
--- a/src/backend/storage/ipc/shmem.c
+++ b/src/backend/storage/ipc/shmem.c
@@ -1210,7 +1210,9 @@ pg_get_shmem_allocations_numa(PG_FUNCTION_ARGS)
Size *nodes;
if (pg_numa_init() == -1)
- elog(ERROR, "libnuma initialization failed or NUMA is not supported on this platform");
+ ereport(ERROR,
+ (errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
+ errmsg("libnuma initialization failed or NUMA is not supported on this platform")));
InitMaterializedSRF(fcinfo, 0);
diff --git a/src/backend/utils/adt/acl.c b/src/backend/utils/adt/acl.c
index a01d8f4bc41..913d715a8c8 100644
--- a/src/backend/utils/adt/acl.c
+++ b/src/backend/utils/adt/acl.c
@@ -989,7 +989,16 @@ acldefault_sql(PG_FUNCTION_ARGS)
objtype = OBJECT_TYPE;
break;
default:
- elog(ERROR, "unrecognized object type abbreviation: %c", objtypec);
+ /* Avoid printing non-ASCII bytes, else we have encoding issues */
+ if (objtypec >= ' ' && objtypec < 0x7f)
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("unrecognized object type abbreviation: \"%c\"", objtypec)));
+ else /* use \ooo format, like charout() */
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("unrecognized object type abbreviation: \"\\%03o\"",
+ (unsigned char) objtypec)));
}
PG_RETURN_ACL_P(acldefault(objtype, owner));
diff --git a/src/backend/utils/adt/timestamp.c b/src/backend/utils/adt/timestamp.c
index 8ef16c9ad4c..43efa548452 100644
--- a/src/backend/utils/adt/timestamp.c
+++ b/src/backend/utils/adt/timestamp.c
@@ -1186,7 +1186,9 @@ intervaltypmodout(PG_FUNCTION_ARGS)
fieldstr = "";
break;
default:
- elog(ERROR, "invalid INTERVAL typmod: 0x%x", typmod);
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("unrecognized interval typmod: %d", typmod)));
fieldstr = "";
break;
}
@@ -1246,7 +1248,9 @@ intervaltypmodleastfield(int32 typmod)
case INTERVAL_FULL_RANGE:
return 0; /* SECOND */
default:
- elog(ERROR, "invalid INTERVAL typmod: 0x%x", typmod);
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("unrecognized interval typmod: %d", typmod)));
break;
}
return 0; /* can't get here, but keep compiler quiet */
@@ -1489,7 +1493,9 @@ AdjustIntervalForTypmod(Interval *interval, int32 typmod,
/* fractional-second rounding will be dealt with below */
}
else
- elog(ERROR, "unrecognized interval typmod: %d", typmod);
+ ereport(ERROR,
+ (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
+ errmsg("unrecognized interval typmod: %d", typmod)));
/* Need to adjust sub-second precision? */
if (precision != INTERVAL_FULL_PRECISION)
diff --git a/src/pl/plpgsql/src/pl_gram.y b/src/pl/plpgsql/src/pl_gram.y
index 5e14a2d7302..37785f58cc2 100644
--- a/src/pl/plpgsql/src/pl_gram.y
+++ b/src/pl/plpgsql/src/pl_gram.y
@@ -393,7 +393,9 @@ comp_option : '#' K_OPTION K_DUMP
else if (strcmp($3, "off") == 0)
plpgsql_curr_compile->print_strict_params = false;
else
- elog(ERROR, "unrecognized print_strict_params option %s", $3);
+ ereport(ERROR,
+ (errcode(ERRCODE_SYNTAX_ERROR),
+ errmsg("unrecognized %s option \"%s\"", "print_strict_params", $3)));
}
| '#' K_VARIABLE_CONFLICT K_ERROR
{
diff --git a/src/backend/catalog/heap.c b/src/backend/catalog/heap.c
index 1c188b7a0ff..f7fa1b901d1 100644
--- a/src/backend/catalog/heap.c
+++ b/src/backend/catalog/heap.c
@@ -3001,7 +3001,7 @@ AddRelationNotNullConstraints(Relation rel, List *constraints,
{
if (other->is_no_inherit != constr->is_no_inherit)
ereport(ERROR,
- errcode(ERRCODE_SYNTAX_ERROR),
+ errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NO INHERIT declaration for not-null constraint on column \"%s\"",
strVal(linitial(constr->keys))));
@@ -3015,7 +3015,7 @@ AddRelationNotNullConstraints(Relation rel, List *constraints,
constr->conname = pstrdup(other->conname);
else if (strcmp(constr->conname, other->conname) != 0)
ereport(ERROR,
- errcode(ERRCODE_SYNTAX_ERROR),
+ errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting not-null constraint names \"%s\" and \"%s\"",
constr->conname, other->conname));
}
diff --git a/src/backend/parser/parse_utilcmd.c b/src/backend/parser/parse_utilcmd.c
index f0c7755b8fb..0210b568a1e 100644
--- a/src/backend/parser/parse_utilcmd.c
+++ b/src/backend/parser/parse_utilcmd.c
@@ -749,7 +749,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
case CONSTR_NULL:
if ((saw_nullable && column->is_not_null) || need_notnull)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NULL/NOT NULL declarations for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -767,7 +767,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
/* Disallow conflicting [NOT] NULL markings */
if (saw_nullable && !column->is_not_null)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NULL/NOT NULL declarations for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -775,7 +775,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (disallow_noinherit_notnull && constraint->is_no_inherit)
ereport(ERROR,
- errcode(ERRCODE_SYNTAX_ERROR),
+ errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NO INHERIT declarations for not-null constraints on column \"%s\"",
column->colname));
@@ -812,7 +812,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (notnull_constraint->is_no_inherit != constraint->is_no_inherit)
ereport(ERROR,
- errcode(ERRCODE_SYNTAX_ERROR),
+ errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NO INHERIT declarations for not-null constraints on column \"%s\"",
column->colname));
@@ -825,7 +825,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
case CONSTR_DEFAULT:
if (saw_default)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("multiple default values specified for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -855,7 +855,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (saw_identity)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("multiple identity specifications for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -877,7 +877,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
need_notnull = true;
else if (!column->is_not_null)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NULL/NOT NULL declarations for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -892,7 +892,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
errmsg("generated columns are not supported on typed tables")));
if (saw_generated)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("multiple generation clauses specified for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -910,7 +910,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
case CONSTR_PRIMARY:
if (saw_nullable && !column->is_not_null)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("conflicting NULL/NOT NULL declarations for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -975,7 +975,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (saw_default && saw_identity)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("both default and identity specified for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -983,7 +983,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (saw_default && saw_generated)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("both default and generation expression specified for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,
@@ -991,7 +991,7 @@ transformColumnDefinition(CreateStmtContext *cxt, ColumnDef *column)
if (saw_identity && saw_generated)
ereport(ERROR,
- (errcode(ERRCODE_SYNTAX_ERROR),
+ (errcode(ERRCODE_INVALID_OBJECT_DEFINITION),
errmsg("both identity and generation expression specified for column \"%s\" of table \"%s\"",
column->colname, cxt->relation->relname),
parser_errposition(cxt->pstate,