From cf0cab868aa4758b7eec5f9412f2ec74acda7f45 Mon Sep 17 00:00:00 2001 From: Tom Lane Date: Thu, 16 Dec 2021 14:02:28 -0500 Subject: [PATCH] Remove psql support for server versions preceding 9.2. Per discussion, we'll limit support for old servers to those branches that can still be built easily on modern platforms, which as of now is 9.2 and up. Aside from removing code that is dead per the assumption of server >= 9.2, I tweaked the startup warning for unsupported versions to complain about too-old servers as well as too-new ones. The warning that "Some psql features might not work" applies precisely to both cases. Discussion: https://postgr.es/m/2923349.1634942313@sss.pgh.pa.us --- src/bin/psql/command.c | 56 +-- src/bin/psql/common.c | 27 +- src/bin/psql/describe.c | 954 +++++++++--------------------------- src/bin/psql/large_obj.c | 31 +- src/bin/psql/tab-complete.c | 4 +- 5 files changed, 259 insertions(+), 813 deletions(-) diff --git a/src/bin/psql/command.c b/src/bin/psql/command.c index f5b2cd12c0f..ccd7b481084 100644 --- a/src/bin/psql/command.c +++ b/src/bin/psql/command.c @@ -1103,21 +1103,7 @@ exec_command_ef_ev(PsqlScanState scan_state, bool active_branch, NULL, true); int lineno = -1; - if (pset.sversion < (is_func ? 80400 : 70400)) - { - char sverbuf[32]; - - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf)); - if (is_func) - pg_log_error("The server (version %s) does not support editing function source.", - sverbuf); - else - pg_log_error("The server (version %s) does not support editing view definitions.", - sverbuf); - status = PSQL_CMD_ERROR; - } - else if (!query_buf) + if (!query_buf) { pg_log_error("no query buffer"); status = PSQL_CMD_ERROR; @@ -2418,21 +2404,7 @@ exec_command_sf_sv(PsqlScanState scan_state, bool active_branch, buf = createPQExpBuffer(); obj_desc = psql_scan_slash_option(scan_state, OT_WHOLE_LINE, NULL, true); - if (pset.sversion < (is_func ? 80400 : 70400)) - { - char sverbuf[32]; - - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf)); - if (is_func) - pg_log_error("The server (version %s) does not support showing function source.", - sverbuf); - else - pg_log_error("The server (version %s) does not support showing view definitions.", - sverbuf); - status = PSQL_CMD_ERROR; - } - else if (!obj_desc) + if (!obj_desc) { if (is_func) pg_log_error("function name is required"); @@ -3611,7 +3583,12 @@ connection_warnings(bool in_startup) else if (in_startup) printf("%s (%s)\n", pset.progname, PG_VERSION); - if (pset.sversion / 100 > client_ver / 100) + /* + * Warn if server's major version is newer than ours, or if server + * predates our support cutoff (currently 9.2). + */ + if (pset.sversion / 100 > client_ver / 100 || + pset.sversion < 90200) printf(_("WARNING: %s major version %s, server major version %s.\n" " Some psql features might not work.\n"), pset.progname, @@ -5271,8 +5248,7 @@ get_create_object_cmd(EditableObjectType obj_type, Oid oid, * ensure the right view gets replaced. Also, check relation kind * to be sure it's a view. * - * Starting with 9.2, views may have reloptions (security_barrier) - * and from 9.4 onwards they may also have WITH [LOCAL|CASCADED] + * Starting with PG 9.4, views may have WITH [LOCAL|CASCADED] * CHECK OPTION. These are not part of the view definition * returned by pg_get_viewdef() and so need to be retrieved * separately. Materialized views (introduced in 9.3) may have @@ -5291,24 +5267,12 @@ get_create_object_cmd(EditableObjectType obj_type, Oid oid, "ON c.relnamespace = n.oid WHERE c.oid = %u", oid); } - else if (pset.sversion >= 90200) - { - printfPQExpBuffer(query, - "SELECT nspname, relname, relkind, " - "pg_catalog.pg_get_viewdef(c.oid, true), " - "c.reloptions AS reloptions, " - "NULL AS checkoption " - "FROM pg_catalog.pg_class c " - "LEFT JOIN pg_catalog.pg_namespace n " - "ON c.relnamespace = n.oid WHERE c.oid = %u", - oid); - } else { printfPQExpBuffer(query, "SELECT nspname, relname, relkind, " "pg_catalog.pg_get_viewdef(c.oid, true), " - "NULL AS reloptions, " + "c.reloptions AS reloptions, " "NULL AS checkoption " "FROM pg_catalog.pg_class c " "LEFT JOIN pg_catalog.pg_namespace n " diff --git a/src/bin/psql/common.c b/src/bin/psql/common.c index 1b224bf9e42..ec975c3e2a5 100644 --- a/src/bin/psql/common.c +++ b/src/bin/psql/common.c @@ -1200,7 +1200,6 @@ SendQuery(const char *query) bool OK = false; int i; bool on_error_rollback_savepoint = false; - static bool on_error_rollback_warning = false; if (!pset.db) { @@ -1264,28 +1263,16 @@ SendQuery(const char *query) (pset.cur_cmd_interactive || pset.on_error_rollback == PSQL_ERROR_ROLLBACK_ON)) { - if (on_error_rollback_warning == false && pset.sversion < 80000) + results = PQexec(pset.db, "SAVEPOINT pg_psql_temporary_savepoint"); + if (PQresultStatus(results) != PGRES_COMMAND_OK) { - char sverbuf[32]; - - pg_log_warning("The server (version %s) does not support savepoints for ON_ERROR_ROLLBACK.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - on_error_rollback_warning = true; - } - else - { - results = PQexec(pset.db, "SAVEPOINT pg_psql_temporary_savepoint"); - if (PQresultStatus(results) != PGRES_COMMAND_OK) - { - pg_log_info("%s", PQerrorMessage(pset.db)); - ClearOrSaveResult(results); - ResetCancelConn(); - goto sendquery_cleanup; - } + pg_log_info("%s", PQerrorMessage(pset.db)); ClearOrSaveResult(results); - on_error_rollback_savepoint = true; + ResetCancelConn(); + goto sendquery_cleanup; } + ClearOrSaveResult(results); + on_error_rollback_savepoint = true; } if (pset.gdesc_flag) diff --git a/src/bin/psql/describe.c b/src/bin/psql/describe.c index 72d8547628a..c28788e84fa 100644 --- a/src/bin/psql/describe.c +++ b/src/bin/psql/describe.c @@ -3,8 +3,9 @@ * * Support for the various \d ("describe") commands. Note that the current * expectation is that all functions in this file will succeed when working - * with servers of versions 7.4 and up. It's okay to omit irrelevant - * information for an old server, but not to fail outright. + * with servers of versions 9.2 and up. It's okay to omit irrelevant + * information for an old server, but not to fail outright. (But failing + * against a pre-9.2 server is allowed.) * * Copyright (c) 2000-2021, PostgreSQL Global Development Group * @@ -72,35 +73,15 @@ describeAggregates(const char *pattern, bool verbose, bool showSystem) printfPQExpBuffer(&buf, "SELECT n.nspname as \"%s\",\n" " p.proname AS \"%s\",\n" - " pg_catalog.format_type(p.prorettype, NULL) AS \"%s\",\n", + " pg_catalog.format_type(p.prorettype, NULL) AS \"%s\",\n" + " CASE WHEN p.pronargs = 0\n" + " THEN CAST('*' AS pg_catalog.text)\n" + " ELSE pg_catalog.pg_get_function_arguments(p.oid)\n" + " END AS \"%s\",\n", gettext_noop("Schema"), gettext_noop("Name"), - gettext_noop("Result data type")); - - if (pset.sversion >= 80400) - appendPQExpBuffer(&buf, - " CASE WHEN p.pronargs = 0\n" - " THEN CAST('*' AS pg_catalog.text)\n" - " ELSE pg_catalog.pg_get_function_arguments(p.oid)\n" - " END AS \"%s\",\n", - gettext_noop("Argument data types")); - else if (pset.sversion >= 80200) - appendPQExpBuffer(&buf, - " CASE WHEN p.pronargs = 0\n" - " THEN CAST('*' AS pg_catalog.text)\n" - " ELSE\n" - " pg_catalog.array_to_string(ARRAY(\n" - " SELECT\n" - " pg_catalog.format_type(p.proargtypes[s.i], NULL)\n" - " FROM\n" - " pg_catalog.generate_series(0, pg_catalog.array_upper(p.proargtypes, 1)) AS s(i)\n" - " ), ', ')\n" - " END AS \"%s\",\n", - gettext_noop("Argument data types")); - else - appendPQExpBuffer(&buf, - " pg_catalog.format_type(p.proargtypes[0], NULL) AS \"%s\",\n", - gettext_noop("Argument data types")); + gettext_noop("Result data type"), + gettext_noop("Argument data types")); if (pset.sversion >= 110000) appendPQExpBuffer(&buf, @@ -223,55 +204,28 @@ describeTablespaces(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80000) - { - char sverbuf[32]; - - pg_log_info("The server (version %s) does not support tablespaces.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); - if (pset.sversion >= 90200) - printfPQExpBuffer(&buf, - "SELECT spcname AS \"%s\",\n" - " pg_catalog.pg_get_userbyid(spcowner) AS \"%s\",\n" - " pg_catalog.pg_tablespace_location(oid) AS \"%s\"", - gettext_noop("Name"), - gettext_noop("Owner"), - gettext_noop("Location")); - else - printfPQExpBuffer(&buf, - "SELECT spcname AS \"%s\",\n" - " pg_catalog.pg_get_userbyid(spcowner) AS \"%s\",\n" - " spclocation AS \"%s\"", - gettext_noop("Name"), - gettext_noop("Owner"), - gettext_noop("Location")); + printfPQExpBuffer(&buf, + "SELECT spcname AS \"%s\",\n" + " pg_catalog.pg_get_userbyid(spcowner) AS \"%s\",\n" + " pg_catalog.pg_tablespace_location(oid) AS \"%s\"", + gettext_noop("Name"), + gettext_noop("Owner"), + gettext_noop("Location")); if (verbose) { appendPQExpBufferStr(&buf, ",\n "); printACLColumn(&buf, "spcacl"); - } - - if (verbose && pset.sversion >= 90000) - appendPQExpBuffer(&buf, - ",\n spcoptions AS \"%s\"", - gettext_noop("Options")); - - if (verbose && pset.sversion >= 90200) - appendPQExpBuffer(&buf, - ",\n pg_catalog.pg_size_pretty(pg_catalog.pg_tablespace_size(oid)) AS \"%s\"", - gettext_noop("Size")); - - if (verbose && pset.sversion >= 80200) appendPQExpBuffer(&buf, + ",\n spcoptions AS \"%s\"" + ",\n pg_catalog.pg_size_pretty(pg_catalog.pg_tablespace_size(oid)) AS \"%s\"" ",\n pg_catalog.shobj_description(oid, 'pg_tablespace') AS \"%s\"", + gettext_noop("Options"), + gettext_noop("Size"), gettext_noop("Description")); + } appendPQExpBufferStr(&buf, "\nFROM pg_catalog.pg_tablespace\n"); @@ -348,24 +302,11 @@ describeFunctions(const char *functypes, const char *func_pattern, return true; } - if (showWindow && pset.sversion < 80400) - { - char sverbuf[32]; - - pg_log_error("\\df does not take a \"%c\" option with server version %s", - 'w', - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - if (!showAggregate && !showNormal && !showProcedure && !showTrigger && !showWindow) { - showAggregate = showNormal = showTrigger = true; + showAggregate = showNormal = showTrigger = showWindow = true; if (pset.sversion >= 110000) showProcedure = true; - if (pset.sversion >= 80400) - showWindow = true; } initPQExpBuffer(&buf); @@ -394,7 +335,7 @@ describeFunctions(const char *functypes, const char *func_pattern, gettext_noop("proc"), gettext_noop("func"), gettext_noop("Type")); - else if (pset.sversion >= 80400) + else appendPQExpBuffer(&buf, " pg_catalog.pg_get_function_result(p.oid) as \"%s\",\n" " pg_catalog.pg_get_function_arguments(p.oid) as \"%s\",\n" @@ -412,68 +353,6 @@ describeFunctions(const char *functypes, const char *func_pattern, gettext_noop("trigger"), gettext_noop("func"), gettext_noop("Type")); - else if (pset.sversion >= 80100) - appendPQExpBuffer(&buf, - " CASE WHEN p.proretset THEN 'SETOF ' ELSE '' END ||\n" - " pg_catalog.format_type(p.prorettype, NULL) as \"%s\",\n" - " CASE WHEN proallargtypes IS NOT NULL THEN\n" - " pg_catalog.array_to_string(ARRAY(\n" - " SELECT\n" - " CASE\n" - " WHEN p.proargmodes[s.i] = 'i' THEN ''\n" - " WHEN p.proargmodes[s.i] = 'o' THEN 'OUT '\n" - " WHEN p.proargmodes[s.i] = 'b' THEN 'INOUT '\n" - " WHEN p.proargmodes[s.i] = 'v' THEN 'VARIADIC '\n" - " END ||\n" - " CASE\n" - " WHEN COALESCE(p.proargnames[s.i], '') = '' THEN ''\n" - " ELSE p.proargnames[s.i] || ' '\n" - " END ||\n" - " pg_catalog.format_type(p.proallargtypes[s.i], NULL)\n" - " FROM\n" - " pg_catalog.generate_series(1, pg_catalog.array_upper(p.proallargtypes, 1)) AS s(i)\n" - " ), ', ')\n" - " ELSE\n" - " pg_catalog.array_to_string(ARRAY(\n" - " SELECT\n" - " CASE\n" - " WHEN COALESCE(p.proargnames[s.i+1], '') = '' THEN ''\n" - " ELSE p.proargnames[s.i+1] || ' '\n" - " END ||\n" - " pg_catalog.format_type(p.proargtypes[s.i], NULL)\n" - " FROM\n" - " pg_catalog.generate_series(0, pg_catalog.array_upper(p.proargtypes, 1)) AS s(i)\n" - " ), ', ')\n" - " END AS \"%s\",\n" - " CASE\n" - " WHEN p.proisagg THEN '%s'\n" - " WHEN p.prorettype = 'pg_catalog.trigger'::pg_catalog.regtype THEN '%s'\n" - " ELSE '%s'\n" - " END AS \"%s\"", - gettext_noop("Result data type"), - gettext_noop("Argument data types"), - /* translator: "agg" is short for "aggregate" */ - gettext_noop("agg"), - gettext_noop("trigger"), - gettext_noop("func"), - gettext_noop("Type")); - else - appendPQExpBuffer(&buf, - " CASE WHEN p.proretset THEN 'SETOF ' ELSE '' END ||\n" - " pg_catalog.format_type(p.prorettype, NULL) as \"%s\",\n" - " pg_catalog.oidvectortypes(p.proargtypes) as \"%s\",\n" - " CASE\n" - " WHEN p.proisagg THEN '%s'\n" - " WHEN p.prorettype = 'pg_catalog.trigger'::pg_catalog.regtype THEN '%s'\n" - " ELSE '%s'\n" - " END AS \"%s\"", - gettext_noop("Result data type"), - gettext_noop("Argument data types"), - /* translator: "agg" is short for "aggregate" */ - gettext_noop("agg"), - gettext_noop("trigger"), - gettext_noop("func"), - gettext_noop("Type")); if (verbose) { @@ -582,7 +461,7 @@ describeFunctions(const char *functypes, const char *func_pattern, } appendPQExpBufferStr(&buf, "p.prorettype <> 'pg_catalog.trigger'::pg_catalog.regtype\n"); } - if (!showWindow && pset.sversion >= 80400) + if (!showWindow) { if (have_where) appendPQExpBufferStr(&buf, " AND "); @@ -727,6 +606,7 @@ describeTypes(const char *pattern, bool verbose, bool showSystem) gettext_noop("Schema"), gettext_noop("Name")); if (verbose) + { appendPQExpBuffer(&buf, " t.typname AS \"%s\",\n" " CASE WHEN t.typrelid != 0\n" @@ -734,39 +614,21 @@ describeTypes(const char *pattern, bool verbose, bool showSystem) " WHEN t.typlen < 0\n" " THEN CAST('var' AS pg_catalog.text)\n" " ELSE CAST(t.typlen AS pg_catalog.text)\n" - " END AS \"%s\",\n", - gettext_noop("Internal name"), - gettext_noop("Size")); - if (verbose && pset.sversion >= 80300) - { - appendPQExpBufferStr(&buf, - " pg_catalog.array_to_string(\n" - " ARRAY(\n" - " SELECT e.enumlabel\n" - " FROM pg_catalog.pg_enum e\n" - " WHERE e.enumtypid = t.oid\n"); - - if (pset.sversion >= 90100) - appendPQExpBufferStr(&buf, - " ORDER BY e.enumsortorder\n"); - else - appendPQExpBufferStr(&buf, - " ORDER BY e.oid\n"); - - appendPQExpBuffer(&buf, + " END AS \"%s\",\n" + " pg_catalog.array_to_string(\n" + " ARRAY(\n" + " SELECT e.enumlabel\n" + " FROM pg_catalog.pg_enum e\n" + " WHERE e.enumtypid = t.oid\n" + " ORDER BY e.enumsortorder\n" " ),\n" " E'\\n'\n" - " ) AS \"%s\",\n", - gettext_noop("Elements")); - } - if (verbose) - { - appendPQExpBuffer(&buf, + " ) AS \"%s\",\n" " pg_catalog.pg_get_userbyid(t.typowner) AS \"%s\",\n", + gettext_noop("Internal name"), + gettext_noop("Size"), + gettext_noop("Elements"), gettext_noop("Owner")); - } - if (verbose && pset.sversion >= 90200) - { printACLColumn(&buf, "t.typacl"); appendPQExpBufferStr(&buf, ",\n "); } @@ -788,16 +650,10 @@ describeTypes(const char *pattern, bool verbose, bool showSystem) "WHERE c.oid = t.typrelid))\n"); /* - * do not include array types unless the pattern contains [] (before 8.3 - * we have to use the assumption that their names start with underscore) + * do not include array types unless the pattern contains [] */ if (pattern == NULL || strstr(pattern, "[]") == NULL) - { - if (pset.sversion >= 80300) - appendPQExpBufferStr(&buf, " AND NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type el WHERE el.oid = t.typelem AND el.typarray = t.oid)\n"); - else - appendPQExpBufferStr(&buf, " AND t.typname !~ '^_'\n"); - } + appendPQExpBufferStr(&buf, " AND NOT EXISTS(SELECT 1 FROM pg_catalog.pg_type el WHERE el.oid = t.typelem AND el.typarray = t.oid)\n"); if (!showSystem && !pattern) appendPQExpBufferStr(&buf, " AND n.nspname <> 'pg_catalog'\n" @@ -902,12 +758,11 @@ describeOperators(const char *oper_pattern, * operators, preferring to let the comment on the underlying function * suffice. The coalesce() on the obj_description() calls below supports * this convention by providing a fallback lookup of a comment on the - * operator's function. As of 9.1 there is a policy that every built-in + * operator's function. Since 9.1 there is a policy that every built-in * operator should have a comment; so the coalesce() is no longer * necessary so far as built-in operators are concerned. We keep it - * anyway, for now, because (1) third-party modules may still be following - * the old convention, and (2) we'd need to do it anyway when talking to a - * pre-9.1 server. + * anyway, for now, because third-party modules may still be following the + * old convention. * * The support for postfix operators in this query is dead code as of * Postgres 14, but we need to keep it for as long as we support talking @@ -1033,36 +888,30 @@ listAllDbs(const char *pattern, bool verbose) printfPQExpBuffer(&buf, "SELECT d.datname as \"%s\",\n" " pg_catalog.pg_get_userbyid(d.datdba) as \"%s\",\n" - " pg_catalog.pg_encoding_to_char(d.encoding) as \"%s\",\n", + " pg_catalog.pg_encoding_to_char(d.encoding) as \"%s\",\n" + " d.datcollate as \"%s\",\n" + " d.datctype as \"%s\",\n", gettext_noop("Name"), gettext_noop("Owner"), - gettext_noop("Encoding")); - if (pset.sversion >= 80400) - appendPQExpBuffer(&buf, - " d.datcollate as \"%s\",\n" - " d.datctype as \"%s\",\n", - gettext_noop("Collate"), - gettext_noop("Ctype")); + gettext_noop("Encoding"), + gettext_noop("Collate"), + gettext_noop("Ctype")); appendPQExpBufferStr(&buf, " "); printACLColumn(&buf, "d.datacl"); - if (verbose && pset.sversion >= 80200) + if (verbose) appendPQExpBuffer(&buf, ",\n CASE WHEN pg_catalog.has_database_privilege(d.datname, 'CONNECT')\n" " THEN pg_catalog.pg_size_pretty(pg_catalog.pg_database_size(d.datname))\n" " ELSE 'No Access'\n" - " END as \"%s\"", - gettext_noop("Size")); - if (verbose && pset.sversion >= 80000) - appendPQExpBuffer(&buf, - ",\n t.spcname as \"%s\"", - gettext_noop("Tablespace")); - if (verbose && pset.sversion >= 80200) - appendPQExpBuffer(&buf, + " END as \"%s\"" + ",\n t.spcname as \"%s\"" ",\n pg_catalog.shobj_description(d.oid, 'pg_database') as \"%s\"", + gettext_noop("Size"), + gettext_noop("Tablespace"), gettext_noop("Description")); appendPQExpBufferStr(&buf, "\nFROM pg_catalog.pg_database d\n"); - if (verbose && pset.sversion >= 80000) + if (verbose) appendPQExpBufferStr(&buf, " JOIN pg_catalog.pg_tablespace t on d.dattablespace = t.oid\n"); @@ -1128,14 +977,13 @@ permissionsList(const char *pattern) printACLColumn(&buf, "c.relacl"); - if (pset.sversion >= 80400) - appendPQExpBuffer(&buf, - ",\n pg_catalog.array_to_string(ARRAY(\n" - " SELECT attname || E':\\n ' || pg_catalog.array_to_string(attacl, E'\\n ')\n" - " FROM pg_catalog.pg_attribute a\n" - " WHERE attrelid = c.oid AND NOT attisdropped AND attacl IS NOT NULL\n" - " ), E'\\n') AS \"%s\"", - gettext_noop("Column privileges")); + appendPQExpBuffer(&buf, + ",\n pg_catalog.array_to_string(ARRAY(\n" + " SELECT attname || E':\\n ' || pg_catalog.array_to_string(attacl, E'\\n ')\n" + " FROM pg_catalog.pg_attribute a\n" + " WHERE attrelid = c.oid AND NOT attisdropped AND attacl IS NOT NULL\n" + " ), E'\\n') AS \"%s\"", + gettext_noop("Column privileges")); if (pset.sversion >= 90500 && pset.sversion < 100000) appendPQExpBuffer(&buf, @@ -1259,16 +1107,6 @@ listDefaultACLs(const char *pattern) printQueryOpt myopt = pset.popt; static const bool translate_columns[] = {false, false, true, false}; - if (pset.sversion < 90000) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support altering default privileges.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, @@ -1397,63 +1235,49 @@ objectDescription(const char *pattern, bool showSystem) false, "n.nspname", "pgc.conname", NULL, "pg_catalog.pg_type_is_visible(t.oid)"); + /* Operator class descriptions */ + appendPQExpBuffer(&buf, + "UNION ALL\n" + " SELECT o.oid as oid, o.tableoid as tableoid,\n" + " n.nspname as nspname,\n" + " CAST(o.opcname AS pg_catalog.text) as name,\n" + " CAST('%s' AS pg_catalog.text) as object\n" + " FROM pg_catalog.pg_opclass o\n" + " JOIN pg_catalog.pg_am am ON " + "o.opcmethod = am.oid\n" + " JOIN pg_catalog.pg_namespace n ON " + "n.oid = o.opcnamespace\n", + gettext_noop("operator class")); - /* - * pg_opclass.opcmethod only available in 8.3+ - */ - if (pset.sversion >= 80300) - { - /* Operator class descriptions */ - appendPQExpBuffer(&buf, - "UNION ALL\n" - " SELECT o.oid as oid, o.tableoid as tableoid,\n" - " n.nspname as nspname,\n" - " CAST(o.opcname AS pg_catalog.text) as name,\n" - " CAST('%s' AS pg_catalog.text) as object\n" - " FROM pg_catalog.pg_opclass o\n" - " JOIN pg_catalog.pg_am am ON " - "o.opcmethod = am.oid\n" - " JOIN pg_catalog.pg_namespace n ON " - "n.oid = o.opcnamespace\n", - gettext_noop("operator class")); + if (!showSystem && !pattern) + appendPQExpBufferStr(&buf, " AND n.nspname <> 'pg_catalog'\n" + " AND n.nspname <> 'information_schema'\n"); - if (!showSystem && !pattern) - appendPQExpBufferStr(&buf, " AND n.nspname <> 'pg_catalog'\n" - " AND n.nspname <> 'information_schema'\n"); + processSQLNamePattern(pset.db, &buf, pattern, true, false, + "n.nspname", "o.opcname", NULL, + "pg_catalog.pg_opclass_is_visible(o.oid)"); - processSQLNamePattern(pset.db, &buf, pattern, true, false, - "n.nspname", "o.opcname", NULL, - "pg_catalog.pg_opclass_is_visible(o.oid)"); - } + /* Operator family descriptions */ + appendPQExpBuffer(&buf, + "UNION ALL\n" + " SELECT opf.oid as oid, opf.tableoid as tableoid,\n" + " n.nspname as nspname,\n" + " CAST(opf.opfname AS pg_catalog.text) AS name,\n" + " CAST('%s' AS pg_catalog.text) as object\n" + " FROM pg_catalog.pg_opfamily opf\n" + " JOIN pg_catalog.pg_am am " + "ON opf.opfmethod = am.oid\n" + " JOIN pg_catalog.pg_namespace n " + "ON opf.opfnamespace = n.oid\n", + gettext_noop("operator family")); - /* - * although operator family comments have been around since 8.3, - * pg_opfamily_is_visible is only available in 9.2+ - */ - if (pset.sversion >= 90200) - { - /* Operator family descriptions */ - appendPQExpBuffer(&buf, - "UNION ALL\n" - " SELECT opf.oid as oid, opf.tableoid as tableoid,\n" - " n.nspname as nspname,\n" - " CAST(opf.opfname AS pg_catalog.text) AS name,\n" - " CAST('%s' AS pg_catalog.text) as object\n" - " FROM pg_catalog.pg_opfamily opf\n" - " JOIN pg_catalog.pg_am am " - "ON opf.opfmethod = am.oid\n" - " JOIN pg_catalog.pg_namespace n " - "ON opf.opfnamespace = n.oid\n", - gettext_noop("operator family")); + if (!showSystem && !pattern) + appendPQExpBufferStr(&buf, " AND n.nspname <> 'pg_catalog'\n" + " AND n.nspname <> 'information_schema'\n"); - if (!showSystem && !pattern) - appendPQExpBufferStr(&buf, " AND n.nspname <> 'pg_catalog'\n" - " AND n.nspname <> 'information_schema'\n"); - - processSQLNamePattern(pset.db, &buf, pattern, true, false, - "n.nspname", "opf.opfname", NULL, - "pg_catalog.pg_opfamily_is_visible(opf.oid)"); - } + processSQLNamePattern(pset.db, &buf, pattern, true, false, + "n.nspname", "opf.opfname", NULL, + "pg_catalog.pg_opfamily_is_visible(opf.oid)"); /* Rule descriptions (ignore rules for views) */ appendPQExpBuffer(&buf, @@ -1737,7 +1561,7 @@ describeOneTableDetails(const char *schemaname, : "''"), oid); } - else if (pset.sversion >= 90100) + else { printfPQExpBuffer(&buf, "SELECT c.relchecks, c.relkind, c.relhasindex, c.relhasrules, " @@ -1754,66 +1578,6 @@ describeOneTableDetails(const char *schemaname, : "''"), oid); } - else if (pset.sversion >= 90000) - { - printfPQExpBuffer(&buf, - "SELECT c.relchecks, c.relkind, c.relhasindex, c.relhasrules, " - "c.relhastriggers, false, false, c.relhasoids, " - "false as relispartition, %s, c.reltablespace, " - "CASE WHEN c.reloftype = 0 THEN '' ELSE c.reloftype::pg_catalog.regtype::pg_catalog.text END\n" - "FROM pg_catalog.pg_class c\n " - "LEFT JOIN pg_catalog.pg_class tc ON (c.reltoastrelid = tc.oid)\n" - "WHERE c.oid = '%s';", - (verbose ? - "pg_catalog.array_to_string(c.reloptions || " - "array(select 'toast.' || x from pg_catalog.unnest(tc.reloptions) x), ', ')\n" - : "''"), - oid); - } - else if (pset.sversion >= 80400) - { - printfPQExpBuffer(&buf, - "SELECT c.relchecks, c.relkind, c.relhasindex, c.relhasrules, " - "c.relhastriggers, false, false, c.relhasoids, " - "false as relispartition, %s, c.reltablespace\n" - "FROM pg_catalog.pg_class c\n " - "LEFT JOIN pg_catalog.pg_class tc ON (c.reltoastrelid = tc.oid)\n" - "WHERE c.oid = '%s';", - (verbose ? - "pg_catalog.array_to_string(c.reloptions || " - "array(select 'toast.' || x from pg_catalog.unnest(tc.reloptions) x), ', ')\n" - : "''"), - oid); - } - else if (pset.sversion >= 80200) - { - printfPQExpBuffer(&buf, - "SELECT relchecks, relkind, relhasindex, relhasrules, " - "reltriggers <> 0, false, false, relhasoids, " - "false as relispartition, %s, reltablespace\n" - "FROM pg_catalog.pg_class WHERE oid = '%s';", - (verbose ? - "pg_catalog.array_to_string(reloptions, E', ')" : "''"), - oid); - } - else if (pset.sversion >= 80000) - { - printfPQExpBuffer(&buf, - "SELECT relchecks, relkind, relhasindex, relhasrules, " - "reltriggers <> 0, false, false, relhasoids, " - "false as relispartition, '', reltablespace\n" - "FROM pg_catalog.pg_class WHERE oid = '%s';", - oid); - } - else - { - printfPQExpBuffer(&buf, - "SELECT relchecks, relkind, relhasindex, relhasrules, " - "reltriggers <> 0, false, false, relhasoids, " - "false as relispartition, '', ''\n" - "FROM pg_catalog.pg_class WHERE oid = '%s';", - oid); - } res = PSQLexec(buf.data); if (!res) @@ -1836,15 +1600,11 @@ describeOneTableDetails(const char *schemaname, tableinfo.forcerowsecurity = strcmp(PQgetvalue(res, 0, 6), "t") == 0; tableinfo.hasoids = strcmp(PQgetvalue(res, 0, 7), "t") == 0; tableinfo.ispartition = strcmp(PQgetvalue(res, 0, 8), "t") == 0; - tableinfo.reloptions = (pset.sversion >= 80200) ? - pg_strdup(PQgetvalue(res, 0, 9)) : NULL; - tableinfo.tablespace = (pset.sversion >= 80000) ? - atooid(PQgetvalue(res, 0, 10)) : 0; - tableinfo.reloftype = (pset.sversion >= 90000 && - strcmp(PQgetvalue(res, 0, 11), "") != 0) ? + tableinfo.reloptions = pg_strdup(PQgetvalue(res, 0, 9)); + tableinfo.tablespace = atooid(PQgetvalue(res, 0, 10)); + tableinfo.reloftype = (strcmp(PQgetvalue(res, 0, 11), "") != 0) ? pg_strdup(PQgetvalue(res, 0, 11)) : NULL; - tableinfo.relpersistence = (pset.sversion >= 90100) ? - *(PQgetvalue(res, 0, 12)) : 0; + tableinfo.relpersistence = *(PQgetvalue(res, 0, 12)); tableinfo.relreplident = (pset.sversion >= 90400) ? *(PQgetvalue(res, 0, 13)) : 'd'; if (pset.sversion >= 120000) @@ -2010,11 +1770,8 @@ describeOneTableDetails(const char *schemaname, ",\n a.attnotnull"); attrdef_col = cols++; attnotnull_col = cols++; - if (pset.sversion >= 90100) - appendPQExpBufferStr(&buf, ",\n (SELECT c.collname FROM pg_catalog.pg_collation c, pg_catalog.pg_type t\n" - " WHERE c.oid = a.attcollation AND t.oid = a.atttypid AND a.attcollation <> t.typcollation) AS attcollation"); - else - appendPQExpBufferStr(&buf, ",\n NULL AS attcollation"); + appendPQExpBufferStr(&buf, ",\n (SELECT c.collname FROM pg_catalog.pg_collation c, pg_catalog.pg_type t\n" + " WHERE c.oid = a.attcollation AND t.oid = a.atttypid AND a.attcollation <> t.typcollation) AS attcollation"); attcoll_col = cols++; if (pset.sversion >= 100000) appendPQExpBufferStr(&buf, ",\n a.attidentity"); @@ -2041,8 +1798,8 @@ describeOneTableDetails(const char *schemaname, appendPQExpBufferStr(&buf, ",\n pg_catalog.pg_get_indexdef(a.attrelid, a.attnum, TRUE) AS indexdef"); indexdef_col = cols++; } - /* FDW options for foreign table column, only for 9.2 or later */ - if (tableinfo.relkind == RELKIND_FOREIGN_TABLE && pset.sversion >= 90200) + /* FDW options for foreign table column */ + if (tableinfo.relkind == RELKIND_FOREIGN_TABLE) { appendPQExpBufferStr(&buf, ",\n CASE WHEN attfdwoptions IS NULL THEN '' ELSE " " '(' || pg_catalog.array_to_string(ARRAY(SELECT pg_catalog.quote_ident(option_name) || ' ' || pg_catalog.quote_literal(option_value) FROM " @@ -2141,11 +1898,6 @@ describeOneTableDetails(const char *schemaname, printfPQExpBuffer(&title, _("Partitioned index \"%s.%s\""), schemaname, relationname); break; - case 's': - /* not used as of 8.2, but keep it for backwards compatibility */ - printfPQExpBuffer(&title, _("Special relation \"%s.%s\""), - schemaname, relationname); - break; case RELKIND_TOASTVALUE: printfPQExpBuffer(&title, _("TOAST table \"%s.%s\""), schemaname, relationname); @@ -2409,28 +2161,20 @@ describeOneTableDetails(const char *schemaname, PGresult *result; printfPQExpBuffer(&buf, - "SELECT i.indisunique, i.indisprimary, i.indisclustered, "); - if (pset.sversion >= 80200) - appendPQExpBufferStr(&buf, "i.indisvalid,\n"); - else - appendPQExpBufferStr(&buf, "true AS indisvalid,\n"); - if (pset.sversion >= 90000) - appendPQExpBufferStr(&buf, - " (NOT i.indimmediate) AND " - "EXISTS (SELECT 1 FROM pg_catalog.pg_constraint " - "WHERE conrelid = i.indrelid AND " - "conindid = i.indexrelid AND " - "contype IN ('p','u','x') AND " - "condeferrable) AS condeferrable,\n" - " (NOT i.indimmediate) AND " - "EXISTS (SELECT 1 FROM pg_catalog.pg_constraint " - "WHERE conrelid = i.indrelid AND " - "conindid = i.indexrelid AND " - "contype IN ('p','u','x') AND " - "condeferred) AS condeferred,\n"); - else - appendPQExpBufferStr(&buf, - " false AS condeferrable, false AS condeferred,\n"); + "SELECT i.indisunique, i.indisprimary, i.indisclustered, " + "i.indisvalid,\n" + " (NOT i.indimmediate) AND " + "EXISTS (SELECT 1 FROM pg_catalog.pg_constraint " + "WHERE conrelid = i.indrelid AND " + "conindid = i.indexrelid AND " + "contype IN ('p','u','x') AND " + "condeferrable) AS condeferrable,\n" + " (NOT i.indimmediate) AND " + "EXISTS (SELECT 1 FROM pg_catalog.pg_constraint " + "WHERE conrelid = i.indrelid AND " + "conindid = i.indexrelid AND " + "contype IN ('p','u','x') AND " + "condeferred) AS condeferred,\n"); if (pset.sversion >= 90400) appendPQExpBufferStr(&buf, "i.indisreplident,\n"); @@ -2523,32 +2267,19 @@ describeOneTableDetails(const char *schemaname, if (tableinfo.hasindex) { printfPQExpBuffer(&buf, - "SELECT c2.relname, i.indisprimary, i.indisunique, i.indisclustered, "); - if (pset.sversion >= 80200) - appendPQExpBufferStr(&buf, "i.indisvalid, "); - else - appendPQExpBufferStr(&buf, "true as indisvalid, "); - appendPQExpBufferStr(&buf, "pg_catalog.pg_get_indexdef(i.indexrelid, 0, true),\n "); - if (pset.sversion >= 90000) - appendPQExpBufferStr(&buf, - "pg_catalog.pg_get_constraintdef(con.oid, true), " - "contype, condeferrable, condeferred"); - else - appendPQExpBufferStr(&buf, - "null AS constraintdef, null AS contype, " - "false AS condeferrable, false AS condeferred"); + "SELECT c2.relname, i.indisprimary, i.indisunique, " + "i.indisclustered, i.indisvalid, " + "pg_catalog.pg_get_indexdef(i.indexrelid, 0, true),\n " + "pg_catalog.pg_get_constraintdef(con.oid, true), " + "contype, condeferrable, condeferred"); if (pset.sversion >= 90400) appendPQExpBufferStr(&buf, ", i.indisreplident"); else appendPQExpBufferStr(&buf, ", false AS indisreplident"); - if (pset.sversion >= 80000) - appendPQExpBufferStr(&buf, ", c2.reltablespace"); - appendPQExpBufferStr(&buf, - "\nFROM pg_catalog.pg_class c, pg_catalog.pg_class c2, pg_catalog.pg_index i\n"); - if (pset.sversion >= 90000) - appendPQExpBufferStr(&buf, - " LEFT JOIN pg_catalog.pg_constraint con ON (conrelid = i.indrelid AND conindid = i.indexrelid AND contype IN ('p','u','x'))\n"); + appendPQExpBufferStr(&buf, ", c2.reltablespace"); appendPQExpBuffer(&buf, + "\nFROM pg_catalog.pg_class c, pg_catalog.pg_class c2, pg_catalog.pg_index i\n" + " LEFT JOIN pg_catalog.pg_constraint con ON (conrelid = i.indrelid AND conindid = i.indexrelid AND contype IN ('p','u','x'))\n" "WHERE c.oid = '%s' AND c.oid = i.indrelid AND i.indexrelid = c2.oid\n" "ORDER BY i.indisprimary DESC, c2.relname;", oid); @@ -2617,10 +2348,9 @@ describeOneTableDetails(const char *schemaname, printTableAddFooter(&cont, buf.data); /* Print tablespace of the index on the same line */ - if (pset.sversion >= 80000) - add_tablespace_footer(&cont, RELKIND_INDEX, - atooid(PQgetvalue(result, i, 11)), - false); + add_tablespace_footer(&cont, RELKIND_INDEX, + atooid(PQgetvalue(result, i, 11)), + false); } } PQclear(result); @@ -3051,24 +2781,12 @@ describeOneTableDetails(const char *schemaname, /* print rules */ if (tableinfo.hasrules && tableinfo.relkind != RELKIND_MATVIEW) { - if (pset.sversion >= 80300) - { - printfPQExpBuffer(&buf, - "SELECT r.rulename, trim(trailing ';' from pg_catalog.pg_get_ruledef(r.oid, true)), " - "ev_enabled\n" - "FROM pg_catalog.pg_rewrite r\n" - "WHERE r.ev_class = '%s' ORDER BY 1;", - oid); - } - else - { - printfPQExpBuffer(&buf, - "SELECT r.rulename, trim(trailing ';' from pg_catalog.pg_get_ruledef(r.oid, true)), " - "'O' AS ev_enabled\n" - "FROM pg_catalog.pg_rewrite r\n" - "WHERE r.ev_class = '%s' ORDER BY 1;", - oid); - } + printfPQExpBuffer(&buf, + "SELECT r.rulename, trim(trailing ';' from pg_catalog.pg_get_ruledef(r.oid, true)), " + "ev_enabled\n" + "FROM pg_catalog.pg_rewrite r\n" + "WHERE r.ev_class = '%s' ORDER BY 1;", + oid); result = PSQLexec(buf.data); if (!result) goto error_return; @@ -3271,15 +2989,10 @@ describeOneTableDetails(const char *schemaname, printfPQExpBuffer(&buf, "SELECT t.tgname, " - "pg_catalog.pg_get_triggerdef(t.oid%s), " - "t.tgenabled, %s, %s\n" + "pg_catalog.pg_get_triggerdef(t.oid, true), " + "t.tgenabled, t.tgisinternal, %s\n" "FROM pg_catalog.pg_trigger t\n" "WHERE t.tgrelid = '%s' AND ", - (pset.sversion >= 90000 ? ", true" : ""), - (pset.sversion >= 90000 ? "t.tgisinternal" : - pset.sversion >= 80300 ? - "t.tgconstraint <> 0 AS tgisinternal" : - "false AS tgisinternal"), (pset.sversion >= 130000 ? "(SELECT (NULLIF(a.relid, t.tgrelid))::pg_catalog.regclass" " FROM pg_catalog.pg_trigger AS u, " @@ -3292,18 +3005,9 @@ describeOneTableDetails(const char *schemaname, appendPQExpBufferStr(&buf, "(NOT t.tgisinternal OR (t.tgisinternal AND t.tgenabled = 'D') \n" " OR EXISTS (SELECT 1 FROM pg_catalog.pg_depend WHERE objid = t.oid \n" " AND refclassid = 'pg_catalog.pg_trigger'::pg_catalog.regclass))"); - else if (pset.sversion >= 90000) + else /* display/warn about disabled internal triggers */ appendPQExpBufferStr(&buf, "(NOT t.tgisinternal OR (t.tgisinternal AND t.tgenabled = 'D'))"); - else if (pset.sversion >= 80300) - appendPQExpBufferStr(&buf, "(t.tgconstraint = 0 OR (t.tgconstraint <> 0 AND t.tgenabled = 'D'))"); - else - appendPQExpBufferStr(&buf, - "(NOT tgisconstraint " - " OR NOT EXISTS" - " (SELECT 1 FROM pg_catalog.pg_depend d " - " JOIN pg_catalog.pg_constraint c ON (d.refclassid = c.tableoid AND d.refobjid = c.oid) " - " WHERE d.classid = t.tableoid AND d.objid = t.oid AND d.deptype = 'i' AND c.contype = 'f'))"); appendPQExpBufferStr(&buf, "\nORDER BY 1;"); result = PSQLexec(buf.data); @@ -3376,10 +3080,7 @@ describeOneTableDetails(const char *schemaname, printfPQExpBuffer(&buf, _("Triggers:")); break; case 1: - if (pset.sversion >= 80300) - printfPQExpBuffer(&buf, _("Disabled user triggers:")); - else - printfPQExpBuffer(&buf, _("Disabled triggers:")); + printfPQExpBuffer(&buf, _("Disabled user triggers:")); break; case 2: printfPQExpBuffer(&buf, _("Disabled internal triggers:")); @@ -3532,21 +3233,13 @@ describeOneTableDetails(const char *schemaname, "ORDER BY pg_catalog.pg_get_expr(c.relpartbound, c.oid) = 'DEFAULT'," " c.oid::pg_catalog.regclass::pg_catalog.text;", oid); - else if (pset.sversion >= 80300) - printfPQExpBuffer(&buf, - "SELECT c.oid::pg_catalog.regclass, c.relkind," - " false AS inhdetachpending, NULL\n" - "FROM pg_catalog.pg_class c, pg_catalog.pg_inherits i\n" - "WHERE c.oid = i.inhrelid AND i.inhparent = '%s'\n" - "ORDER BY c.oid::pg_catalog.regclass::pg_catalog.text;", - oid); else printfPQExpBuffer(&buf, "SELECT c.oid::pg_catalog.regclass, c.relkind," " false AS inhdetachpending, NULL\n" "FROM pg_catalog.pg_class c, pg_catalog.pg_inherits i\n" "WHERE c.oid = i.inhrelid AND i.inhparent = '%s'\n" - "ORDER BY c.relname;", + "ORDER BY c.oid::pg_catalog.regclass::pg_catalog.text;", oid); result = PSQLexec(buf.data); @@ -3705,8 +3398,7 @@ add_tablespace_footer(printTableContent *const cont, char relkind, { /* * We ignore the database default tablespace so that users not using - * tablespaces don't need to know about them. This case also covers - * pre-8.0 servers, for which tablespace will always be 0. + * tablespaces don't need to know about them. */ if (tablespace != 0) { @@ -3775,56 +3467,35 @@ describeRoles(const char *pattern, bool verbose, bool showSystem) initPQExpBuffer(&buf); - if (pset.sversion >= 80100) + printfPQExpBuffer(&buf, + "SELECT r.rolname, r.rolsuper, r.rolinherit,\n" + " r.rolcreaterole, r.rolcreatedb, r.rolcanlogin,\n" + " r.rolconnlimit, r.rolvaliduntil,\n" + " ARRAY(SELECT b.rolname\n" + " FROM pg_catalog.pg_auth_members m\n" + " JOIN pg_catalog.pg_roles b ON (m.roleid = b.oid)\n" + " WHERE m.member = r.oid) as memberof"); + + if (verbose) { - printfPQExpBuffer(&buf, - "SELECT r.rolname, r.rolsuper, r.rolinherit,\n" - " r.rolcreaterole, r.rolcreatedb, r.rolcanlogin,\n" - " r.rolconnlimit, r.rolvaliduntil,\n" - " ARRAY(SELECT b.rolname\n" - " FROM pg_catalog.pg_auth_members m\n" - " JOIN pg_catalog.pg_roles b ON (m.roleid = b.oid)\n" - " WHERE m.member = r.oid) as memberof"); - - if (verbose && pset.sversion >= 80200) - { - appendPQExpBufferStr(&buf, "\n, pg_catalog.shobj_description(r.oid, 'pg_authid') AS description"); - ncols++; - } - if (pset.sversion >= 90100) - { - appendPQExpBufferStr(&buf, "\n, r.rolreplication"); - } - - if (pset.sversion >= 90500) - { - appendPQExpBufferStr(&buf, "\n, r.rolbypassrls"); - } - - appendPQExpBufferStr(&buf, "\nFROM pg_catalog.pg_roles r\n"); - - if (!showSystem && !pattern) - appendPQExpBufferStr(&buf, "WHERE r.rolname !~ '^pg_'\n"); - - processSQLNamePattern(pset.db, &buf, pattern, false, false, - NULL, "r.rolname", NULL, NULL); + appendPQExpBufferStr(&buf, "\n, pg_catalog.shobj_description(r.oid, 'pg_authid') AS description"); + ncols++; } - else + appendPQExpBufferStr(&buf, "\n, r.rolreplication"); + + if (pset.sversion >= 90500) { - printfPQExpBuffer(&buf, - "SELECT u.usename AS rolname,\n" - " u.usesuper AS rolsuper,\n" - " true AS rolinherit, false AS rolcreaterole,\n" - " u.usecreatedb AS rolcreatedb, true AS rolcanlogin,\n" - " -1 AS rolconnlimit," - " u.valuntil as rolvaliduntil,\n" - " ARRAY(SELECT g.groname FROM pg_catalog.pg_group g WHERE u.usesysid = ANY(g.grolist)) as memberof" - "\nFROM pg_catalog.pg_user u\n"); - - processSQLNamePattern(pset.db, &buf, pattern, false, false, - NULL, "u.usename", NULL, NULL); + appendPQExpBufferStr(&buf, "\n, r.rolbypassrls"); } + appendPQExpBufferStr(&buf, "\nFROM pg_catalog.pg_roles r\n"); + + if (!showSystem && !pattern) + appendPQExpBufferStr(&buf, "WHERE r.rolname !~ '^pg_'\n"); + + processSQLNamePattern(pset.db, &buf, pattern, false, false, + NULL, "r.rolname", NULL, NULL); + appendPQExpBufferStr(&buf, "ORDER BY 1;"); res = PSQLexec(buf.data); @@ -3841,7 +3512,7 @@ describeRoles(const char *pattern, bool verbose, bool showSystem) /* ignores implicit memberships from superuser & pg_database_owner */ printTableAddHeader(&cont, gettext_noop("Member of"), true, align); - if (verbose && pset.sversion >= 80200) + if (verbose) printTableAddHeader(&cont, gettext_noop("Description"), true, align); for (i = 0; i < nrows; i++) @@ -3864,9 +3535,8 @@ describeRoles(const char *pattern, bool verbose, bool showSystem) if (strcmp(PQgetvalue(res, i, 5), "t") != 0) add_role_attribute(&buf, _("Cannot login")); - if (pset.sversion >= 90100) - if (strcmp(PQgetvalue(res, i, (verbose ? 10 : 9)), "t") == 0) - add_role_attribute(&buf, _("Replication")); + if (strcmp(PQgetvalue(res, i, (verbose ? 10 : 9)), "t") == 0) + add_role_attribute(&buf, _("Replication")); if (pset.sversion >= 90500) if (strcmp(PQgetvalue(res, i, (verbose ? 11 : 10)), "t") == 0) @@ -3901,7 +3571,7 @@ describeRoles(const char *pattern, bool verbose, bool showSystem) printTableAddCell(&cont, PQgetvalue(res, i, 8), false, false); - if (verbose && pset.sversion >= 80200) + if (verbose) printTableAddCell(&cont, PQgetvalue(res, i, 9), false, false); } termPQExpBuffer(&buf); @@ -3937,16 +3607,6 @@ listDbRoleSettings(const char *pattern, const char *pattern2) printQueryOpt myopt = pset.popt; bool havewhere; - if (pset.sversion < 90000) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support per-database role settings.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT rolname AS \"%s\", datname AS \"%s\",\n" @@ -4035,10 +3695,6 @@ listTables(const char *tabtypes, const char *pattern, bool verbose, bool showSys initPQExpBuffer(&buf); - /* - * Note: as of Pg 8.2, we no longer use relkind 's' (special), but we keep - * it here for backwards compatibility. - */ printfPQExpBuffer(&buf, "SELECT n.nspname as \"%s\",\n" " c.relname as \"%s\",\n" @@ -4048,7 +3704,6 @@ listTables(const char *tabtypes, const char *pattern, bool verbose, bool showSys " WHEN " CppAsString2(RELKIND_MATVIEW) " THEN '%s'" " WHEN " CppAsString2(RELKIND_INDEX) " THEN '%s'" " WHEN " CppAsString2(RELKIND_SEQUENCE) " THEN '%s'" - " WHEN 's' THEN '%s'" " WHEN " CppAsString2(RELKIND_TOASTVALUE) " THEN '%s'" " WHEN " CppAsString2(RELKIND_FOREIGN_TABLE) " THEN '%s'" " WHEN " CppAsString2(RELKIND_PARTITIONED_TABLE) " THEN '%s'" @@ -4062,7 +3717,6 @@ listTables(const char *tabtypes, const char *pattern, bool verbose, bool showSys gettext_noop("materialized view"), gettext_noop("index"), gettext_noop("sequence"), - gettext_noop("special"), gettext_noop("TOAST table"), gettext_noop("foreign table"), gettext_noop("partitioned table"), @@ -4082,20 +3736,15 @@ listTables(const char *tabtypes, const char *pattern, bool verbose, bool showSys if (verbose) { /* - * Show whether a relation is permanent, temporary, or unlogged. Like - * describeOneTableDetails(), we consider that persistence emerged in - * v9.1, even though related concepts existed before. + * Show whether a relation is permanent, temporary, or unlogged. */ - if (pset.sversion >= 90100) - { - appendPQExpBuffer(&buf, - ",\n CASE c.relpersistence WHEN 'p' THEN '%s' WHEN 't' THEN '%s' WHEN 'u' THEN '%s' END as \"%s\"", - gettext_noop("permanent"), - gettext_noop("temporary"), - gettext_noop("unlogged"), - gettext_noop("Persistence")); - translate_columns[cols_so_far] = true; - } + appendPQExpBuffer(&buf, + ",\n CASE c.relpersistence WHEN 'p' THEN '%s' WHEN 't' THEN '%s' WHEN 'u' THEN '%s' END as \"%s\"", + gettext_noop("permanent"), + gettext_noop("temporary"), + gettext_noop("unlogged"), + gettext_noop("Persistence")); + translate_columns[cols_so_far] = true; /* * We don't bother to count cols_so_far below here, as there's no need @@ -4112,21 +3761,10 @@ listTables(const char *tabtypes, const char *pattern, bool verbose, bool showSys ",\n am.amname as \"%s\"", gettext_noop("Access method")); - /* - * As of PostgreSQL 9.0, use pg_table_size() to show a more accurate - * size of a table, including FSM, VM and TOAST tables. - */ - if (pset.sversion >= 90000) - appendPQExpBuffer(&buf, - ",\n pg_catalog.pg_size_pretty(pg_catalog.pg_table_size(c.oid)) as \"%s\"", - gettext_noop("Size")); - else if (pset.sversion >= 80100) - appendPQExpBuffer(&buf, - ",\n pg_catalog.pg_size_pretty(pg_catalog.pg_relation_size(c.oid)) as \"%s\"", - gettext_noop("Size")); - appendPQExpBuffer(&buf, + ",\n pg_catalog.pg_size_pretty(pg_catalog.pg_table_size(c.oid)) as \"%s\"" ",\n pg_catalog.obj_description(c.oid, 'pg_class') as \"%s\"", + gettext_noop("Size"), gettext_noop("Description")); } @@ -4435,15 +4073,11 @@ listLanguages(const char *pattern, bool verbose, bool showSystem) initPQExpBuffer(&buf); printfPQExpBuffer(&buf, - "SELECT l.lanname AS \"%s\",\n", - gettext_noop("Name")); - if (pset.sversion >= 80300) - appendPQExpBuffer(&buf, - " pg_catalog.pg_get_userbyid(l.lanowner) as \"%s\",\n", - gettext_noop("Owner")); - - appendPQExpBuffer(&buf, + "SELECT l.lanname AS \"%s\",\n" + " pg_catalog.pg_get_userbyid(l.lanowner) as \"%s\",\n" " l.lanpltrusted AS \"%s\"", + gettext_noop("Name"), + gettext_noop("Owner"), gettext_noop("Trusted")); if (verbose) @@ -4451,13 +4085,12 @@ listLanguages(const char *pattern, bool verbose, bool showSystem) appendPQExpBuffer(&buf, ",\n NOT l.lanispl AS \"%s\",\n" " l.lanplcallfoid::pg_catalog.regprocedure AS \"%s\",\n" - " l.lanvalidator::pg_catalog.regprocedure AS \"%s\",\n ", + " l.lanvalidator::pg_catalog.regprocedure AS \"%s\",\n " + "l.laninline::pg_catalog.regprocedure AS \"%s\",\n ", gettext_noop("Internal language"), gettext_noop("Call handler"), - gettext_noop("Validator")); - if (pset.sversion >= 90000) - appendPQExpBuffer(&buf, "l.laninline::pg_catalog.regprocedure AS \"%s\",\n ", - gettext_noop("Inline handler")); + gettext_noop("Validator"), + gettext_noop("Inline handler")); printACLColumn(&buf, "l.lanacl"); } @@ -4512,33 +4145,26 @@ listDomains(const char *pattern, bool verbose, bool showSystem) printfPQExpBuffer(&buf, "SELECT n.nspname as \"%s\",\n" " t.typname as \"%s\",\n" - " pg_catalog.format_type(t.typbasetype, t.typtypmod) as \"%s\",\n", - gettext_noop("Schema"), - gettext_noop("Name"), - gettext_noop("Type")); - - if (pset.sversion >= 90100) - appendPQExpBuffer(&buf, - " (SELECT c.collname FROM pg_catalog.pg_collation c, pg_catalog.pg_type bt\n" - " WHERE c.oid = t.typcollation AND bt.oid = t.typbasetype AND t.typcollation <> bt.typcollation) as \"%s\",\n", - gettext_noop("Collation")); - appendPQExpBuffer(&buf, + " pg_catalog.format_type(t.typbasetype, t.typtypmod) as \"%s\",\n" + " (SELECT c.collname FROM pg_catalog.pg_collation c, pg_catalog.pg_type bt\n" + " WHERE c.oid = t.typcollation AND bt.oid = t.typbasetype AND t.typcollation <> bt.typcollation) as \"%s\",\n" " CASE WHEN t.typnotnull THEN 'not null' END as \"%s\",\n" " t.typdefault as \"%s\",\n" " pg_catalog.array_to_string(ARRAY(\n" " SELECT pg_catalog.pg_get_constraintdef(r.oid, true) FROM pg_catalog.pg_constraint r WHERE t.oid = r.contypid\n" " ), ' ') as \"%s\"", + gettext_noop("Schema"), + gettext_noop("Name"), + gettext_noop("Type"), + gettext_noop("Collation"), gettext_noop("Nullable"), gettext_noop("Default"), gettext_noop("Check")); if (verbose) { - if (pset.sversion >= 90200) - { - appendPQExpBufferStr(&buf, ",\n "); - printACLColumn(&buf, "t.typacl"); - } + appendPQExpBufferStr(&buf, ",\n "); + printACLColumn(&buf, "t.typacl"); appendPQExpBuffer(&buf, ",\n d.description as \"%s\"", gettext_noop("Description")); @@ -4671,6 +4297,16 @@ listEventTriggers(const char *pattern, bool verbose) static const bool translate_columns[] = {false, false, false, true, false, false, false}; + if (pset.sversion < 90300) + { + char sverbuf[32]; + + pg_log_error("The server (version %s) does not support event triggers.", + formatPGVersionNumber(pset.sversion, false, + sverbuf, sizeof(sverbuf))); + return true; + } + initPQExpBuffer(&buf); printfPQExpBuffer(&buf, @@ -4841,21 +4477,14 @@ listCasts(const char *pattern, bool verbose) * because there's too much risk of gettext translating a function name * that happens to match some string in the PO database. */ - if (pset.sversion >= 80400) - appendPQExpBuffer(&buf, - " CASE WHEN c.castmethod = '%c' THEN '(binary coercible)'\n" - " WHEN c.castmethod = '%c' THEN '(with inout)'\n" - " ELSE p.proname\n" - " END AS \"%s\",\n", - COERCION_METHOD_BINARY, - COERCION_METHOD_INOUT, - gettext_noop("Function")); - else - appendPQExpBuffer(&buf, - " CASE WHEN c.castfunc = 0 THEN '(binary coercible)'\n" - " ELSE p.proname\n" - " END AS \"%s\",\n", - gettext_noop("Function")); + appendPQExpBuffer(&buf, + " CASE WHEN c.castmethod = '%c' THEN '(binary coercible)'\n" + " WHEN c.castmethod = '%c' THEN '(with inout)'\n" + " ELSE p.proname\n" + " END AS \"%s\",\n", + COERCION_METHOD_BINARY, + COERCION_METHOD_INOUT, + gettext_noop("Function")); appendPQExpBuffer(&buf, " CASE WHEN c.castcontext = '%c' THEN '%s'\n" @@ -4946,16 +4575,6 @@ listCollations(const char *pattern, bool verbose, bool showSystem) printQueryOpt myopt = pset.popt; static const bool translate_columns[] = {false, false, false, false, false, true, false}; - if (pset.sversion < 90100) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support collations.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, @@ -5166,16 +4785,6 @@ listTSParsers(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80300) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support full text search.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - if (verbose) return listTSParsersVerbose(pattern); @@ -5413,16 +5022,6 @@ listTSDictionaries(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80300) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support full text search.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, @@ -5484,16 +5083,6 @@ listTSTemplates(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80300) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support full text search.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); if (verbose) @@ -5555,16 +5144,6 @@ listTSConfigs(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80300) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support full text search.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - if (verbose) return listTSConfigsVerbose(pattern); @@ -5761,28 +5340,15 @@ listForeignDataWrappers(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80400) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support foreign-data wrappers.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT fdw.fdwname AS \"%s\",\n" - " pg_catalog.pg_get_userbyid(fdw.fdwowner) AS \"%s\",\n", - gettext_noop("Name"), - gettext_noop("Owner")); - if (pset.sversion >= 90100) - appendPQExpBuffer(&buf, - " fdw.fdwhandler::pg_catalog.regproc AS \"%s\",\n", - gettext_noop("Handler")); - appendPQExpBuffer(&buf, + " pg_catalog.pg_get_userbyid(fdw.fdwowner) AS \"%s\",\n" + " fdw.fdwhandler::pg_catalog.regproc AS \"%s\",\n" " fdw.fdwvalidator::pg_catalog.regproc AS \"%s\"", + gettext_noop("Name"), + gettext_noop("Owner"), + gettext_noop("Handler"), gettext_noop("Validator")); if (verbose) @@ -5795,18 +5361,15 @@ listForeignDataWrappers(const char *pattern, bool verbose) " pg_catalog.quote_ident(option_name) || ' ' || " " pg_catalog.quote_literal(option_value) FROM " " pg_catalog.pg_options_to_table(fdwoptions)), ', ') || ')' " - " END AS \"%s\"", - gettext_noop("FDW options")); - - if (pset.sversion >= 90100) - appendPQExpBuffer(&buf, - ",\n d.description AS \"%s\" ", - gettext_noop("Description")); + " END AS \"%s\"" + ",\n d.description AS \"%s\" ", + gettext_noop("FDW options"), + gettext_noop("Description")); } appendPQExpBufferStr(&buf, "\nFROM pg_catalog.pg_foreign_data_wrapper fdw\n"); - if (verbose && pset.sversion >= 90100) + if (verbose) appendPQExpBufferStr(&buf, "LEFT JOIN pg_catalog.pg_description d\n" " ON d.classoid = fdw.tableoid " @@ -5844,16 +5407,6 @@ listForeignServers(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80400) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support foreign servers.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT s.srvname AS \"%s\",\n" @@ -5926,16 +5479,6 @@ listUserMappings(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 80400) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support user mappings.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT um.srvname AS \"%s\",\n" @@ -5987,16 +5530,6 @@ listForeignTables(const char *pattern, bool verbose) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 90100) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support foreign tables.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT n.nspname AS \"%s\",\n" @@ -6065,16 +5598,6 @@ listExtensions(const char *pattern) PGresult *res; printQueryOpt myopt = pset.popt; - if (pset.sversion < 90100) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support extensions.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT e.extname AS \"%s\", " @@ -6122,16 +5645,6 @@ listExtensionContents(const char *pattern) PGresult *res; int i; - if (pset.sversion < 90100) - { - char sverbuf[32]; - - pg_log_error("The server (version %s) does not support extensions.", - formatPGVersionNumber(pset.sversion, false, - sverbuf, sizeof(sverbuf))); - return true; - } - initPQExpBuffer(&buf); printfPQExpBuffer(&buf, "SELECT e.extname, e.oid\n" @@ -6595,14 +6108,9 @@ describeSubscriptions(const char *pattern, bool verbose) static void printACLColumn(PQExpBuffer buf, const char *colname) { - if (pset.sversion >= 80100) - appendPQExpBuffer(buf, - "pg_catalog.array_to_string(%s, E'\\n') AS \"%s\"", - colname, gettext_noop("Access privileges")); - else - appendPQExpBuffer(buf, - "pg_catalog.array_to_string(%s, '\\n') AS \"%s\"", - colname, gettext_noop("Access privileges")); + appendPQExpBuffer(buf, + "pg_catalog.array_to_string(%s, E'\\n') AS \"%s\"", + colname, gettext_noop("Access privileges")); } /* diff --git a/src/bin/psql/large_obj.c b/src/bin/psql/large_obj.c index c15fcc08851..10e47c87ac9 100644 --- a/src/bin/psql/large_obj.c +++ b/src/bin/psql/large_obj.c @@ -277,28 +277,15 @@ do_lo_list(void) char buf[1024]; printQueryOpt myopt = pset.popt; - if (pset.sversion >= 90000) - { - snprintf(buf, sizeof(buf), - "SELECT oid as \"%s\",\n" - " pg_catalog.pg_get_userbyid(lomowner) as \"%s\",\n" - " pg_catalog.obj_description(oid, 'pg_largeobject') as \"%s\"\n" - " FROM pg_catalog.pg_largeobject_metadata " - " ORDER BY oid", - gettext_noop("ID"), - gettext_noop("Owner"), - gettext_noop("Description")); - } - else - { - snprintf(buf, sizeof(buf), - "SELECT loid as \"%s\",\n" - " pg_catalog.obj_description(loid, 'pg_largeobject') as \"%s\"\n" - "FROM (SELECT DISTINCT loid FROM pg_catalog.pg_largeobject) x\n" - "ORDER BY 1", - gettext_noop("ID"), - gettext_noop("Description")); - } + snprintf(buf, sizeof(buf), + "SELECT oid as \"%s\",\n" + " pg_catalog.pg_get_userbyid(lomowner) as \"%s\",\n" + " pg_catalog.obj_description(oid, 'pg_largeobject') as \"%s\"\n" + " FROM pg_catalog.pg_largeobject_metadata " + " ORDER BY oid", + gettext_noop("ID"), + gettext_noop("Owner"), + gettext_noop("Description")); res = PSQLexec(buf); if (!res) diff --git a/src/bin/psql/tab-complete.c b/src/bin/psql/tab-complete.c index 2f412ca3db3..b524dc87fc1 100644 --- a/src/bin/psql/tab-complete.c +++ b/src/bin/psql/tab-complete.c @@ -993,7 +993,7 @@ Query_for_index_of_table \ /* * These object types were introduced later than our support cutoff of - * server version 7.4. We use the VersionedQuery infrastructure so that + * server version 9.2. We use the VersionedQuery infrastructure so that * we don't send certain-to-fail queries to older servers. */ @@ -2911,7 +2911,7 @@ psql_completion(const char *text, int start, int end) Matches("CREATE", "OR", "REPLACE", "TRANSFORM")) COMPLETE_WITH("FOR"); else if (Matches("CREATE", "TRANSFORM", "FOR") || - Matches("CREATE","OR", "REPLACE", "TRANSFORM", "FOR")) + Matches("CREATE", "OR", "REPLACE", "TRANSFORM", "FOR")) COMPLETE_WITH_SCHEMA_QUERY(Query_for_list_of_datatypes, NULL); else if (Matches("CREATE", "TRANSFORM", "FOR", MatchAny) || Matches("CREATE", "OR", "REPLACE", "TRANSFORM", "FOR", MatchAny))