mirror of
https://github.com/postgres/postgres.git
synced 2025-06-30 21:42:05 +03:00
Add SETTINGS option to EXPLAIN, to print modified settings.
Query planning is affected by a number of configuration options, and it may be crucial to know which of those options were set to non-default values. With this patch you can say EXPLAIN (SETTINGS ON) to include that information in the query plan. Only options affecting planning, with values different from the built-in default are printed. This patch also adds auto_explain.log_settings option, providing the same capability in auto_explain module. Author: Tomas Vondra Reviewed-by: Rafia Sabih, John Naylor Discussion: https://postgr.es/m/e1791b4c-df9c-be02-edc5-7c8874944be0@2ndquadrant.com
This commit is contained in:
@ -29,6 +29,7 @@
|
||||
#include "storage/bufmgr.h"
|
||||
#include "tcop/tcopprot.h"
|
||||
#include "utils/builtins.h"
|
||||
#include "utils/guc_tables.h"
|
||||
#include "utils/json.h"
|
||||
#include "utils/lsyscache.h"
|
||||
#include "utils/rel.h"
|
||||
@ -162,6 +163,8 @@ ExplainQuery(ParseState *pstate, ExplainStmt *stmt, const char *queryString,
|
||||
es->costs = defGetBoolean(opt);
|
||||
else if (strcmp(opt->defname, "buffers") == 0)
|
||||
es->buffers = defGetBoolean(opt);
|
||||
else if (strcmp(opt->defname, "settings") == 0)
|
||||
es->settings = defGetBoolean(opt);
|
||||
else if (strcmp(opt->defname, "timing") == 0)
|
||||
{
|
||||
timing_set = true;
|
||||
@ -596,6 +599,73 @@ ExplainOnePlan(PlannedStmt *plannedstmt, IntoClause *into, ExplainState *es,
|
||||
ExplainCloseGroup("Query", NULL, true, es);
|
||||
}
|
||||
|
||||
/*
|
||||
* ExplainPrintSettings -
|
||||
* Print summary of modified settings affecting query planning.
|
||||
*/
|
||||
static void
|
||||
ExplainPrintSettings(ExplainState *es)
|
||||
{
|
||||
int num;
|
||||
struct config_generic **gucs;
|
||||
|
||||
/* bail out if information about settings not requested */
|
||||
if (!es->settings)
|
||||
return;
|
||||
|
||||
/* request an array of relevant settings */
|
||||
gucs = get_explain_guc_options(&num);
|
||||
|
||||
/* also bail out of there are no options */
|
||||
if (!num)
|
||||
return;
|
||||
|
||||
if (es->format != EXPLAIN_FORMAT_TEXT)
|
||||
{
|
||||
int i;
|
||||
|
||||
ExplainOpenGroup("Settings", "Settings", true, es);
|
||||
|
||||
for (i = 0; i < num; i++)
|
||||
{
|
||||
char *setting;
|
||||
struct config_generic *conf = gucs[i];
|
||||
|
||||
setting = GetConfigOptionByName(conf->name, NULL, true);
|
||||
|
||||
ExplainPropertyText(conf->name, setting, es);
|
||||
}
|
||||
|
||||
ExplainCloseGroup("Settings", "Settings", true, es);
|
||||
}
|
||||
else
|
||||
{
|
||||
int i;
|
||||
StringInfoData str;
|
||||
|
||||
initStringInfo(&str);
|
||||
|
||||
for (i = 0; i < num; i++)
|
||||
{
|
||||
char *setting;
|
||||
struct config_generic *conf = gucs[i];
|
||||
|
||||
if (i > 0)
|
||||
appendStringInfoString(&str, ", ");
|
||||
|
||||
setting = GetConfigOptionByName(conf->name, NULL, true);
|
||||
|
||||
if (setting)
|
||||
appendStringInfo(&str, "%s = '%s'", conf->name, setting);
|
||||
else
|
||||
appendStringInfo(&str, "%s = NULL", conf->name);
|
||||
}
|
||||
|
||||
if (num > 0)
|
||||
ExplainPropertyText("Settings", str.data, es);
|
||||
}
|
||||
}
|
||||
|
||||
/*
|
||||
* ExplainPrintPlan -
|
||||
* convert a QueryDesc's plan tree to text and append it to es->str
|
||||
@ -633,6 +703,12 @@ ExplainPrintPlan(ExplainState *es, QueryDesc *queryDesc)
|
||||
if (IsA(ps, GatherState) &&((Gather *) ps->plan)->invisible)
|
||||
ps = outerPlanState(ps);
|
||||
ExplainNode(ps, NIL, NULL, NULL, es);
|
||||
|
||||
/*
|
||||
* If requested, include information about GUC parameters with values
|
||||
* that don't match the built-in defaults.
|
||||
*/
|
||||
ExplainPrintSettings(es);
|
||||
}
|
||||
|
||||
/*
|
||||
|
Reference in New Issue
Block a user