agora inbox for [email protected]help / color / mirror / Atom feed
[PATCH 2/4] Syscache usage tracking feature. 56+ messages / 3 participants [nested] [flat]
* [PATCH 2/4] Syscache usage tracking feature. @ 2018-10-16 06:48 Kyotaro Horiguchi <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Kyotaro Horiguchi @ 2018-10-16 06:48 UTC (permalink / raw) Collects syscache usage statictics and show it using the view pg_stat_syscache. The feature is controlled by the GUC variable track_syscache_usage_interval. --- doc/src/sgml/config.sgml | 15 ++ src/backend/catalog/system_views.sql | 17 +++ src/backend/postmaster/pgstat.c | 201 ++++++++++++++++++++++++-- src/backend/tcop/postgres.c | 23 +++ src/backend/utils/adt/pgstatfuncs.c | 134 +++++++++++++++++ src/backend/utils/cache/catcache.c | 115 +++++++++++---- src/backend/utils/cache/syscache.c | 24 +++ src/backend/utils/init/globals.c | 1 + src/backend/utils/init/postinit.c | 11 ++ src/backend/utils/misc/guc.c | 10 ++ src/backend/utils/misc/postgresql.conf.sample | 1 + src/include/catalog/pg_proc.dat | 9 ++ src/include/miscadmin.h | 1 + src/include/pgstat.h | 6 +- src/include/utils/catcache.h | 9 +- src/include/utils/syscache.h | 19 +++ src/include/utils/timeout.h | 1 + src/test/regress/expected/rules.out | 24 ++- 18 files changed, 576 insertions(+), 45 deletions(-) diff --git a/doc/src/sgml/config.sgml b/doc/src/sgml/config.sgml index d0d2374944..5ff3ebeb4e 100644 --- a/doc/src/sgml/config.sgml +++ b/doc/src/sgml/config.sgml @@ -6687,6 +6687,21 @@ COPY postgres_log FROM '/full/path/to/logfile.csv' WITH csv; </listitem> </varlistentry> + <varlistentry id="guc-track-syscache-usage-interval" xreflabel="track_syscache_usage_interval"> + <term><varname>track_syscache_usage_interval</varname> (<type>integer</type>) + <indexterm> + <primary><varname>track_syscache_usage_interval</varname> configuration parameter</primary> + </indexterm> + </term> + <listitem> + <para> + Specifies the interval to collect system cache usage statistics in + milliseconds. This parameter is 0 by default, which means disabled. + Only superusers can change this setting. + </para> + </listitem> + </varlistentry> + <varlistentry id="guc-track-io-timing" xreflabel="track_io_timing"> <term><varname>track_io_timing</varname> (<type>boolean</type>) <indexterm> diff --git a/src/backend/catalog/system_views.sql b/src/backend/catalog/system_views.sql index 3e229c693c..f5d1aaf96f 100644 --- a/src/backend/catalog/system_views.sql +++ b/src/backend/catalog/system_views.sql @@ -906,6 +906,22 @@ CREATE VIEW pg_stat_progress_vacuum AS FROM pg_stat_get_progress_info('VACUUM') AS S LEFT JOIN pg_database D ON S.datid = D.oid; +CREATE VIEW pg_stat_syscache AS + SELECT + S.pid AS pid, + S.relid::regclass AS relname, + S.indid::regclass AS cache_name, + S.size AS size, + S.ntup AS ntuples, + S.searches AS searches, + S.hits AS hits, + S.neg_hits AS neg_hits, + S.ageclass AS ageclass, + S.last_update AS last_update + FROM pg_stat_activity A + JOIN LATERAL (SELECT A.pid, * FROM pg_get_syscache_stats(A.pid)) S + ON (A.pid = S.pid); + CREATE VIEW pg_user_mappings AS SELECT U.oid AS umid, @@ -1185,6 +1201,7 @@ GRANT EXECUTE ON FUNCTION pg_ls_waldir() TO pg_monitor; GRANT EXECUTE ON FUNCTION pg_ls_archive_statusdir() TO pg_monitor; GRANT EXECUTE ON FUNCTION pg_ls_tmpdir() TO pg_monitor; GRANT EXECUTE ON FUNCTION pg_ls_tmpdir(oid) TO pg_monitor; +GRANT EXECUTE ON FUNCTION pg_get_syscache_stats(int) TO pg_monitor; GRANT pg_read_all_settings TO pg_monitor; GRANT pg_read_all_stats TO pg_monitor; diff --git a/src/backend/postmaster/pgstat.c b/src/backend/postmaster/pgstat.c index 81c6499251..a1939958b7 100644 --- a/src/backend/postmaster/pgstat.c +++ b/src/backend/postmaster/pgstat.c @@ -66,6 +66,7 @@ #include "utils/ps_status.h" #include "utils/rel.h" #include "utils/snapmgr.h" +#include "utils/syscache.h" #include "utils/timestamp.h" @@ -124,6 +125,7 @@ bool pgstat_track_activities = false; bool pgstat_track_counts = false; int pgstat_track_functions = TRACK_FUNC_OFF; +int pgstat_track_syscache_usage_interval = 0; int pgstat_track_activity_query_size = 1024; /* ---------- @@ -236,6 +238,11 @@ typedef struct TwoPhasePgStatRecord bool t_truncated; /* was the relation truncated? */ } TwoPhasePgStatRecord; +/* bitmap symbols to specify target file types remove */ +#define PGSTAT_REMFILE_DBSTAT 1 /* remove only databsae stats files */ +#define PGSTAT_REMFILE_SYSCACHE 2 /* remove only syscache stats files */ +#define PGSTAT_REMFILE_ALL 3 /* remove both type of files */ + /* * Info about current "snapshot" of stats file */ @@ -335,6 +342,7 @@ static void pgstat_recv_funcpurge(PgStat_MsgFuncpurge *msg, int len); static void pgstat_recv_recoveryconflict(PgStat_MsgRecoveryConflict *msg, int len); static void pgstat_recv_deadlock(PgStat_MsgDeadlock *msg, int len); static void pgstat_recv_tempfile(PgStat_MsgTempFile *msg, int len); +static void pgstat_remove_syscache_statsfile(void); /* ------------------------------------------------------------ * Public functions called from postmaster follow @@ -630,10 +638,13 @@ startup_failed: } /* - * subroutine for pgstat_reset_all + * remove stats files + * + * clean up stats files in specified directory. target is one of + * PGSTAT_REFILE_DBSTAT/SYSCACHE/ALL and restricts files to remove. */ static void -pgstat_reset_remove_files(const char *directory) +pgstat_reset_remove_files(const char *directory, int target) { DIR *dir; struct dirent *entry; @@ -644,25 +655,39 @@ pgstat_reset_remove_files(const char *directory) { int nchars; Oid tmp_oid; + int filetype = 0; /* * Skip directory entries that don't match the file names we write. * See get_dbstat_filename for the database-specific pattern. */ if (strncmp(entry->d_name, "global.", 7) == 0) + { + filetype = PGSTAT_REMFILE_DBSTAT; nchars = 7; + } else { + char head[2]; + nchars = 0; - (void) sscanf(entry->d_name, "db_%u.%n", - &tmp_oid, &nchars); - if (nchars <= 0) - continue; + (void) sscanf(entry->d_name, "%c%c_%u.%n", + head, head + 1, &tmp_oid, &nchars); + /* %u allows leading whitespace, so reject that */ - if (strchr("0123456789", entry->d_name[3]) == NULL) + if (nchars < 3 || !isdigit(entry->d_name[3])) continue; + + if (strncmp(head, "db", 2) == 0) + filetype = PGSTAT_REMFILE_DBSTAT; + else if (strncmp(head, "cc", 2) == 0) + filetype = PGSTAT_REMFILE_SYSCACHE; } + /* skip if this is not a target */ + if ((filetype & target) == 0) + continue; + if (strcmp(entry->d_name + nchars, "tmp") != 0 && strcmp(entry->d_name + nchars, "stat") != 0) continue; @@ -683,8 +708,9 @@ pgstat_reset_remove_files(const char *directory) void pgstat_reset_all(void) { - pgstat_reset_remove_files(pgstat_stat_directory); - pgstat_reset_remove_files(PGSTAT_STAT_PERMANENT_DIRECTORY); + pgstat_reset_remove_files(pgstat_stat_directory, PGSTAT_REMFILE_ALL); + pgstat_reset_remove_files(PGSTAT_STAT_PERMANENT_DIRECTORY, + PGSTAT_REMFILE_ALL); } #ifdef EXEC_BACKEND @@ -2963,6 +2989,10 @@ pgstat_beshutdown_hook(int code, Datum arg) if (OidIsValid(MyDatabaseId)) pgstat_report_stat(true); + /* clear syscache statistics files and temprary settings */ + if (MyBackendId != InvalidBackendId) + pgstat_remove_syscache_statsfile(); + /* * Clear my status entry, following the protocol of bumping st_changecount * before and after. We use a volatile pointer here to ensure the @@ -4287,6 +4317,9 @@ PgstatCollectorMain(int argc, char *argv[]) pgStatRunningInCollector = true; pgStatDBHash = pgstat_read_statsfiles(InvalidOid, true, true); + /* Remove left-over syscache stats files */ + pgstat_reset_remove_files(pgstat_stat_directory, PGSTAT_REMFILE_SYSCACHE); + /* * Loop to process messages until we get SIGQUIT or detect ungraceful * death of our parent postmaster. @@ -6377,3 +6410,153 @@ pgstat_clip_activity(const char *raw_activity) return activity; } + +/* + * return the filename for a syscache stat file; filename is the output + * buffer, of length len. + */ +void +pgstat_get_syscachestat_filename(bool permanent, bool tempname, int backendid, + char *filename, int len) +{ + int printed; + + /* NB -- pgstat_reset_remove_files knows about the pattern this uses */ + printed = snprintf(filename, len, "%s/cc_%u.%s", + permanent ? PGSTAT_STAT_PERMANENT_DIRECTORY : + pgstat_stat_directory, + backendid, + tempname ? "tmp" : "stat"); + if (printed >= len) + elog(ERROR, "overlength pgstat path"); +} + +/* removes syscache stats files of this backend */ +static void +pgstat_remove_syscache_statsfile(void) +{ + char fname[MAXPGPATH]; + + pgstat_get_syscachestat_filename(false, false, MyBackendId, + fname, MAXPGPATH); + unlink(fname); /* don't care of the result */ +} + +/* + * pgstat_write_syscache_stats() - + * Write the syscache statistics files. + * + * If 'force' is false, this function skips writing a file and resturns the + * time remaining in the current interval in milliseconds. If'force' is true, + * writes a file regardless of the remaining time and reset the interval. + */ +long +pgstat_write_syscache_stats(bool force) +{ + static TimestampTz last_report = 0; + TimestampTz now; + long elapsed; + long secs; + int usecs; + int cacheId; + FILE *fpout; + char statfile[MAXPGPATH]; + char tmpfile[MAXPGPATH]; + + /* Return if we don't want it */ + if (!force && pgstat_track_syscache_usage_interval <= 0) + { + /* disabled. remove the statistics file if any */ + if (last_report > 0) + { + last_report = 0; + pgstat_remove_syscache_statsfile(); + } + return 0; + } + + /* Check aginst the interval */ + now = GetCurrentTransactionStopTimestamp(); + TimestampDifference(last_report, now, &secs, &usecs); + elapsed = secs * 1000 + usecs / 1000; + + if (!force && elapsed < pgstat_track_syscache_usage_interval) + { + /* not yet the time, inform the remaining time to the caller */ + return pgstat_track_syscache_usage_interval - elapsed; + } + + /* now update the stats */ + last_report = now; + + pgstat_get_syscachestat_filename(false, true, + MyBackendId, tmpfile, MAXPGPATH); + pgstat_get_syscachestat_filename(false, false, + MyBackendId, statfile, MAXPGPATH); + + /* + * This function can be called from ProcessInterrupts(). Inhibit recursive + * interrupts to avoid recursive entry. + */ + HOLD_INTERRUPTS(); + + fpout = AllocateFile(tmpfile, PG_BINARY_W); + if (fpout == NULL) + { + ereport(LOG, + (errcode_for_file_access(), + errmsg("could not open temporary statistics file \"%s\": %m", + tmpfile))); + /* + * Failure writing this file is not critical. Just skip this time and + * tell caller to wait for the next interval. + */ + RESUME_INTERRUPTS(); + return pgstat_track_syscache_usage_interval; + } + + /* write out every catcache stats */ + for (cacheId = 0 ; cacheId < SysCacheSize ; cacheId++) + { + SysCacheStats *stats; + + stats = SysCacheGetStats(cacheId); + Assert (stats); + + /* write error is checked later using ferror() */ + fputc('T', fpout); + (void)fwrite(&cacheId, sizeof(int), 1, fpout); + (void)fwrite(&last_report, sizeof(TimestampTz), 1, fpout); + (void)fwrite(stats, sizeof(*stats), 1, fpout); + } + fputc('E', fpout); + + if (ferror(fpout)) + { + ereport(LOG, + (errcode_for_file_access(), + errmsg("could not write syscache statistics file \"%s\": %m", + tmpfile))); + FreeFile(fpout); + unlink(tmpfile); + } + else if (FreeFile(fpout) < 0) + { + ereport(LOG, + (errcode_for_file_access(), + errmsg("could not close syscache statistics file \"%s\": %m", + tmpfile))); + unlink(tmpfile); + } + else if (rename(tmpfile, statfile) < 0) + { + ereport(LOG, + (errcode_for_file_access(), + errmsg("could not rename syscache statistics file \"%s\" to \"%s\": %m", + tmpfile, statfile))); + unlink(tmpfile); + } + + RESUME_INTERRUPTS(); + return 0; +} diff --git a/src/backend/tcop/postgres.c b/src/backend/tcop/postgres.c index 36cfd507b2..fb77a0ce4c 100644 --- a/src/backend/tcop/postgres.c +++ b/src/backend/tcop/postgres.c @@ -3157,6 +3157,12 @@ ProcessInterrupts(void) } + if (IdleSyscacheStatsUpdateTimeoutPending) + { + IdleSyscacheStatsUpdateTimeoutPending = false; + pgstat_write_syscache_stats(true); + } + if (ParallelMessagePending) HandleParallelMessages(); } @@ -3733,6 +3739,7 @@ PostgresMain(int argc, char *argv[], sigjmp_buf local_sigjmp_buf; volatile bool send_ready_for_query = true; bool disable_idle_in_transaction_timeout = false; + bool disable_idle_catcache_update_timeout = false; /* Initialize startup process environment if necessary. */ if (!IsUnderPostmaster) @@ -4173,9 +4180,19 @@ PostgresMain(int argc, char *argv[], } else { + long timeout; + ProcessCompletedNotifies(); pgstat_report_stat(false); + timeout = pgstat_write_syscache_stats(false); + + if (timeout > 0) + { + disable_idle_catcache_update_timeout = true; + enable_timeout_after(IDLE_CATCACHE_UPDATE_TIMEOUT, + timeout); + } set_ps_display("idle", false); pgstat_report_activity(STATE_IDLE, NULL); } @@ -4218,6 +4235,12 @@ PostgresMain(int argc, char *argv[], disable_idle_in_transaction_timeout = false; } + if (disable_idle_catcache_update_timeout) + { + disable_timeout(IDLE_CATCACHE_UPDATE_TIMEOUT, false); + disable_idle_catcache_update_timeout = false; + } + /* * (6) check for any other interesting events that happened while we * slept. diff --git a/src/backend/utils/adt/pgstatfuncs.c b/src/backend/utils/adt/pgstatfuncs.c index b6ba856ebe..6526cfefb4 100644 --- a/src/backend/utils/adt/pgstatfuncs.c +++ b/src/backend/utils/adt/pgstatfuncs.c @@ -14,6 +14,8 @@ */ #include "postgres.h" +#include <sys/stat.h> + #include "access/htup_details.h" #include "catalog/pg_authid.h" #include "catalog/pg_type.h" @@ -28,6 +30,7 @@ #include "utils/acl.h" #include "utils/builtins.h" #include "utils/inet.h" +#include "utils/syscache.h" #include "utils/timestamp.h" #define UINT32_ACCESS_ONCE(var) ((uint32)(*((volatile uint32 *)&(var)))) @@ -1899,3 +1902,134 @@ pg_stat_get_archiver(PG_FUNCTION_ARGS) PG_RETURN_DATUM(HeapTupleGetDatum( heap_form_tuple(tupdesc, values, nulls))); } + +Datum +pgstat_get_syscache_stats(PG_FUNCTION_ARGS) +{ +#define PG_GET_SYSCACHE_SIZE 9 + int pid = PG_GETARG_INT32(0); + ReturnSetInfo *rsinfo = (ReturnSetInfo *) fcinfo->resultinfo; + TupleDesc tupdesc; + Tuplestorestate *tupstore; + MemoryContext per_query_ctx; + MemoryContext oldcontext; + PgBackendStatus *beentry; + int beid; + char fname[MAXPGPATH]; + FILE *fpin; + char c; + + if (rsinfo == NULL || !IsA(rsinfo, ReturnSetInfo)) + ereport(ERROR, + (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), + errmsg("set-valued function called in context that cannot accept a set"))); + if (!(rsinfo->allowedModes & SFRM_Materialize)) + ereport(ERROR, + (errcode(ERRCODE_FEATURE_NOT_SUPPORTED), + errmsg("materialize mode required, but it is not " \ + "allowed in this context"))); + + /* Build a tuple descriptor for our result type */ + if (get_call_result_type(fcinfo, NULL, &tupdesc) != TYPEFUNC_COMPOSITE) + elog(ERROR, "return type must be a row type"); + + + per_query_ctx = rsinfo->econtext->ecxt_per_query_memory; + + oldcontext = MemoryContextSwitchTo(per_query_ctx); + tupstore = tuplestore_begin_heap(true, false, work_mem); + rsinfo->returnMode = SFRM_Materialize; + rsinfo->setResult = tupstore; + rsinfo->setDesc = tupdesc; + + MemoryContextSwitchTo(oldcontext); + + /* find beentry for given pid*/ + beentry = NULL; + for (beid = 1; + (beentry = pgstat_fetch_stat_beentry(beid)) && + beentry->st_procpid != pid ; + beid++); + + /* + * we silently return empty result on failure or insufficient privileges + */ + if (!beentry || + (!has_privs_of_role(GetUserId(), beentry->st_userid) && + !is_member_of_role(GetUserId(), DEFAULT_ROLE_READ_ALL_STATS))) + goto no_data; + + pgstat_get_syscachestat_filename(false, false, beid, fname, MAXPGPATH); + + if ((fpin = AllocateFile(fname, PG_BINARY_R)) == NULL) + { + if (errno != ENOENT) + ereport(WARNING, + (errcode_for_file_access(), + errmsg("could not open statistics file \"%s\": %m", + fname))); + /* also return empty on no statistics file */ + goto no_data; + } + + /* read the statistics file into tuplestore */ + while ((c = fgetc(fpin)) == 'T') + { + TimestampTz last_update; + SysCacheStats stats; + int cacheid; + Datum values[PG_GET_SYSCACHE_SIZE]; + bool nulls[PG_GET_SYSCACHE_SIZE] = {0}; + Datum datums[SYSCACHE_STATS_NAGECLASSES * 2]; + bool arrnulls[SYSCACHE_STATS_NAGECLASSES * 2] = {0}; + int dims[] = {SYSCACHE_STATS_NAGECLASSES, 2}; + int lbs[] = {1, 1}; + ArrayType *arr; + int i, j; + + fread(&cacheid, sizeof(int), 1, fpin); + fread(&last_update, sizeof(TimestampTz), 1, fpin); + if (fread(&stats, 1, sizeof(stats), fpin) != sizeof(stats)) + { + ereport(WARNING, + (errmsg("corrupted syscache statistics file \"%s\"", + fname))); + goto no_data; + } + + i = 0; + values[i++] = ObjectIdGetDatum(stats.reloid); + values[i++] = ObjectIdGetDatum(stats.indoid); + values[i++] = Int64GetDatum(stats.size); + values[i++] = Int64GetDatum(stats.ntuples); + values[i++] = Int64GetDatum(stats.nsearches); + values[i++] = Int64GetDatum(stats.nhits); + values[i++] = Int64GetDatum(stats.nneg_hits); + + for (j = 0 ; j < SYSCACHE_STATS_NAGECLASSES ; j++) + { + datums[j * 2] = Int32GetDatum((int32) stats.ageclasses[j]); + datums[j * 2 + 1] = Int32GetDatum((int32) stats.nclass_entries[j]); + } + + arr = construct_md_array(datums, arrnulls, 2, dims, lbs, + INT4OID, sizeof(int32), true, 'i'); + values[i++] = PointerGetDatum(arr); + + values[i++] = TimestampTzGetDatum(last_update); + + Assert (i == PG_GET_SYSCACHE_SIZE); + + tuplestore_putvalues(tupstore, tupdesc, values, nulls); + } + + /* check for the end of file. abandon the result if file is broken */ + if (c != 'E' || fgetc(fpin) != EOF) + tuplestore_clear(tupstore); + + FreeFile(fpin); + +no_data: + tuplestore_donestoring(tupstore); + return (Datum) 0; +} diff --git a/src/backend/utils/cache/catcache.c b/src/backend/utils/cache/catcache.c index 5106ed896a..950576fea0 100644 --- a/src/backend/utils/cache/catcache.c +++ b/src/backend/utils/cache/catcache.c @@ -89,6 +89,10 @@ static CatCacheHeader *CacheHdr = NULL; /* Timestamp used for any operation on caches. */ TimestampTz catcacheclock = 0; +/* age classes for pruning */ +static double ageclass[SYSCACHE_STATS_NAGECLASSES] + = {0.05, 0.1, 1.0, 2.0, 3.0, 0.0}; + static inline HeapTuple SearchCatCacheInternal(CatCache *cache, int nkeys, Datum v1, Datum v2, @@ -619,9 +623,7 @@ CatCacheInvalidate(CatCache *cache, uint32 hashValue) else CatCacheRemoveCTup(cache, ct); CACHE1_elog(DEBUG2, "CatCacheInvalidate: invalidated"); -#ifdef CATCACHE_STATS cache->cc_invals++; -#endif /* could be multiple matches, so keep looking! */ } } @@ -697,9 +699,7 @@ ResetCatalogCache(CatCache *cache) } else CatCacheRemoveCTup(cache, ct); -#ifdef CATCACHE_STATS cache->cc_invals++; -#endif } } } @@ -906,10 +906,11 @@ CatCacheCleanupOldEntries(CatCache *cp) * cache_prune_min_age. The index of nremoved_entry is the value of the * clock-sweep counter, which takes from 0 up to 2. */ - double ageclass[] = {0.05, 0.1, 1.0, 2.0, 3.0, 0.0}; - int nentries[] = {0, 0, 0, 0, 0, 0}; + int nentries[SYSCACHE_STATS_NAGECLASSES] = {0, 0, 0, 0, 0, 0}; int nremoved_entry[3] = {0, 0, 0}; int j; + + Assert(ageclass[SYSCACHE_STATS_NAGECLASSES - 1] == 0.0); #endif /* Return immediately if no pruning is wanted */ @@ -923,7 +924,11 @@ CatCacheCleanupOldEntries(CatCache *cp) if (hash_size + cp->cc_tupsize < (Size) cache_memory_target * 1024L) return false; - /* Search the whole hash for entries to remove */ + /* + * Search the whole hash for entries to remove. This is a quite time + * consuming task during catcache lookup, but accetable since now we are + * going to expand the hash table. + */ for (i = 0; i < cp->cc_nbuckets; i++) { dlist_mutable_iter iter; @@ -936,21 +941,21 @@ CatCacheCleanupOldEntries(CatCache *cp) /* - * Calculate the duration from the time of the last access to the - * "current" time. Since catcacheclock is not advanced within a - * transaction, the entries that are accessed within the current - * transaction won't be pruned. + * Calculate the duration from the time from the last access to + * the "current" time. Since catcacheclock is not advanced within + * a transaction, the entries that are accessed within the current + * transaction always get 0 as the result. */ TimestampDifference(ct->lastaccess, catcacheclock, &entry_age, &us); #ifdef CATCACHE_STATS /* count catcache entries for each age class */ ntotal++; - for (j = 0 ; - ageclass[j] != 0.0 && - entry_age > cache_prune_min_age * ageclass[j] ; - j++); - if (ageclass[j] == 0.0) j--; + + j = 0; + while (j < SYSCACHE_STATS_NAGECLASSES - 1 && + entry_age > cache_prune_min_age * ageclass[j]) + j++; nentries[j]++; #endif @@ -981,14 +986,17 @@ CatCacheCleanupOldEntries(CatCache *cp) } #ifdef CATCACHE_STATS + StaticAssertStmt(SYSCACHE_STATS_NAGECLASSES == 6, + "number of syscache age class must be 6"); ereport(DEBUG1, - (errmsg ("removed %d/%d, age(-%.0fs:%d, -%.0fs:%d, *-%.0fs:%d, -%.0fs:%d, -%.0fs:%d) naccessed(0:%d, 1:%d, 2:%d)", + (errmsg ("removed %d/%d, age(-%.0fs:%d, -%.0fs:%d, *-%.0fs:%d, -%.0fs:%d, -%.0fs:%d, rest:%d) naccessed(0:%d, 1:%d, 2:%d)", nremoved, ntotal, ageclass[0] * cache_prune_min_age, nentries[0], ageclass[1] * cache_prune_min_age, nentries[1], ageclass[2] * cache_prune_min_age, nentries[2], ageclass[3] * cache_prune_min_age, nentries[3], ageclass[4] * cache_prune_min_age, nentries[4], + nentries[5], nremoved_entry[0], nremoved_entry[1], nremoved_entry[2]), errhidestmt(true))); #endif @@ -1365,9 +1373,7 @@ SearchCatCacheInternal(CatCache *cache, if (unlikely(cache->cc_tupdesc == NULL)) CatalogCacheInitializeCache(cache); -#ifdef CATCACHE_STATS cache->cc_searches++; -#endif /* Initialize local parameter array */ arguments[0] = v1; @@ -1427,9 +1433,7 @@ SearchCatCacheInternal(CatCache *cache, CACHE3_elog(DEBUG2, "SearchCatCache(%s): found in bucket %d", cache->cc_relname, hashIndex); -#ifdef CATCACHE_STATS cache->cc_hits++; -#endif return &ct->tuple; } @@ -1438,9 +1442,7 @@ SearchCatCacheInternal(CatCache *cache, CACHE3_elog(DEBUG2, "SearchCatCache(%s): found neg entry in bucket %d", cache->cc_relname, hashIndex); -#ifdef CATCACHE_STATS cache->cc_neg_hits++; -#endif return NULL; } @@ -1568,9 +1570,7 @@ SearchCatCacheMiss(CatCache *cache, CACHE3_elog(DEBUG2, "SearchCatCache(%s): put in bucket %d", cache->cc_relname, hashIndex); -#ifdef CATCACHE_STATS cache->cc_newloads++; -#endif return &ct->tuple; } @@ -1681,9 +1681,7 @@ SearchCatCacheList(CatCache *cache, Assert(nkeys > 0 && nkeys < cache->cc_nkeys); -#ifdef CATCACHE_STATS cache->cc_lsearches++; -#endif /* Initialize local parameter array */ arguments[0] = v1; @@ -1740,9 +1738,7 @@ SearchCatCacheList(CatCache *cache, CACHE2_elog(DEBUG2, "SearchCatCacheList(%s): found list", cache->cc_relname); -#ifdef CATCACHE_STATS cache->cc_lhits++; -#endif return cl; } @@ -2254,3 +2250,64 @@ PrintCatCacheListLeakWarning(CatCList *list) list->my_cache->cc_relname, list->my_cache->id, list, list->refcount); } + +/* + * CatCacheGetStats - fill in SysCacheStats struct. + * + * This is a support routine for SysCacheGetStats, substantially fills in the + * result. The classification here is based on the same criteria to + * CatCacheCleanupOldEntries(). + */ +void +CatCacheGetStats(CatCache *cache, SysCacheStats *stats) +{ + int i, j; + + Assert(ageclass[SYSCACHE_STATS_NAGECLASSES - 1] == 0.0); + + /* fill in the stats struct */ + stats->size = cache->cc_tupsize + cache->cc_nbuckets * sizeof(dlist_head); + stats->ntuples = cache->cc_ntup; + stats->nsearches = cache->cc_searches; + stats->nhits = cache->cc_hits; + stats->nneg_hits = cache->cc_neg_hits; + + /* cache_prune_min_age can be changed on-session, fill it every time */ + for (i = 0 ; i < SYSCACHE_STATS_NAGECLASSES ; i++) + stats->ageclasses[i] = (int) (cache_prune_min_age * ageclass[i]); + + /* + * nth element in nclass_entries stores the number of cache entries that + * have lived unaccessed for corresponding multiple in ageclass of + * cache_prune_min_age. + */ + memset(stats->nclass_entries, 0, sizeof(int) * SYSCACHE_STATS_NAGECLASSES); + + /* Scan the whole hash */ + for (i = 0; i < cache->cc_nbuckets; i++) + { + dlist_mutable_iter iter; + + dlist_foreach_modify(iter, &cache->cc_bucket[i]) + { + CatCTup *ct = dlist_container(CatCTup, cache_elem, iter.cur); + long entry_age; + int us; + + /* + * Calculate the duration from the time from the last access to + * the "current" time. Since catcacheclock is not advanced within + * a transaction, the entries that are accessed within the current + * transaction won't be pruned. + */ + TimestampDifference(ct->lastaccess, catcacheclock, &entry_age, &us); + + j = 0; + while (j < SYSCACHE_STATS_NAGECLASSES - 1 && + entry_age > stats->ageclasses[j]) + j++; + + stats->nclass_entries[j]++; + } + } +} diff --git a/src/backend/utils/cache/syscache.c b/src/backend/utils/cache/syscache.c index ac98c19155..7b38a06708 100644 --- a/src/backend/utils/cache/syscache.c +++ b/src/backend/utils/cache/syscache.c @@ -20,6 +20,9 @@ */ #include "postgres.h" +#include <sys/stat.h> +#include <unistd.h> + #include "access/htup_details.h" #include "access/sysattr.h" #include "catalog/indexing.h" @@ -1534,6 +1537,27 @@ RelationSupportsSysCache(Oid relid) return false; } +/* + * SysCacheGetStats - returns stats of specified syscache + * + * This routine returns the address of its local static memory. + */ +SysCacheStats * +SysCacheGetStats(int cacheId) +{ + static SysCacheStats stats; + + Assert(cacheId >=0 && cacheId < SysCacheSize); + + memset(&stats, 0, sizeof(stats)); + + stats.reloid = cacheinfo[cacheId].reloid; + stats.indoid = cacheinfo[cacheId].indoid; + + CatCacheGetStats(SysCache[cacheId], &stats); + + return &stats; +} /* * OID comparator for pg_qsort diff --git a/src/backend/utils/init/globals.c b/src/backend/utils/init/globals.c index fd51934aaf..f039ecd805 100644 --- a/src/backend/utils/init/globals.c +++ b/src/backend/utils/init/globals.c @@ -32,6 +32,7 @@ volatile sig_atomic_t QueryCancelPending = false; volatile sig_atomic_t ProcDiePending = false; volatile sig_atomic_t ClientConnectionLost = false; volatile sig_atomic_t IdleInTransactionSessionTimeoutPending = false; +volatile sig_atomic_t IdleSyscacheStatsUpdateTimeoutPending = false; volatile sig_atomic_t ConfigReloadPending = false; volatile uint32 InterruptHoldoffCount = 0; volatile uint32 QueryCancelHoldoffCount = 0; diff --git a/src/backend/utils/init/postinit.c b/src/backend/utils/init/postinit.c index c0b6231458..dee7f19475 100644 --- a/src/backend/utils/init/postinit.c +++ b/src/backend/utils/init/postinit.c @@ -72,6 +72,7 @@ static void ShutdownPostgres(int code, Datum arg); static void StatementTimeoutHandler(void); static void LockTimeoutHandler(void); static void IdleInTransactionSessionTimeoutHandler(void); +static void IdleSyscacheStatsUpdateTimeoutHandler(void); static bool ThereIsAtLeastOneRole(void); static void process_startup_options(Port *port, bool am_superuser); static void process_settings(Oid databaseid, Oid roleid); @@ -628,6 +629,8 @@ InitPostgres(const char *in_dbname, Oid dboid, const char *username, RegisterTimeout(LOCK_TIMEOUT, LockTimeoutHandler); RegisterTimeout(IDLE_IN_TRANSACTION_SESSION_TIMEOUT, IdleInTransactionSessionTimeoutHandler); + RegisterTimeout(IDLE_CATCACHE_UPDATE_TIMEOUT, + IdleSyscacheStatsUpdateTimeoutHandler); } /* @@ -1239,6 +1242,14 @@ IdleInTransactionSessionTimeoutHandler(void) SetLatch(MyLatch); } +static void +IdleSyscacheStatsUpdateTimeoutHandler(void) +{ + IdleSyscacheStatsUpdateTimeoutPending = true; + InterruptPending = true; + SetLatch(MyLatch); +} + /* * Returns true if at least one role is defined in this database cluster. */ diff --git a/src/backend/utils/misc/guc.c b/src/backend/utils/misc/guc.c index 06c589f725..32e41253a6 100644 --- a/src/backend/utils/misc/guc.c +++ b/src/backend/utils/misc/guc.c @@ -3168,6 +3168,16 @@ static struct config_int ConfigureNamesInt[] = NULL, NULL, NULL }, + { + {"track_syscache_usage_interval", PGC_SUSET, STATS_COLLECTOR, + gettext_noop("Sets the interval between syscache usage collection, in milliseconds. Zero disables syscache usage tracking."), + NULL + }, + &pgstat_track_syscache_usage_interval, + 0, 0, INT_MAX / 2, + NULL, NULL, NULL + }, + { {"gin_pending_list_limit", PGC_USERSET, CLIENT_CONN_STATEMENT, gettext_noop("Sets the maximum size of the pending list for GIN index."), diff --git a/src/backend/utils/misc/postgresql.conf.sample b/src/backend/utils/misc/postgresql.conf.sample index 108d332f2c..4d4fb42251 100644 --- a/src/backend/utils/misc/postgresql.conf.sample +++ b/src/backend/utils/misc/postgresql.conf.sample @@ -560,6 +560,7 @@ #track_io_timing = off #track_functions = none # none, pl, all #track_activity_query_size = 1024 # (change requires restart) +#track_syscache_usage_interval = 0 # zero disables tracking #stats_temp_directory = 'pg_stat_tmp' diff --git a/src/include/catalog/pg_proc.dat b/src/include/catalog/pg_proc.dat index b8de13f03b..6099a828d2 100644 --- a/src/include/catalog/pg_proc.dat +++ b/src/include/catalog/pg_proc.dat @@ -9669,6 +9669,15 @@ proargmodes => '{o,o,o,o,o,o,o,o,o,o,o}', proargnames => '{slot_name,plugin,slot_type,datoid,temporary,active,active_pid,xmin,catalog_xmin,restart_lsn,confirmed_flush_lsn}', prosrc => 'pg_get_replication_slots' }, +{ oid => '3425', + descr => 'syscache statistics', + proname => 'pg_get_syscache_stats', prorows => '100', proisstrict => 'f', + proretset => 't', provolatile => 'v', prorettype => 'record', + proargtypes => 'int4', + proallargtypes => '{int4,oid,oid,int8,int8,int8,int8,int8,_int4,timestamptz}', + proargmodes => '{i,o,o,o,o,o,o,o,o,o}', + proargnames => '{pid,relid,indid,size,ntup,searches,hits,neg_hits,ageclass,last_update}', + prosrc => 'pgstat_get_syscache_stats' }, { oid => '3786', descr => 'set up a logical replication slot', proname => 'pg_create_logical_replication_slot', provolatile => 'v', proparallel => 'u', prorettype => 'record', proargtypes => 'name name bool', diff --git a/src/include/miscadmin.h b/src/include/miscadmin.h index c9e35003a5..69b9a976f0 100644 --- a/src/include/miscadmin.h +++ b/src/include/miscadmin.h @@ -82,6 +82,7 @@ extern PGDLLIMPORT volatile sig_atomic_t InterruptPending; extern PGDLLIMPORT volatile sig_atomic_t QueryCancelPending; extern PGDLLIMPORT volatile sig_atomic_t ProcDiePending; extern PGDLLIMPORT volatile sig_atomic_t IdleInTransactionSessionTimeoutPending; +extern PGDLLIMPORT volatile sig_atomic_t IdleSyscacheStatsUpdateTimeoutPending; extern PGDLLIMPORT volatile sig_atomic_t ConfigReloadPending; extern PGDLLIMPORT volatile sig_atomic_t ClientConnectionLost; diff --git a/src/include/pgstat.h b/src/include/pgstat.h index 88a75fb798..b6bfd7d644 100644 --- a/src/include/pgstat.h +++ b/src/include/pgstat.h @@ -1144,6 +1144,7 @@ extern bool pgstat_track_activities; extern bool pgstat_track_counts; extern int pgstat_track_functions; extern PGDLLIMPORT int pgstat_track_activity_query_size; +extern int pgstat_track_syscache_usage_interval; extern char *pgstat_stat_directory; extern char *pgstat_stat_tmpname; extern char *pgstat_stat_filename; @@ -1228,7 +1229,8 @@ extern PgStat_BackendFunctionEntry *find_funcstat_entry(Oid func_id); extern void pgstat_initstats(Relation rel); extern char *pgstat_clip_activity(const char *raw_activity); - +extern void pgstat_get_syscachestat_filename(bool permanent, + bool tempname, int backendid, char *filename, int len); /* ---------- * pgstat_report_wait_start() - * @@ -1363,5 +1365,5 @@ extern PgStat_StatFuncEntry *pgstat_fetch_stat_funcentry(Oid funcid); extern int pgstat_fetch_stat_numbackends(void); extern PgStat_ArchiverStats *pgstat_fetch_stat_archiver(void); extern PgStat_GlobalStats *pgstat_fetch_global(void); - +extern long pgstat_write_syscache_stats(bool force); #endif /* PGSTAT_H */ diff --git a/src/include/utils/catcache.h b/src/include/utils/catcache.h index 5d24809900..4d51975920 100644 --- a/src/include/utils/catcache.h +++ b/src/include/utils/catcache.h @@ -65,10 +65,8 @@ typedef struct catcache int cc_tupsize; /* total amount of catcache tuples */ /* - * Keep these at the end, so that compiling catcache.c with CATCACHE_STATS - * doesn't break ABI for other modules + * Statistics entries */ -#ifdef CATCACHE_STATS long cc_searches; /* total # searches against this cache */ long cc_hits; /* # of matches against existing entry */ long cc_neg_hits; /* # of matches against negative entry */ @@ -81,7 +79,6 @@ typedef struct catcache long cc_invals; /* # of entries invalidated from cache */ long cc_lsearches; /* total # list-searches */ long cc_lhits; /* # of matches against existing lists */ -#endif } CatCache; @@ -254,4 +251,8 @@ extern void PrepareToInvalidateCacheTuple(Relation relation, extern void PrintCatCacheLeakWarning(HeapTuple tuple); extern void PrintCatCacheListLeakWarning(CatCList *list); +/* defined in syscache.h */ +typedef struct syscachestats SysCacheStats; +extern void CatCacheGetStats(CatCache *cache, SysCacheStats *syscachestats); + #endif /* CATCACHE_H */ diff --git a/src/include/utils/syscache.h b/src/include/utils/syscache.h index 95ee48954e..71b399c902 100644 --- a/src/include/utils/syscache.h +++ b/src/include/utils/syscache.h @@ -112,6 +112,24 @@ enum SysCacheIdentifier #define SysCacheSize (USERMAPPINGUSERSERVER + 1) }; +#define SYSCACHE_STATS_NAGECLASSES 6 +/* Struct for catcache tracking information */ +typedef struct syscachestats +{ + Oid reloid; /* target relation */ + Oid indoid; /* index */ + size_t size; /* size of the catcache */ + int ntuples; /* number of tuples resides in the catcache */ + int nsearches; /* number of searches */ + int nhits; /* number of cache hits */ + int nneg_hits; /* number of negative cache hits */ + /* age classes in seconds */ + int ageclasses[SYSCACHE_STATS_NAGECLASSES]; + /* number of tuples fall into the corresponding age class */ + int nclass_entries[SYSCACHE_STATS_NAGECLASSES]; +} SysCacheStats; + + extern void InitCatalogCache(void); extern void InitCatalogCachePhase2(void); @@ -164,6 +182,7 @@ extern void SysCacheInvalidate(int cacheId, uint32 hashValue); extern bool RelationInvalidatesSnapshotsOnly(Oid relid); extern bool RelationHasSysCache(Oid relid); extern bool RelationSupportsSysCache(Oid relid); +extern SysCacheStats *SysCacheGetStats(int cacheId); /* * The use of the macros below rather than direct calls to the corresponding diff --git a/src/include/utils/timeout.h b/src/include/utils/timeout.h index 9244a2a7b7..0ab441a364 100644 --- a/src/include/utils/timeout.h +++ b/src/include/utils/timeout.h @@ -31,6 +31,7 @@ typedef enum TimeoutId STANDBY_TIMEOUT, STANDBY_LOCK_TIMEOUT, IDLE_IN_TRANSACTION_SESSION_TIMEOUT, + IDLE_CATCACHE_UPDATE_TIMEOUT, /* First user-definable timeout reason */ USER_TIMEOUT, /* Maximum number of timeout reasons */ diff --git a/src/test/regress/expected/rules.out b/src/test/regress/expected/rules.out index 2c8e21baa7..7bd77e9972 100644 --- a/src/test/regress/expected/rules.out +++ b/src/test/regress/expected/rules.out @@ -1921,6 +1921,28 @@ pg_stat_sys_tables| SELECT pg_stat_all_tables.relid, pg_stat_all_tables.autoanalyze_count FROM pg_stat_all_tables WHERE ((pg_stat_all_tables.schemaname = ANY (ARRAY['pg_catalog'::name, 'information_schema'::name])) OR (pg_stat_all_tables.schemaname ~ '^pg_toast'::text)); +pg_stat_syscache| SELECT s.pid, + (s.relid)::regclass AS relname, + (s.indid)::regclass AS cache_name, + s.size, + s.ntup AS ntuples, + s.searches, + s.hits, + s.neg_hits, + s.ageclass, + s.last_update + FROM (pg_stat_activity a + JOIN LATERAL ( SELECT a.pid, + pg_get_syscache_stats.relid, + pg_get_syscache_stats.indid, + pg_get_syscache_stats.size, + pg_get_syscache_stats.ntup, + pg_get_syscache_stats.searches, + pg_get_syscache_stats.hits, + pg_get_syscache_stats.neg_hits, + pg_get_syscache_stats.ageclass, + pg_get_syscache_stats.last_update + FROM pg_get_syscache_stats(a.pid) pg_get_syscache_stats(relid, indid, size, ntup, searches, hits, neg_hits, ageclass, last_update)) s ON ((a.pid = s.pid))); pg_stat_user_functions| SELECT p.oid AS funcid, n.nspname AS schemaname, p.proname AS funcname, @@ -2352,7 +2374,7 @@ pg_settings|pg_settings_n|CREATE RULE pg_settings_n AS ON UPDATE TO pg_catalog.pg_settings DO INSTEAD NOTHING; pg_settings|pg_settings_u|CREATE RULE pg_settings_u AS ON UPDATE TO pg_catalog.pg_settings - WHERE (new.name = old.name) DO SELECT set_config(old.name, new.setting, false) AS set_config; + WHERE (new.name = old.name) DO SELECT set_config(old.name, new.setting, false, false) AS set_config; rtest_emp|rtest_emp_del|CREATE RULE rtest_emp_del AS ON DELETE TO public.rtest_emp DO INSERT INTO rtest_emplog (ename, who, action, newsal, oldsal) VALUES (old.ename, CURRENT_USER, 'fired'::bpchar, '$0.00'::money, old.salary); -- 2.16.3 ----Next_Part(Wed_Feb_06_17_37_04_2019_764)-- Content-Type: Text/X-Patch; charset=us-ascii Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="v11-0003-PoC-add-prune-by-number-of-entries-feature.patch" ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v3 01/11] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/.arW0LC=Yi8JO9BRih4YlyS Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v3-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v3 01/11] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/.arW0LC=Yi8JO9BRih4YlyS Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v3-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v2 01/11] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/RgO6TscyR9fMvkEm1k5N=yu Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v2-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v7 01/16] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/VSGM3xNEmY7iJyL2wuWRCjV Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v7-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v2 01/11] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/RgO6TscyR9fMvkEm1k5N=yu Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v2-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v6 01/15] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/74urtnrsBSymuH7bJczNOGS Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v6-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v5 01/14] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_//gBZFZYGWm7urqUgDbu6PSe Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v5-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) @ 2023-09-24 20:49 Karl O. Pinc <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Karl O. Pinc @ 2023-09-24 20:49 UTC (permalink / raw) The current section title of "Executing a Command with a Single-Row Result" does not reflect what the section is really about. Other sections make clear how to _execute_ commands, single-row result or not. What this section is about is how to _save_ a single row of results into variable(s). It would be nice to talk about saving results into variables in the section heading but I couldn't come up with anything pithy. "Saving a Single-Row of a Command's Result" seems good enough, especially since there's few other places to save results other than in variables. --- doc/src/sgml/plpgsql.sgml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/doc/src/sgml/plpgsql.sgml b/doc/src/sgml/plpgsql.sgml index f55e901c7e..8747e84245 100644 --- a/doc/src/sgml/plpgsql.sgml +++ b/doc/src/sgml/plpgsql.sgml @@ -1126,7 +1126,7 @@ PERFORM create_mv('cs_session_page_requests_mv', my_query); </sect2> <sect2 id="plpgsql-statements-sql-onerow"> - <title>Executing a Command with a Single-Row Result</title> + <title>Saving a Single-Row of a Command's Result</title> <indexterm zone="plpgsql-statements-sql-onerow"> <primary>SELECT INTO</primary> -- 2.30.2 --MP_/OOXZvOwbpccKfGOtE9/SwX6 Content-Type: text/x-patch Content-Transfer-Encoding: 7bit Content-Disposition: attachment; filename=v4-0002-Change-section-heading-to-better-describe-referen.patch ^ permalink raw reply [nested|flat] 56+ messages in thread
* [PATCH v54 1/5] Introduce an option to make logical replication database specific. @ 2026-04-05 07:51 Antonin Houska <[email protected]> 0 siblings, 0 replies; 56+ messages in thread From: Antonin Houska @ 2026-04-05 07:51 UTC (permalink / raw) By default, the logical decoding assumes access to shared catalogs, so the snapshot builder needs to consider cluster-wide XIDs during startup. That in turn means that, if any transaction is already running (and has XID assigned), the snapshot builder needs to wait for its completion, as it does not know if that transaction performed catalog changes earlier. Possible problem with this concept is that if REPACK (CONCURRENTLY) is running in some database, backends running the same command in other databases get stuck until the first one has committed. Thus only as single backend in the cluster can run REPACK (CONCURRENTLY) at any time. Likewise, REPACK (CONCURRENTLY) can block walsenders starting on behalf of subscriptions throughout the cluster. This patch adds a new option to logical replication output plugin, to declare that it does not use shared catalogs (i.e. catalogs that can be changed by transactions running in other databases in the cluster). In that case, no snapshot the backend will use during the decoding needs to contain information about transactions running in other databases. Thus the snapshot builder only needs to wait for completion of transactions in the current database. Currently we only use this option in the REPACK background worker. It could possibly be used in the plugin for logical replication too, however that would need thorough analysis of that plugin. The patch bumps WAL version number, due to a new field in xl_running_xacts. --- contrib/pg_visibility/pg_visibility.c | 4 +- doc/src/sgml/logicaldecoding.sgml | 4 ++ src/backend/access/index/genam.c | 8 +++ src/backend/access/rmgrdesc/standbydesc.c | 2 + src/backend/access/transam/xlog.c | 2 +- src/backend/access/transam/xlogfuncs.c | 2 +- src/backend/postmaster/bgwriter.c | 2 +- src/backend/replication/logical/decode.c | 8 ++- src/backend/replication/logical/logical.c | 3 ++ src/backend/replication/logical/snapbuild.c | 54 +++++++++++++++++++-- src/backend/replication/slot.c | 2 +- src/backend/storage/ipc/procarray.c | 23 ++++++++- src/backend/storage/ipc/standby.c | 14 +++++- src/include/access/genam.h | 7 +++ src/include/access/xlog_internal.h | 2 +- src/include/replication/output_plugin.h | 1 + src/include/replication/snapbuild.h | 3 +- src/include/storage/procarray.h | 2 +- src/include/storage/standby.h | 3 +- src/include/storage/standbydefs.h | 1 + 20 files changed, 128 insertions(+), 19 deletions(-) diff --git a/contrib/pg_visibility/pg_visibility.c b/contrib/pg_visibility/pg_visibility.c index dfab0b64cf5..d564bd2a00c 100644 --- a/contrib/pg_visibility/pg_visibility.c +++ b/contrib/pg_visibility/pg_visibility.c @@ -621,7 +621,7 @@ GetStrictOldestNonRemovableTransactionId(Relation rel) else if (rel == NULL || rel->rd_rel->relisshared) { /* Shared relation: take into account all running xids */ - runningTransactions = GetRunningTransactionData(); + runningTransactions = GetRunningTransactionData(InvalidOid); LWLockRelease(ProcArrayLock); LWLockRelease(XidGenLock); return runningTransactions->oldestRunningXid; @@ -632,7 +632,7 @@ GetStrictOldestNonRemovableTransactionId(Relation rel) * Normal relation: take into account xids running within the current * database */ - runningTransactions = GetRunningTransactionData(); + runningTransactions = GetRunningTransactionData(InvalidOid); LWLockRelease(ProcArrayLock); LWLockRelease(XidGenLock); return runningTransactions->oldestDatabaseRunningXid; diff --git a/doc/src/sgml/logicaldecoding.sgml b/doc/src/sgml/logicaldecoding.sgml index 6dc49108997..28089d1053c 100644 --- a/doc/src/sgml/logicaldecoding.sgml +++ b/doc/src/sgml/logicaldecoding.sgml @@ -959,6 +959,7 @@ typedef struct OutputPluginOptions { OutputPluginOutputType output_type; bool receive_rewrites; + bool need_shared_catalogs; } OutputPluginOptions; </programlisting> <literal>output_type</literal> has to either be set to @@ -969,6 +970,9 @@ typedef struct OutputPluginOptions also be called for changes made by heap rewrites during certain DDL operations. These are of interest to plugins that handle DDL replication, but they require special handling. + <literal>need_shared_catalogs</literal> can be set to false if you are + sure the plugin functions do not access shared system catalogs. It can + speed up creation of replication slots that use this plugin. </para> <para> diff --git a/src/backend/access/index/genam.c b/src/backend/access/index/genam.c index 1408989c568..44df2605068 100644 --- a/src/backend/access/index/genam.c +++ b/src/backend/access/index/genam.c @@ -394,6 +394,14 @@ systable_beginscan(Relation heapRelation, SysScanDesc sysscan; Relation irel; + /* + * If this backend promised that it won't access shared catalogs during + * logical decoding, this seems to be the right place to check. + */ + Assert(!HistoricSnapshotActive() || + accessSharedCatalogsInDecoding || + !heapRelation->rd_rel->relisshared); + if (indexOK && !IgnoreSystemIndexes && !ReindexIsProcessingIndex(indexId)) diff --git a/src/backend/access/rmgrdesc/standbydesc.c b/src/backend/access/rmgrdesc/standbydesc.c index 0a291354ae2..685d1bdb024 100644 --- a/src/backend/access/rmgrdesc/standbydesc.c +++ b/src/backend/access/rmgrdesc/standbydesc.c @@ -41,6 +41,8 @@ standby_desc_running_xacts(StringInfo buf, xl_running_xacts *xlrec) for (i = 0; i < xlrec->subxcnt; i++) appendStringInfo(buf, " %u", xlrec->xids[xlrec->xcnt + i]); } + + appendStringInfo(buf, "; dbid: %u", xlrec->dbid); } void diff --git a/src/backend/access/transam/xlog.c b/src/backend/access/transam/xlog.c index 9e8999bbb61..1a6c1456d2c 100644 --- a/src/backend/access/transam/xlog.c +++ b/src/backend/access/transam/xlog.c @@ -7731,7 +7731,7 @@ CreateCheckPoint(int flags) * recovery we don't need to write running xact data. */ if (!shutdown && XLogStandbyInfoActive()) - LogStandbySnapshot(); + LogStandbySnapshot(InvalidOid); START_CRIT_SECTION(); diff --git a/src/backend/access/transam/xlogfuncs.c b/src/backend/access/transam/xlogfuncs.c index 65bbaeda59c..0f5979691e6 100644 --- a/src/backend/access/transam/xlogfuncs.c +++ b/src/backend/access/transam/xlogfuncs.c @@ -245,7 +245,7 @@ pg_log_standby_snapshot(PG_FUNCTION_ARGS) (errcode(ERRCODE_OBJECT_NOT_IN_PREREQUISITE_STATE), errmsg("pg_log_standby_snapshot() can only be used if \"wal_level\" >= \"replica\""))); - recptr = LogStandbySnapshot(); + recptr = LogStandbySnapshot(InvalidOid); /* * As a convenience, return the WAL location of the last inserted record diff --git a/src/backend/postmaster/bgwriter.c b/src/backend/postmaster/bgwriter.c index 1d8947774a9..a30de4262eb 100644 --- a/src/backend/postmaster/bgwriter.c +++ b/src/backend/postmaster/bgwriter.c @@ -289,7 +289,7 @@ BackgroundWriterMain(const void *startup_data, size_t startup_data_len) if (now >= timeout && last_snapshot_lsn <= GetLastImportantRecPtr()) { - last_snapshot_lsn = LogStandbySnapshot(); + last_snapshot_lsn = LogStandbySnapshot(InvalidOid); last_snapshot_ts = now; } } diff --git a/src/backend/replication/logical/decode.c b/src/backend/replication/logical/decode.c index 57aaef57c61..4299d0bc867 100644 --- a/src/backend/replication/logical/decode.c +++ b/src/backend/replication/logical/decode.c @@ -381,7 +381,13 @@ standby_decode(LogicalDecodingContext *ctx, XLogRecordBuffer *buf) { xl_running_xacts *running = (xl_running_xacts *) XLogRecGetData(r); - SnapBuildProcessRunningXacts(builder, buf->origptr, running); + + /* + * If the plugin does not access shared catalogs, only keep + * track of transactions in the current database. + */ + SnapBuildProcessRunningXacts(builder, buf->origptr, running, + !ctx->options.need_shared_catalogs); /* * Abort all transactions that we keep track of, that are diff --git a/src/backend/replication/logical/logical.c b/src/backend/replication/logical/logical.c index f20d0c542f3..8ceaf64d164 100644 --- a/src/backend/replication/logical/logical.c +++ b/src/backend/replication/logical/logical.c @@ -285,6 +285,9 @@ StartupDecodingContext(List *output_plugin_options, ctx->write = do_write; ctx->update_progress = update_progress; + /* Assume shared catalog access. The startup callback can change it. */ + ctx->options.need_shared_catalogs = true; + ctx->output_plugin_options = output_plugin_options; ctx->fast_forward = fast_forward; diff --git a/src/backend/replication/logical/snapbuild.c b/src/backend/replication/logical/snapbuild.c index b4269a3b102..8ef2326c66d 100644 --- a/src/backend/replication/logical/snapbuild.c +++ b/src/backend/replication/logical/snapbuild.c @@ -125,6 +125,7 @@ #include <sys/stat.h> #include <unistd.h> +#include "access/genam.h" #include "access/heapam_xlog.h" #include "access/transam.h" #include "access/xact.h" @@ -154,6 +155,14 @@ static ResourceOwner SavedResourceOwnerDuringExport = NULL; static bool ExportInProgress = false; +/* + * If a backend is going to do logical decoding and the output plugin does + * not need to access shared catalogs, setting this variable to false can make + * the decoding startup faster. In particular, the backend will not need to + * wait for completion of already running transactions in other databases. + */ +bool accessSharedCatalogsInDecoding = true; + /* ->committed and ->catchange manipulation */ static void SnapBuildPurgeOlderTxn(SnapBuild *builder); @@ -170,7 +179,8 @@ static inline bool SnapBuildXidHasCatalogChanges(SnapBuild *builder, Transaction uint32 xinfo); /* xlog reading helper functions for SnapBuildProcessRunningXacts */ -static bool SnapBuildFindSnapshot(SnapBuild *builder, XLogRecPtr lsn, xl_running_xacts *running); +static bool SnapBuildFindSnapshot(SnapBuild *builder, XLogRecPtr lsn, + xl_running_xacts *running, bool db_specific); static void SnapBuildWaitSnapshot(xl_running_xacts *running, TransactionId cutoff); /* serialization functions */ @@ -1136,7 +1146,8 @@ SnapBuildXidHasCatalogChanges(SnapBuild *builder, TransactionId xid, * anymore. */ void -SnapBuildProcessRunningXacts(SnapBuild *builder, XLogRecPtr lsn, xl_running_xacts *running) +SnapBuildProcessRunningXacts(SnapBuild *builder, XLogRecPtr lsn, xl_running_xacts *running, + bool db_specific) { ReorderBufferTXN *txn; TransactionId xmin; @@ -1149,12 +1160,21 @@ SnapBuildProcessRunningXacts(SnapBuild *builder, XLogRecPtr lsn, xl_running_xact if (builder->state < SNAPBUILD_CONSISTENT) { /* returns false if there's no point in performing cleanup just yet */ - if (!SnapBuildFindSnapshot(builder, lsn, running)) + if (!SnapBuildFindSnapshot(builder, lsn, running, db_specific)) return; } else SnapBuildSerialize(builder, lsn); + /* + * If database specific transaction info was used during startup, the info + * for the whole cluster can make xmin go backwards. The code below + * probably does not expect that, let's wait with the cleanup for the next + * record. + */ + if (!NormalTransactionIdFollows(running->oldestRunningXid, builder->xmin)) + return; + /* * Update range of interesting xids based on the running xacts * information. We don't increase ->xmax using it, because once we are in @@ -1238,7 +1258,8 @@ SnapBuildProcessRunningXacts(SnapBuild *builder, XLogRecPtr lsn, xl_running_xact * using the xl_running_xacts record. */ static bool -SnapBuildFindSnapshot(SnapBuild *builder, XLogRecPtr lsn, xl_running_xacts *running) +SnapBuildFindSnapshot(SnapBuild *builder, XLogRecPtr lsn, xl_running_xacts *running, + bool db_specific) { /* --- * Build catalog decoding snapshot incrementally using information about @@ -1265,6 +1286,25 @@ SnapBuildFindSnapshot(SnapBuild *builder, XLogRecPtr lsn, xl_running_xacts *runn * --- */ + if (db_specific) + { + /* + * If we must only keep track of transactions running in the current + * database, we need transaction info from exactly that database. + */ + if (running->dbid != MyDatabaseId) + { + LogStandbySnapshot(MyDatabaseId); + return false; + } + + /* + * We'd better be able to check during scan if the plugin does not + * lie. + */ + accessSharedCatalogsInDecoding = false; + } + /* * xl_running_xacts record is older than what we can use, we might not * have all necessary catalog rows anymore. @@ -1465,7 +1505,11 @@ SnapBuildWaitSnapshot(xl_running_xacts *running, TransactionId cutoff) */ if (!RecoveryInProgress()) { - LogStandbySnapshot(); + /* + * If the last transaction info was about specific database, so needs + * to be the next one - at least until we're in the CONSISTENT state. + */ + LogStandbySnapshot(running->dbid); } } diff --git a/src/backend/replication/slot.c b/src/backend/replication/slot.c index a9092fc2382..9533515a63b 100644 --- a/src/backend/replication/slot.c +++ b/src/backend/replication/slot.c @@ -1762,7 +1762,7 @@ ReplicationSlotReserveWal(void) XLogRecPtr flushptr; /* make sure we have enough information to start */ - flushptr = LogStandbySnapshot(); + flushptr = LogStandbySnapshot(InvalidOid); /* and make sure it's fsynced to disk */ XLogFlush(flushptr); diff --git a/src/backend/storage/ipc/procarray.c b/src/backend/storage/ipc/procarray.c index cc207cb56e3..92ed34128e5 100644 --- a/src/backend/storage/ipc/procarray.c +++ b/src/backend/storage/ipc/procarray.c @@ -2631,9 +2631,11 @@ ProcArrayInstallRestoredXmin(TransactionId xmin, PGPROC *proc) * * Note that if any transaction has overflowed its cached subtransactions * then there is no real need include any subtransactions. + * + * If 'dbid' is valid, only gather transactions running in that database. */ RunningTransactions -GetRunningTransactionData(void) +GetRunningTransactionData(Oid dbid) { /* result workspace */ static RunningTransactionsData CurrentRunningXactsData; @@ -2708,6 +2710,18 @@ GetRunningTransactionData(void) if (!TransactionIdIsValid(xid)) continue; + /* + * Filter by database OID if requested. + */ + if (OidIsValid(dbid)) + { + int pgprocno = arrayP->pgprocnos[index]; + PGPROC *proc = &allProcs[pgprocno]; + + if (proc->databaseId != dbid) + continue; + } + /* * Be careful not to exclude any xids before calculating the values of * oldestRunningXid and suboverflowed, since these are used to clean @@ -2758,6 +2772,12 @@ GetRunningTransactionData(void) PGPROC *proc = &allProcs[pgprocno]; int nsubxids; + /* + * Filter by database OID if requested. + */ + if (OidIsValid(dbid) && proc->databaseId != dbid) + continue; + /* * Save subtransaction XIDs. Other backends can't add or remove * entries while we're holding XidGenLock. @@ -2791,6 +2811,7 @@ GetRunningTransactionData(void) * increases if slots do. */ + CurrentRunningXacts->dbid = dbid; CurrentRunningXacts->xcnt = count - subcount; CurrentRunningXacts->subxcnt = subcount; CurrentRunningXacts->subxid_status = suboverflowed ? SUBXIDS_IN_SUBTRANS : SUBXIDS_IN_ARRAY; diff --git a/src/backend/storage/ipc/standby.c b/src/backend/storage/ipc/standby.c index de9092fdf5b..c653ea742bc 100644 --- a/src/backend/storage/ipc/standby.c +++ b/src/backend/storage/ipc/standby.c @@ -1188,6 +1188,14 @@ standby_redo(XLogReaderState *record) xl_running_xacts *xlrec = (xl_running_xacts *) XLogRecGetData(record); RunningTransactionsData running; + /* + * Records issued for specific database are not suitable for physical + * replication because that affects the whole cluster. In particular, + * the list of XID is probably incomplete here. + */ + if (OidIsValid(xlrec->dbid)) + return; + running.xcnt = xlrec->xcnt; running.subxcnt = xlrec->subxcnt; running.subxid_status = xlrec->subxid_overflow ? SUBXIDS_MISSING : SUBXIDS_IN_ARRAY; @@ -1277,11 +1285,12 @@ standby_redo(XLogReaderState *record) * as there's no independent knob to just enable logical decoding. For * details of how this is used, check snapbuild.c's introductory comment. * + * If 'dbid' is valid, only gather transactions running in that database. * * Returns the RecPtr of the last inserted record. */ XLogRecPtr -LogStandbySnapshot(void) +LogStandbySnapshot(Oid dbid) { XLogRecPtr recptr; RunningTransactions running; @@ -1314,7 +1323,7 @@ LogStandbySnapshot(void) * Log details of all in-progress transactions. This should be the last * record we write, because standby will open up when it sees this. */ - running = GetRunningTransactionData(); + running = GetRunningTransactionData(dbid); /* * GetRunningTransactionData() acquired ProcArrayLock, we must release it. @@ -1358,6 +1367,7 @@ LogCurrentRunningXacts(RunningTransactions CurrRunningXacts) xl_running_xacts xlrec; XLogRecPtr recptr; + xlrec.dbid = CurrRunningXacts->dbid; xlrec.xcnt = CurrRunningXacts->xcnt; xlrec.subxcnt = CurrRunningXacts->subxcnt; xlrec.subxid_overflow = (CurrRunningXacts->subxid_status != SUBXIDS_IN_ARRAY); diff --git a/src/include/access/genam.h b/src/include/access/genam.h index b69320a7fc8..c9a52277be1 100644 --- a/src/include/access/genam.h +++ b/src/include/access/genam.h @@ -136,6 +136,13 @@ typedef struct IndexOrderByDistance bool isnull; } IndexOrderByDistance; + +/* + * Keep track of whether logical decoding in this backend promised not to + * access shared catalogs, as a safety check. Somewhat misplaced, but ... + */ +extern bool accessSharedCatalogsInDecoding; + /* * generalized index_ interface routines (in indexam.c) */ diff --git a/src/include/access/xlog_internal.h b/src/include/access/xlog_internal.h index 10c18d39ff8..13ae3ad4fbb 100644 --- a/src/include/access/xlog_internal.h +++ b/src/include/access/xlog_internal.h @@ -32,7 +32,7 @@ /* * Each page of XLOG file has a header like this: */ -#define XLOG_PAGE_MAGIC 0xD11E /* can be used as WAL version indicator */ +#define XLOG_PAGE_MAGIC 0xD11F /* can be used as WAL version indicator */ typedef struct XLogPageHeaderData { diff --git a/src/include/replication/output_plugin.h b/src/include/replication/output_plugin.h index 842fcde67f9..917f3cff232 100644 --- a/src/include/replication/output_plugin.h +++ b/src/include/replication/output_plugin.h @@ -27,6 +27,7 @@ typedef struct OutputPluginOptions { OutputPluginOutputType output_type; bool receive_rewrites; + bool need_shared_catalogs; } OutputPluginOptions; /* diff --git a/src/include/replication/snapbuild.h b/src/include/replication/snapbuild.h index a22a83a2f23..d02530a912a 100644 --- a/src/include/replication/snapbuild.h +++ b/src/include/replication/snapbuild.h @@ -92,7 +92,8 @@ extern void SnapBuildProcessNewCid(SnapBuild *builder, TransactionId xid, XLogRecPtr lsn, xl_heap_new_cid *xlrec); extern void SnapBuildProcessRunningXacts(SnapBuild *builder, XLogRecPtr lsn, - xl_running_xacts *running); + xl_running_xacts *running, + bool db_specific); extern void SnapBuildSerializationPoint(SnapBuild *builder, XLogRecPtr lsn); extern bool SnapBuildSnapshotExists(XLogRecPtr lsn); diff --git a/src/include/storage/procarray.h b/src/include/storage/procarray.h index abdf021e66e..377b3060b9f 100644 --- a/src/include/storage/procarray.h +++ b/src/include/storage/procarray.h @@ -49,7 +49,7 @@ extern bool ProcArrayInstallImportedXmin(TransactionId xmin, VirtualTransactionId *sourcevxid); extern bool ProcArrayInstallRestoredXmin(TransactionId xmin, PGPROC *proc); -extern RunningTransactions GetRunningTransactionData(void); +extern RunningTransactions GetRunningTransactionData(Oid dbid); extern bool TransactionIdIsInProgress(TransactionId xid); extern TransactionId GetOldestNonRemovableTransactionId(Relation rel); diff --git a/src/include/storage/standby.h b/src/include/storage/standby.h index 6a314c693cd..8715c08e94f 100644 --- a/src/include/storage/standby.h +++ b/src/include/storage/standby.h @@ -126,6 +126,7 @@ typedef enum typedef struct RunningTransactionsData { + Oid dbid; /* only track xacts in this database */ int xcnt; /* # of xact ids in xids[] */ int subxcnt; /* # of subxact ids in xids[] */ subxids_array_status subxid_status; @@ -143,7 +144,7 @@ typedef RunningTransactionsData *RunningTransactions; extern void LogAccessExclusiveLock(Oid dbOid, Oid relOid); extern void LogAccessExclusiveLockPrepare(void); -extern XLogRecPtr LogStandbySnapshot(void); +extern XLogRecPtr LogStandbySnapshot(Oid dbid); extern void LogStandbyInvalidations(int nmsgs, SharedInvalidationMessage *msgs, bool relcacheInitFileInval); diff --git a/src/include/storage/standbydefs.h b/src/include/storage/standbydefs.h index 231d251fd51..e75b7078766 100644 --- a/src/include/storage/standbydefs.h +++ b/src/include/storage/standbydefs.h @@ -46,6 +46,7 @@ typedef struct xl_standby_locks */ typedef struct xl_running_xacts { + Oid dbid; /* only track xacts in this database */ int xcnt; /* # of xact ids in xids[] */ int subxcnt; /* # of subxact ids in xids[] */ bool subxid_overflow; /* snapshot overflowed, subxids missing */ -- 2.47.3 --cdhh4t7ukb6tnjoq Content-Type: text/x-diff; charset=utf-8 Content-Disposition: attachment; filename="v54-0002-Rename-cluster.c-h-repack.c-h.patch" ^ permalink raw reply [nested|flat] 56+ messages in thread
end of thread, other threads:[~2026-04-05 07:51 UTC | newest] Thread overview: 56+ messages (download: mbox mbox.gz follow: Atom feed) -- links below jump to the message on this page -- 2018-10-16 06:48 [PATCH 2/4] Syscache usage tracking feature. Kyotaro Horiguchi <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v3 01/11] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v3 01/11] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v2 01/11] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v7 01/16] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v2 01/11] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v6 01/15] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v5 01/14] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2023-09-24 20:49 [PATCH v4 01/12] Change section heading to better reflect saving a result in variable(s) Karl O. Pinc <[email protected]> 2026-04-05 07:51 [PATCH v54 1/5] Introduce an option to make logical replication database specific. Antonin Houska <[email protected]>
This inbox is served by agora; see mirroring instructions for how to clone and mirror all data and code used for this inbox