is a decompiled reconstruction, not the original text of the command.)
<function>pg_get_expr</function> decompiles the internal form of an
individual expression, such as the default value for a column. It can be
- useful when examining the contents of system catalogs.
+ useful when examining the contents of system catalogs. If the expression
+ might contain Vars, specify the OID of the relation they refer to as the
+ second parameter; if no Vars are expected, zero is sufficient.
<function>pg_get_viewdef</function> reconstructs the <command>SELECT</>
query that defines a view. Most of these functions come in two variants,
one of which can optionally <quote>pretty-print</> the result. The
int prettyFlags);
static char *pg_get_constraintdef_worker(Oid constraintId, bool fullCommand,
int prettyFlags);
-static char *pg_get_expr_worker(text *expr, Oid relid, char *relname,
+static text *pg_get_expr_worker(text *expr, Oid relid, const char *relname,
int prettyFlags);
static int print_function_arguments(StringInfo buf, HeapTuple proctup,
bool print_table_args, bool print_defaults);
*
* Currently, the expression can only refer to a single relation, namely
* the one specified by the second parameter. This is sufficient for
- * partial indexes, column default expressions, etc.
+ * partial indexes, column default expressions, etc. We also support
+ * Var-free expressions, for which the OID can be InvalidOid.
* ----------
*/
Datum
Oid relid = PG_GETARG_OID(1);
char *relname;
- /* Get the name for the relation */
- relname = get_rel_name(relid);
- if (relname == NULL)
- PG_RETURN_NULL(); /* should we raise an error? */
+ if (OidIsValid(relid))
+ {
+ /* Get the name for the relation */
+ relname = get_rel_name(relid);
- PG_RETURN_TEXT_P(string_to_text(pg_get_expr_worker(expr, relid, relname, 0)));
+ /*
+ * If the OID isn't actually valid, don't throw an error, just return
+ * NULL. This is a bit questionable, but it's what we've done
+ * historically, and it can help avoid unwanted failures when
+ * examining catalog entries for just-deleted relations.
+ */
+ if (relname == NULL)
+ PG_RETURN_NULL();
+ }
+ else
+ relname = NULL;
+
+ PG_RETURN_TEXT_P(pg_get_expr_worker(expr, relid, relname, 0));
}
Datum
prettyFlags = pretty ? PRETTYFLAG_PAREN | PRETTYFLAG_INDENT : 0;
- /* Get the name for the relation */
- relname = get_rel_name(relid);
- if (relname == NULL)
- PG_RETURN_NULL(); /* should we raise an error? */
+ if (OidIsValid(relid))
+ {
+ /* Get the name for the relation */
+ relname = get_rel_name(relid);
+ /* See notes above */
+ if (relname == NULL)
+ PG_RETURN_NULL();
+ }
+ else
+ relname = NULL;
- PG_RETURN_TEXT_P(string_to_text(pg_get_expr_worker(expr, relid, relname, prettyFlags)));
+ PG_RETURN_TEXT_P(pg_get_expr_worker(expr, relid, relname, prettyFlags));
}
-static char *
-pg_get_expr_worker(text *expr, Oid relid, char *relname, int prettyFlags)
+static text *
+pg_get_expr_worker(text *expr, Oid relid, const char *relname, int prettyFlags)
{
Node *node;
List *context;
/* Convert expression to node tree */
node = (Node *) stringToNode(exprstr);
+ pfree(exprstr);
+
+ /* Prepare deparse context if needed */
+ if (OidIsValid(relid))
+ context = deparse_context_for(relname, relid);
+ else
+ context = NIL;
+
/* Deparse */
- context = deparse_context_for(relname, relid);
str = deparse_expression_pretty(node, context, false, false,
prettyFlags, 0);
- pfree(exprstr);
-
- return str;
+ return string_to_text(str);
}
"typanalyze::pg_catalog.oid AS typanalyzeoid, "
"typcategory, typispreferred, "
"typdelim, typbyval, typalign, typstorage, "
- "pg_catalog.pg_get_expr(typdefaultbin, 'pg_catalog.pg_type'::pg_catalog.regclass) AS typdefaultbin, typdefault "
+ "pg_catalog.pg_get_expr(typdefaultbin, 0) AS typdefaultbin, typdefault "
"FROM pg_catalog.pg_type "
"WHERE oid = '%u'::pg_catalog.oid",
tinfo->dobj.catId.oid);
}
else if (fout->remoteVersion >= 80300)
{
+ /* Before 8.4, pg_get_expr does not allow 0 for its second arg */
appendPQExpBuffer(query, "SELECT typlen, "
"typinput, typoutput, typreceive, typsend, "
"typmodin, typmodout, typanalyze, "