From ca64391d6ca5a8aef6876961f2a8517e014b472d Mon Sep 17 00:00:00 2001 From: Bruce Momjian Date: Wed, 25 Jun 2003 03:56:31 +0000 Subject: [PATCH] Updated the pg_get_constraintdef() to use conbin. Update pg_dump to use pg_get_constraintdef() for >= 70400. Rod Taylor --- src/backend/utils/adt/ruleutils.c | 35 +++++++++++++++++++-- src/backend/utils/cache/lsyscache.c | 33 ++++++++++++++++++- src/bin/pg_dump/pg_dump.c | 49 +++++++++++++++++++++++------ src/include/utils/lsyscache.h | 3 +- 4 files changed, 105 insertions(+), 15 deletions(-) diff --git a/src/backend/utils/adt/ruleutils.c b/src/backend/utils/adt/ruleutils.c index 1040ff3e23..27259044c1 100644 --- a/src/backend/utils/adt/ruleutils.c +++ b/src/backend/utils/adt/ruleutils.c @@ -3,7 +3,7 @@ * back to source text * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/utils/adt/ruleutils.c,v 1.141 2003/05/28 16:03:59 tgl Exp $ + * $Header: /cvsroot/pgsql/src/backend/utils/adt/ruleutils.c,v 1.142 2003/06/25 03:56:30 momjian Exp $ * * This software is copyrighted by Jan Wieck - Hamburg. * @@ -894,6 +894,10 @@ pg_get_constraintdef(PG_FUNCTION_ARGS) { Datum val; bool isnull; + char *conbin; + char *consrc; + Node *expr; + List *context; /* Start off the constraint definition */ /* The consrc for CHECK constraints always seems to be @@ -901,14 +905,39 @@ pg_get_constraintdef(PG_FUNCTION_ARGS) appendStringInfo(&buf, "CHECK "); /* Fetch constraint source */ - val = heap_getattr(tup, Anum_pg_constraint_consrc, + val = heap_getattr(tup, Anum_pg_constraint_conbin, RelationGetDescr(conDesc), &isnull); if (isnull) elog(ERROR, "pg_get_constraintdef: Null consrc for constraint %u", constraintId); + conbin = DatumGetCString(DirectFunctionCall1(textout, val)); + expr = stringToNode(conbin); + + /* + * If top level is a List, assume it is an implicit-AND structure, and + * convert to explicit AND. This is needed for partial index + * predicates. + */ + if (expr && IsA(expr, List)) + expr = (Node *) make_ands_explicit((List *) expr); + + if (conForm->conrelid != InvalidOid) + /* It's a Relation */ + context = deparse_context_for(get_rel_name(conForm->conrelid), + conForm->conrelid); + else + /* + * Since VARNOs aren't allowed in domain constraints, relation context + * isn't required as anything other than a shell. + */ + context = deparse_context_for(get_typname(conForm->contypid), + InvalidOid); + + consrc = deparse_expression(expr, context, false, false); + /* Append the constraint source */ - appendStringInfoString(&buf, DatumGetCString(DirectFunctionCall1(textout, val))); + appendStringInfoString(&buf, consrc); break; } diff --git a/src/backend/utils/cache/lsyscache.c b/src/backend/utils/cache/lsyscache.c index a4fcd3fc28..2c0c645791 100644 --- a/src/backend/utils/cache/lsyscache.c +++ b/src/backend/utils/cache/lsyscache.c @@ -7,7 +7,7 @@ * Portions Copyright (c) 1994, Regents of the University of California * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/backend/utils/cache/lsyscache.c,v 1.97 2003/06/24 23:14:46 momjian Exp $ + * $Header: /cvsroot/pgsql/src/backend/utils/cache/lsyscache.c,v 1.98 2003/06/25 03:56:31 momjian Exp $ * * NOTES * Eventually, the index information should go through here, too. @@ -1443,6 +1443,37 @@ get_typtype(Oid typid) return '\0'; } +/* + * get_typname + * Returns the name of a given type. + * + * Returns a palloc'd copy of the string, or NULL if no such relation. + * + * NOTE: since type name is not unique, be wary of code that uses this + * for anything except preparing error messages. + */ +char * +get_typname(Oid typid) +{ + HeapTuple tp; + + tp = SearchSysCache(TYPEOID, + ObjectIdGetDatum(typid), + 0, 0, 0); + if (HeapTupleIsValid(tp)) + { + Form_pg_type typtup = (Form_pg_type) GETSTRUCT(tp); + char *result; + + result = pstrdup(NameStr(typtup->typname)); + ReleaseSysCache(tp); + return result; + } + else + return NULL; +} + + /* * get_typ_typrelid * diff --git a/src/bin/pg_dump/pg_dump.c b/src/bin/pg_dump/pg_dump.c index e241c8e15b..4879620f12 100644 --- a/src/bin/pg_dump/pg_dump.c +++ b/src/bin/pg_dump/pg_dump.c @@ -12,7 +12,7 @@ * by PostgreSQL * * IDENTIFICATION - * $Header: /cvsroot/pgsql/src/bin/pg_dump/pg_dump.c,v 1.333 2003/06/11 16:29:42 tgl Exp $ + * $Header: /cvsroot/pgsql/src/bin/pg_dump/pg_dump.c,v 1.334 2003/06/25 03:56:31 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -3303,10 +3303,17 @@ dumpOneDomain(Archive *fout, TypeInfo *tinfo) /* * Fetch and process CHECK constraints for the domain */ - appendPQExpBuffer(chkquery, "SELECT conname, consrc " - "FROM pg_catalog.pg_constraint " - "WHERE contypid = '%s'::pg_catalog.oid", - tinfo->oid); + if (g_fout->remoteVersion >= 70400) + appendPQExpBuffer(chkquery, "SELECT conname," + "pg_catalog.pg_get_constraintdef(oid) AS consrc " + "FROM pg_catalog.pg_constraint " + "WHERE contypid = '%s'::pg_catalog.oid", + tinfo->oid); + else + appendPQExpBuffer(chkquery, "SELECT conname, 'CHECK (' || consrc || ')'" + "FROM pg_catalog.pg_constraint " + "WHERE contypid = '%s'::pg_catalog.oid", + tinfo->oid); res = PQexec(g_conn, chkquery->data); if (!res || @@ -3326,7 +3333,7 @@ dumpOneDomain(Archive *fout, TypeInfo *tinfo) conname = PQgetvalue(res, i, PQfnumber(res, "conname")); consrc = PQgetvalue(res, i, PQfnumber(res, "consrc")); - appendPQExpBuffer(q, "\n\tCONSTRAINT %s CHECK %s", + appendPQExpBuffer(q, "\n\tCONSTRAINT %s %s", fmtId(conname), consrc); } @@ -5257,8 +5264,29 @@ dumpOneTable(Archive *fout, TableInfo *tbinfo, TableInfo *g_tblinfo) tbinfo->relname); resetPQExpBuffer(query); - if (g_fout->remoteVersion >= 70300) - appendPQExpBuffer(query, "SELECT conname, consrc" + if (g_fout->remoteVersion >= 70400) + appendPQExpBuffer(query, "SELECT conname, " + " pg_catalog.pg_get_constraintdef(c1.oid) AS consrc " + " from pg_catalog.pg_constraint c1" + " where conrelid = '%s'::pg_catalog.oid " + " and contype = 'c' " + " and not exists " + " (select 1 from " + " pg_catalog.pg_constraint c2, " + " pg_catalog.pg_inherits i " + " where i.inhrelid = c1.conrelid " + " and (c2.conname = c1.conname " + " or (c2.conname[0] = '$' " + " and c1.conname[0] = '$')" + " )" + " and pg_catalog.pg_get_constraintdef(c2.oid) " + " = pg_catalog.pg_get_constraintdef(c1.oid) " + " and c2.conrelid = i.inhparent) " + " order by conname ", + tbinfo->oid); + else if (g_fout->remoteVersion >= 70300) + appendPQExpBuffer(query, "SELECT conname, " + " 'CHECK (' || consrc || ')'" " from pg_catalog.pg_constraint c1" " where conrelid = '%s'::pg_catalog.oid " " and contype = 'c' " @@ -5276,7 +5304,8 @@ dumpOneTable(Archive *fout, TableInfo *tbinfo, TableInfo *g_tblinfo) " order by conname ", tbinfo->oid); else - appendPQExpBuffer(query, "SELECT rcname as conname, rcsrc as consrc" + appendPQExpBuffer(query, "SELECT rcname as conname," + " 'CHECK (' || rcsrc || ')' as consrc" " from pg_relcheck c1" " where rcrelid = '%s'::oid " " and not exists " @@ -5321,7 +5350,7 @@ dumpOneTable(Archive *fout, TableInfo *tbinfo, TableInfo *g_tblinfo) if (name[0] != '$') appendPQExpBuffer(q, "CONSTRAINT %s ", fmtId(name)); - appendPQExpBuffer(q, "CHECK (%s)", expr); + appendPQExpBuffer(q, "%s", expr); } PQclear(res2); } diff --git a/src/include/utils/lsyscache.h b/src/include/utils/lsyscache.h index 0b1badd6ef..e9de9f02c3 100644 --- a/src/include/utils/lsyscache.h +++ b/src/include/utils/lsyscache.h @@ -6,7 +6,7 @@ * Portions Copyright (c) 1996-2002, PostgreSQL Global Development Group * Portions Copyright (c) 1994, Regents of the University of California * - * $Id: lsyscache.h,v 1.72 2003/06/24 23:14:49 momjian Exp $ + * $Id: lsyscache.h,v 1.73 2003/06/25 03:56:31 momjian Exp $ * *------------------------------------------------------------------------- */ @@ -81,6 +81,7 @@ extern char get_typtype(Oid typid); extern Oid get_typ_typrelid(Oid typid); extern Oid get_element_type(Oid typid); extern Oid get_array_type(Oid typid); +extern char *get_typname(Oid relid); extern void getTypeInputInfo(Oid type, Oid *typInput, Oid *typElem); extern void getTypeOutputInfo(Oid type, Oid *typOutput, Oid *typElem, bool *typIsVarlena);