mirror of
https://github.com/postgres/postgres.git
synced 2025-04-27 22:56:53 +03:00
Add 'unit' parameter to ExplainProperty{Integer,Float}.
This allows to deduplicate some existing code, but mainly avoids some duplication in upcoming commits. In passing, fix variable names indicating wrong unit (seconds instead of ms). Author: Andres Freund Discussion: https://postgr.es/m/20180314002740.cah3mdsonz5mxney@alap3.anarazel.de
This commit is contained in:
parent
f3e4b95edb
commit
7a50bb690b
@ -622,7 +622,7 @@ fileExplainForeignScan(ForeignScanState *node, ExplainState *es)
|
|||||||
|
|
||||||
if (!is_program &&
|
if (!is_program &&
|
||||||
stat(filename, &stat_buf) == 0)
|
stat(filename, &stat_buf) == 0)
|
||||||
ExplainPropertyInteger("Foreign File Size",
|
ExplainPropertyInteger("Foreign File Size", "b",
|
||||||
(int64) stat_buf.st_size, es);
|
(int64) stat_buf.st_size, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -123,8 +123,8 @@ static void ExplainSubPlans(List *plans, List *ancestors,
|
|||||||
const char *relationship, ExplainState *es);
|
const char *relationship, ExplainState *es);
|
||||||
static void ExplainCustomChildren(CustomScanState *css,
|
static void ExplainCustomChildren(CustomScanState *css,
|
||||||
List *ancestors, ExplainState *es);
|
List *ancestors, ExplainState *es);
|
||||||
static void ExplainProperty(const char *qlabel, const char *value,
|
static void ExplainProperty(const char *qlabel, const char *unit,
|
||||||
bool numeric, ExplainState *es);
|
const char *value, bool numeric, ExplainState *es);
|
||||||
static void ExplainDummyGroup(const char *objtype, const char *labelname,
|
static void ExplainDummyGroup(const char *objtype, const char *labelname,
|
||||||
ExplainState *es);
|
ExplainState *es);
|
||||||
static void ExplainXMLTag(const char *tagname, int flags, ExplainState *es);
|
static void ExplainXMLTag(const char *tagname, int flags, ExplainState *es);
|
||||||
@ -549,11 +549,7 @@ ExplainOnePlan(PlannedStmt *plannedstmt, IntoClause *into, ExplainState *es,
|
|||||||
{
|
{
|
||||||
double plantime = INSTR_TIME_GET_DOUBLE(*planduration);
|
double plantime = INSTR_TIME_GET_DOUBLE(*planduration);
|
||||||
|
|
||||||
if (es->format == EXPLAIN_FORMAT_TEXT)
|
ExplainPropertyFloat("Planning Time", "ms", 1000.0 * plantime, 3, es);
|
||||||
appendStringInfo(es->str, "Planning time: %.3f ms\n",
|
|
||||||
1000.0 * plantime);
|
|
||||||
else
|
|
||||||
ExplainPropertyFloat("Planning Time", 1000.0 * plantime, 3, es);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/* Print info about runtime of triggers */
|
/* Print info about runtime of triggers */
|
||||||
@ -585,14 +581,8 @@ ExplainOnePlan(PlannedStmt *plannedstmt, IntoClause *into, ExplainState *es,
|
|||||||
* the output). By default, ANALYZE sets SUMMARY to true.
|
* the output). By default, ANALYZE sets SUMMARY to true.
|
||||||
*/
|
*/
|
||||||
if (es->summary && es->analyze)
|
if (es->summary && es->analyze)
|
||||||
{
|
ExplainPropertyFloat("Execution Time", "ms", 1000.0 * totaltime, 3,
|
||||||
if (es->format == EXPLAIN_FORMAT_TEXT)
|
es);
|
||||||
appendStringInfo(es->str, "Execution time: %.3f ms\n",
|
|
||||||
1000.0 * totaltime);
|
|
||||||
else
|
|
||||||
ExplainPropertyFloat("Execution Time", 1000.0 * totaltime,
|
|
||||||
3, es);
|
|
||||||
}
|
|
||||||
|
|
||||||
ExplainCloseGroup("Query", NULL, true, es);
|
ExplainCloseGroup("Query", NULL, true, es);
|
||||||
}
|
}
|
||||||
@ -764,8 +754,9 @@ report_triggers(ResultRelInfo *rInfo, bool show_relname, ExplainState *es)
|
|||||||
ExplainPropertyText("Constraint Name", conname, es);
|
ExplainPropertyText("Constraint Name", conname, es);
|
||||||
ExplainPropertyText("Relation", relname, es);
|
ExplainPropertyText("Relation", relname, es);
|
||||||
if (es->timing)
|
if (es->timing)
|
||||||
ExplainPropertyFloat("Time", 1000.0 * instr->total, 3, es);
|
ExplainPropertyFloat("Time", "ms", 1000.0 * instr->total, 3,
|
||||||
ExplainPropertyFloat("Calls", instr->ntuples, 0, es);
|
es);
|
||||||
|
ExplainPropertyFloat("Calls", NULL, instr->ntuples, 0, es);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (conname)
|
if (conname)
|
||||||
@ -1280,10 +1271,14 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
ExplainPropertyFloat("Startup Cost", plan->startup_cost, 2, es);
|
ExplainPropertyFloat("Startup Cost", NULL, plan->startup_cost,
|
||||||
ExplainPropertyFloat("Total Cost", plan->total_cost, 2, es);
|
2, es);
|
||||||
ExplainPropertyFloat("Plan Rows", plan->plan_rows, 0, es);
|
ExplainPropertyFloat("Total Cost", NULL, plan->total_cost,
|
||||||
ExplainPropertyInteger("Plan Width", plan->plan_width, es);
|
2, es);
|
||||||
|
ExplainPropertyFloat("Plan Rows", NULL, plan->plan_rows,
|
||||||
|
0, es);
|
||||||
|
ExplainPropertyInteger("Plan Width", NULL, plan->plan_width,
|
||||||
|
es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1304,8 +1299,8 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
planstate->instrument && planstate->instrument->nloops > 0)
|
planstate->instrument && planstate->instrument->nloops > 0)
|
||||||
{
|
{
|
||||||
double nloops = planstate->instrument->nloops;
|
double nloops = planstate->instrument->nloops;
|
||||||
double startup_sec = 1000.0 * planstate->instrument->startup / nloops;
|
double startup_ms = 1000.0 * planstate->instrument->startup / nloops;
|
||||||
double total_sec = 1000.0 * planstate->instrument->total / nloops;
|
double total_ms = 1000.0 * planstate->instrument->total / nloops;
|
||||||
double rows = planstate->instrument->ntuples / nloops;
|
double rows = planstate->instrument->ntuples / nloops;
|
||||||
|
|
||||||
if (es->format == EXPLAIN_FORMAT_TEXT)
|
if (es->format == EXPLAIN_FORMAT_TEXT)
|
||||||
@ -1313,7 +1308,7 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
if (es->timing)
|
if (es->timing)
|
||||||
appendStringInfo(es->str,
|
appendStringInfo(es->str,
|
||||||
" (actual time=%.3f..%.3f rows=%.0f loops=%.0f)",
|
" (actual time=%.3f..%.3f rows=%.0f loops=%.0f)",
|
||||||
startup_sec, total_sec, rows, nloops);
|
startup_ms, total_ms, rows, nloops);
|
||||||
else
|
else
|
||||||
appendStringInfo(es->str,
|
appendStringInfo(es->str,
|
||||||
" (actual rows=%.0f loops=%.0f)",
|
" (actual rows=%.0f loops=%.0f)",
|
||||||
@ -1323,11 +1318,13 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
{
|
{
|
||||||
if (es->timing)
|
if (es->timing)
|
||||||
{
|
{
|
||||||
ExplainPropertyFloat("Actual Startup Time", startup_sec, 3, es);
|
ExplainPropertyFloat("Actual Startup Time", "s", startup_ms,
|
||||||
ExplainPropertyFloat("Actual Total Time", total_sec, 3, es);
|
3, es);
|
||||||
|
ExplainPropertyFloat("Actual Total Time", "s", total_ms,
|
||||||
|
3, es);
|
||||||
}
|
}
|
||||||
ExplainPropertyFloat("Actual Rows", rows, 0, es);
|
ExplainPropertyFloat("Actual Rows", NULL, rows, 0, es);
|
||||||
ExplainPropertyFloat("Actual Loops", nloops, 0, es);
|
ExplainPropertyFloat("Actual Loops", NULL, nloops, 0, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (es->analyze)
|
else if (es->analyze)
|
||||||
@ -1338,11 +1335,11 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
{
|
{
|
||||||
if (es->timing)
|
if (es->timing)
|
||||||
{
|
{
|
||||||
ExplainPropertyFloat("Actual Startup Time", 0.0, 3, es);
|
ExplainPropertyFloat("Actual Startup Time", "ms", 0.0, 3, es);
|
||||||
ExplainPropertyFloat("Actual Total Time", 0.0, 3, es);
|
ExplainPropertyFloat("Actual Total Time", "ms", 0.0, 3, es);
|
||||||
}
|
}
|
||||||
ExplainPropertyFloat("Actual Rows", 0.0, 0, es);
|
ExplainPropertyFloat("Actual Rows", NULL, 0.0, 0, es);
|
||||||
ExplainPropertyFloat("Actual Loops", 0.0, 0, es);
|
ExplainPropertyFloat("Actual Loops", NULL, 0.0, 0, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1400,9 +1397,12 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
show_instrumentation_count("Rows Removed by Filter", 1,
|
show_instrumentation_count("Rows Removed by Filter", 1,
|
||||||
planstate, es);
|
planstate, es);
|
||||||
if (es->analyze)
|
if (es->analyze)
|
||||||
ExplainPropertyInteger("Heap Fetches",
|
{
|
||||||
((IndexOnlyScanState *) planstate)->ioss_HeapFetches,
|
long heapFetches =
|
||||||
es);
|
((IndexOnlyScanState *) planstate)->ioss_HeapFetches;
|
||||||
|
|
||||||
|
ExplainPropertyInteger("Heap Fetches", NULL, heapFetches, es);
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
case T_BitmapIndexScan:
|
case T_BitmapIndexScan:
|
||||||
show_scan_qual(((BitmapIndexScan *) plan)->indexqualorig,
|
show_scan_qual(((BitmapIndexScan *) plan)->indexqualorig,
|
||||||
@ -1444,7 +1444,7 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
if (plan->qual)
|
if (plan->qual)
|
||||||
show_instrumentation_count("Rows Removed by Filter", 1,
|
show_instrumentation_count("Rows Removed by Filter", 1,
|
||||||
planstate, es);
|
planstate, es);
|
||||||
ExplainPropertyInteger("Workers Planned",
|
ExplainPropertyInteger("Workers Planned", NULL,
|
||||||
gather->num_workers, es);
|
gather->num_workers, es);
|
||||||
|
|
||||||
/* Show params evaluated at gather node */
|
/* Show params evaluated at gather node */
|
||||||
@ -1456,7 +1456,7 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
int nworkers;
|
int nworkers;
|
||||||
|
|
||||||
nworkers = ((GatherState *) planstate)->nworkers_launched;
|
nworkers = ((GatherState *) planstate)->nworkers_launched;
|
||||||
ExplainPropertyInteger("Workers Launched",
|
ExplainPropertyInteger("Workers Launched", NULL,
|
||||||
nworkers, es);
|
nworkers, es);
|
||||||
}
|
}
|
||||||
if (gather->single_copy || es->format != EXPLAIN_FORMAT_TEXT)
|
if (gather->single_copy || es->format != EXPLAIN_FORMAT_TEXT)
|
||||||
@ -1471,7 +1471,7 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
if (plan->qual)
|
if (plan->qual)
|
||||||
show_instrumentation_count("Rows Removed by Filter", 1,
|
show_instrumentation_count("Rows Removed by Filter", 1,
|
||||||
planstate, es);
|
planstate, es);
|
||||||
ExplainPropertyInteger("Workers Planned",
|
ExplainPropertyInteger("Workers Planned", NULL,
|
||||||
gm->num_workers, es);
|
gm->num_workers, es);
|
||||||
|
|
||||||
/* Show params evaluated at gather-merge node */
|
/* Show params evaluated at gather-merge node */
|
||||||
@ -1483,7 +1483,7 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
int nworkers;
|
int nworkers;
|
||||||
|
|
||||||
nworkers = ((GatherMergeState *) planstate)->nworkers_launched;
|
nworkers = ((GatherMergeState *) planstate)->nworkers_launched;
|
||||||
ExplainPropertyInteger("Workers Launched",
|
ExplainPropertyInteger("Workers Launched", NULL,
|
||||||
nworkers, es);
|
nworkers, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1653,14 +1653,14 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
{
|
{
|
||||||
Instrumentation *instrument = &w->instrument[n];
|
Instrumentation *instrument = &w->instrument[n];
|
||||||
double nloops = instrument->nloops;
|
double nloops = instrument->nloops;
|
||||||
double startup_sec;
|
double startup_ms;
|
||||||
double total_sec;
|
double total_ms;
|
||||||
double rows;
|
double rows;
|
||||||
|
|
||||||
if (nloops <= 0)
|
if (nloops <= 0)
|
||||||
continue;
|
continue;
|
||||||
startup_sec = 1000.0 * instrument->startup / nloops;
|
startup_ms = 1000.0 * instrument->startup / nloops;
|
||||||
total_sec = 1000.0 * instrument->total / nloops;
|
total_ms = 1000.0 * instrument->total / nloops;
|
||||||
rows = instrument->ntuples / nloops;
|
rows = instrument->ntuples / nloops;
|
||||||
|
|
||||||
if (es->format == EXPLAIN_FORMAT_TEXT)
|
if (es->format == EXPLAIN_FORMAT_TEXT)
|
||||||
@ -1670,7 +1670,7 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
if (es->timing)
|
if (es->timing)
|
||||||
appendStringInfo(es->str,
|
appendStringInfo(es->str,
|
||||||
"actual time=%.3f..%.3f rows=%.0f loops=%.0f\n",
|
"actual time=%.3f..%.3f rows=%.0f loops=%.0f\n",
|
||||||
startup_sec, total_sec, rows, nloops);
|
startup_ms, total_ms, rows, nloops);
|
||||||
else
|
else
|
||||||
appendStringInfo(es->str,
|
appendStringInfo(es->str,
|
||||||
"actual rows=%.0f loops=%.0f\n",
|
"actual rows=%.0f loops=%.0f\n",
|
||||||
@ -1688,15 +1688,17 @@ ExplainNode(PlanState *planstate, List *ancestors,
|
|||||||
opened_group = true;
|
opened_group = true;
|
||||||
}
|
}
|
||||||
ExplainOpenGroup("Worker", NULL, true, es);
|
ExplainOpenGroup("Worker", NULL, true, es);
|
||||||
ExplainPropertyInteger("Worker Number", n, es);
|
ExplainPropertyInteger("Worker Number", NULL, n, es);
|
||||||
|
|
||||||
if (es->timing)
|
if (es->timing)
|
||||||
{
|
{
|
||||||
ExplainPropertyFloat("Actual Startup Time", startup_sec, 3, es);
|
ExplainPropertyFloat("Actual Startup Time", "ms",
|
||||||
ExplainPropertyFloat("Actual Total Time", total_sec, 3, es);
|
startup_ms, 3, es);
|
||||||
|
ExplainPropertyFloat("Actual Total Time", "ms",
|
||||||
|
total_ms, 3, es);
|
||||||
}
|
}
|
||||||
ExplainPropertyFloat("Actual Rows", rows, 0, es);
|
ExplainPropertyFloat("Actual Rows", NULL, rows, 0, es);
|
||||||
ExplainPropertyFloat("Actual Loops", nloops, 0, es);
|
ExplainPropertyFloat("Actual Loops", NULL, nloops, 0, es);
|
||||||
|
|
||||||
if (es->buffers)
|
if (es->buffers)
|
||||||
show_buffer_usage(es, &instrument->bufusage);
|
show_buffer_usage(es, &instrument->bufusage);
|
||||||
@ -2326,7 +2328,7 @@ show_sort_info(SortState *sortstate, ExplainState *es)
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
ExplainPropertyText("Sort Method", sortMethod, es);
|
ExplainPropertyText("Sort Method", sortMethod, es);
|
||||||
ExplainPropertyInteger("Sort Space Used", spaceUsed, es);
|
ExplainPropertyInteger("Sort Space Used", "kB", spaceUsed, es);
|
||||||
ExplainPropertyText("Sort Space Type", spaceType, es);
|
ExplainPropertyText("Sort Space Type", spaceType, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -2365,9 +2367,9 @@ show_sort_info(SortState *sortstate, ExplainState *es)
|
|||||||
opened_group = true;
|
opened_group = true;
|
||||||
}
|
}
|
||||||
ExplainOpenGroup("Worker", NULL, true, es);
|
ExplainOpenGroup("Worker", NULL, true, es);
|
||||||
ExplainPropertyInteger("Worker Number", n, es);
|
ExplainPropertyInteger("Worker Number", NULL, n, es);
|
||||||
ExplainPropertyText("Sort Method", sortMethod, es);
|
ExplainPropertyText("Sort Method", sortMethod, es);
|
||||||
ExplainPropertyInteger("Sort Space Used", spaceUsed, es);
|
ExplainPropertyInteger("Sort Space Used", "kB", spaceUsed, es);
|
||||||
ExplainPropertyText("Sort Space Type", spaceType, es);
|
ExplainPropertyText("Sort Space Type", spaceType, es);
|
||||||
ExplainCloseGroup("Worker", NULL, true, es);
|
ExplainCloseGroup("Worker", NULL, true, es);
|
||||||
}
|
}
|
||||||
@ -2446,13 +2448,16 @@ show_hash_info(HashState *hashstate, ExplainState *es)
|
|||||||
|
|
||||||
if (es->format != EXPLAIN_FORMAT_TEXT)
|
if (es->format != EXPLAIN_FORMAT_TEXT)
|
||||||
{
|
{
|
||||||
ExplainPropertyInteger("Hash Buckets", hinstrument.nbuckets, es);
|
ExplainPropertyInteger("Hash Buckets", NULL,
|
||||||
ExplainPropertyInteger("Original Hash Buckets",
|
hinstrument.nbuckets, es);
|
||||||
|
ExplainPropertyInteger("Original Hash Buckets", NULL,
|
||||||
hinstrument.nbuckets_original, es);
|
hinstrument.nbuckets_original, es);
|
||||||
ExplainPropertyInteger("Hash Batches", hinstrument.nbatch, es);
|
ExplainPropertyInteger("Hash Batches", NULL,
|
||||||
ExplainPropertyInteger("Original Hash Batches",
|
hinstrument.nbatch, es);
|
||||||
|
ExplainPropertyInteger("Original Hash Batches", NULL,
|
||||||
hinstrument.nbatch_original, es);
|
hinstrument.nbatch_original, es);
|
||||||
ExplainPropertyInteger("Peak Memory Usage", spacePeakKb, es);
|
ExplainPropertyInteger("Peak Memory Usage", "kB",
|
||||||
|
spacePeakKb, es);
|
||||||
}
|
}
|
||||||
else if (hinstrument.nbatch_original != hinstrument.nbatch ||
|
else if (hinstrument.nbatch_original != hinstrument.nbatch ||
|
||||||
hinstrument.nbuckets_original != hinstrument.nbuckets)
|
hinstrument.nbuckets_original != hinstrument.nbuckets)
|
||||||
@ -2485,9 +2490,9 @@ show_tidbitmap_info(BitmapHeapScanState *planstate, ExplainState *es)
|
|||||||
{
|
{
|
||||||
if (es->format != EXPLAIN_FORMAT_TEXT)
|
if (es->format != EXPLAIN_FORMAT_TEXT)
|
||||||
{
|
{
|
||||||
ExplainPropertyInteger("Exact Heap Blocks",
|
ExplainPropertyInteger("Exact Heap Blocks", NULL,
|
||||||
planstate->exact_pages, es);
|
planstate->exact_pages, es);
|
||||||
ExplainPropertyInteger("Lossy Heap Blocks",
|
ExplainPropertyInteger("Lossy Heap Blocks", NULL,
|
||||||
planstate->lossy_pages, es);
|
planstate->lossy_pages, es);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -2530,9 +2535,9 @@ show_instrumentation_count(const char *qlabel, int which,
|
|||||||
if (nfiltered > 0 || es->format != EXPLAIN_FORMAT_TEXT)
|
if (nfiltered > 0 || es->format != EXPLAIN_FORMAT_TEXT)
|
||||||
{
|
{
|
||||||
if (nloops > 0)
|
if (nloops > 0)
|
||||||
ExplainPropertyFloat(qlabel, nfiltered / nloops, 0, es);
|
ExplainPropertyFloat(qlabel, NULL, nfiltered / nloops, 0, es);
|
||||||
else
|
else
|
||||||
ExplainPropertyFloat(qlabel, 0.0, 0, es);
|
ExplainPropertyFloat(qlabel, NULL, 0.0, 0, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2698,30 +2703,34 @@ show_buffer_usage(ExplainState *es, const BufferUsage *usage)
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
ExplainPropertyInteger("Shared Hit Blocks",
|
ExplainPropertyInteger("Shared Hit Blocks", NULL,
|
||||||
usage->shared_blks_hit, es);
|
usage->shared_blks_hit, es);
|
||||||
ExplainPropertyInteger("Shared Read Blocks",
|
ExplainPropertyInteger("Shared Read Blocks", NULL,
|
||||||
usage->shared_blks_read, es);
|
usage->shared_blks_read, es);
|
||||||
ExplainPropertyInteger("Shared Dirtied Blocks",
|
ExplainPropertyInteger("Shared Dirtied Blocks", NULL,
|
||||||
usage->shared_blks_dirtied, es);
|
usage->shared_blks_dirtied, es);
|
||||||
ExplainPropertyInteger("Shared Written Blocks",
|
ExplainPropertyInteger("Shared Written Blocks", NULL,
|
||||||
usage->shared_blks_written, es);
|
usage->shared_blks_written, es);
|
||||||
ExplainPropertyInteger("Local Hit Blocks",
|
ExplainPropertyInteger("Local Hit Blocks", NULL,
|
||||||
usage->local_blks_hit, es);
|
usage->local_blks_hit, es);
|
||||||
ExplainPropertyInteger("Local Read Blocks",
|
ExplainPropertyInteger("Local Read Blocks", NULL,
|
||||||
usage->local_blks_read, es);
|
usage->local_blks_read, es);
|
||||||
ExplainPropertyInteger("Local Dirtied Blocks",
|
ExplainPropertyInteger("Local Dirtied Blocks", NULL,
|
||||||
usage->local_blks_dirtied, es);
|
usage->local_blks_dirtied, es);
|
||||||
ExplainPropertyInteger("Local Written Blocks",
|
ExplainPropertyInteger("Local Written Blocks", NULL,
|
||||||
usage->local_blks_written, es);
|
usage->local_blks_written, es);
|
||||||
ExplainPropertyInteger("Temp Read Blocks",
|
ExplainPropertyInteger("Temp Read Blocks", NULL,
|
||||||
usage->temp_blks_read, es);
|
usage->temp_blks_read, es);
|
||||||
ExplainPropertyInteger("Temp Written Blocks",
|
ExplainPropertyInteger("Temp Written Blocks", NULL,
|
||||||
usage->temp_blks_written, es);
|
usage->temp_blks_written, es);
|
||||||
if (track_io_timing)
|
if (track_io_timing)
|
||||||
{
|
{
|
||||||
ExplainPropertyFloat("I/O Read Time", INSTR_TIME_GET_MILLISEC(usage->blk_read_time), 3, es);
|
ExplainPropertyFloat("I/O Read Time", "ms",
|
||||||
ExplainPropertyFloat("I/O Write Time", INSTR_TIME_GET_MILLISEC(usage->blk_write_time), 3, es);
|
INSTR_TIME_GET_MILLISEC(usage->blk_read_time),
|
||||||
|
3, es);
|
||||||
|
ExplainPropertyFloat("I/O Write Time", "ms",
|
||||||
|
INSTR_TIME_GET_MILLISEC(usage->blk_write_time),
|
||||||
|
3, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -3021,10 +3030,10 @@ show_modifytable_info(ModifyTableState *mtstate, List *ancestors,
|
|||||||
|
|
||||||
if (node->onConflictAction != ONCONFLICT_NONE)
|
if (node->onConflictAction != ONCONFLICT_NONE)
|
||||||
{
|
{
|
||||||
ExplainProperty("Conflict Resolution",
|
ExplainPropertyText("Conflict Resolution",
|
||||||
node->onConflictAction == ONCONFLICT_NOTHING ?
|
node->onConflictAction == ONCONFLICT_NOTHING ?
|
||||||
"NOTHING" : "UPDATE",
|
"NOTHING" : "UPDATE",
|
||||||
false, es);
|
es);
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Don't display arbiter indexes at all when DO NOTHING variant
|
* Don't display arbiter indexes at all when DO NOTHING variant
|
||||||
@ -3055,8 +3064,10 @@ show_modifytable_info(ModifyTableState *mtstate, List *ancestors,
|
|||||||
other_path = mtstate->ps.instrument->nfiltered2;
|
other_path = mtstate->ps.instrument->nfiltered2;
|
||||||
insert_path = total - other_path;
|
insert_path = total - other_path;
|
||||||
|
|
||||||
ExplainPropertyFloat("Tuples Inserted", insert_path, 0, es);
|
ExplainPropertyFloat("Tuples Inserted", NULL,
|
||||||
ExplainPropertyFloat("Conflicting Tuples", other_path, 0, es);
|
insert_path, 0, es);
|
||||||
|
ExplainPropertyFloat("Conflicting Tuples", NULL,
|
||||||
|
other_path, 0, es);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3259,17 +3270,22 @@ ExplainPropertyListNested(const char *qlabel, List *data, ExplainState *es)
|
|||||||
* If "numeric" is true, the value is a number (or other value that
|
* If "numeric" is true, the value is a number (or other value that
|
||||||
* doesn't need quoting in JSON).
|
* doesn't need quoting in JSON).
|
||||||
*
|
*
|
||||||
|
* If unit is is non-NULL the text format will display it after the value.
|
||||||
|
*
|
||||||
* This usually should not be invoked directly, but via one of the datatype
|
* This usually should not be invoked directly, but via one of the datatype
|
||||||
* specific routines ExplainPropertyText, ExplainPropertyInteger, etc.
|
* specific routines ExplainPropertyText, ExplainPropertyInteger, etc.
|
||||||
*/
|
*/
|
||||||
static void
|
static void
|
||||||
ExplainProperty(const char *qlabel, const char *value, bool numeric,
|
ExplainProperty(const char *qlabel, const char *unit, const char *value,
|
||||||
ExplainState *es)
|
bool numeric, ExplainState *es)
|
||||||
{
|
{
|
||||||
switch (es->format)
|
switch (es->format)
|
||||||
{
|
{
|
||||||
case EXPLAIN_FORMAT_TEXT:
|
case EXPLAIN_FORMAT_TEXT:
|
||||||
appendStringInfoSpaces(es->str, es->indent * 2);
|
appendStringInfoSpaces(es->str, es->indent * 2);
|
||||||
|
if (unit)
|
||||||
|
appendStringInfo(es->str, "%s: %s %s\n", qlabel, value, unit);
|
||||||
|
else
|
||||||
appendStringInfo(es->str, "%s: %s\n", qlabel, value);
|
appendStringInfo(es->str, "%s: %s\n", qlabel, value);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
@ -3315,19 +3331,20 @@ ExplainProperty(const char *qlabel, const char *value, bool numeric,
|
|||||||
void
|
void
|
||||||
ExplainPropertyText(const char *qlabel, const char *value, ExplainState *es)
|
ExplainPropertyText(const char *qlabel, const char *value, ExplainState *es)
|
||||||
{
|
{
|
||||||
ExplainProperty(qlabel, value, false, es);
|
ExplainProperty(qlabel, NULL, value, false, es);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
* Explain an integer-valued property.
|
* Explain an integer-valued property.
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
ExplainPropertyInteger(const char *qlabel, int64 value, ExplainState *es)
|
ExplainPropertyInteger(const char *qlabel, const char *unit, int64 value,
|
||||||
|
ExplainState *es)
|
||||||
{
|
{
|
||||||
char buf[32];
|
char buf[32];
|
||||||
|
|
||||||
snprintf(buf, sizeof(buf), INT64_FORMAT, value);
|
snprintf(buf, sizeof(buf), INT64_FORMAT, value);
|
||||||
ExplainProperty(qlabel, buf, true, es);
|
ExplainProperty(qlabel, unit, buf, true, es);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
@ -3335,13 +3352,13 @@ ExplainPropertyInteger(const char *qlabel, int64 value, ExplainState *es)
|
|||||||
* fractional digits.
|
* fractional digits.
|
||||||
*/
|
*/
|
||||||
void
|
void
|
||||||
ExplainPropertyFloat(const char *qlabel, double value, int ndigits,
|
ExplainPropertyFloat(const char *qlabel, const char *unit, double value,
|
||||||
ExplainState *es)
|
int ndigits, ExplainState *es)
|
||||||
{
|
{
|
||||||
char *buf;
|
char *buf;
|
||||||
|
|
||||||
buf = psprintf("%.*f", ndigits, value);
|
buf = psprintf("%.*f", ndigits, value);
|
||||||
ExplainProperty(qlabel, buf, true, es);
|
ExplainProperty(qlabel, unit, buf, true, es);
|
||||||
pfree(buf);
|
pfree(buf);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -3351,7 +3368,7 @@ ExplainPropertyFloat(const char *qlabel, double value, int ndigits,
|
|||||||
void
|
void
|
||||||
ExplainPropertyBool(const char *qlabel, bool value, ExplainState *es)
|
ExplainPropertyBool(const char *qlabel, bool value, ExplainState *es)
|
||||||
{
|
{
|
||||||
ExplainProperty(qlabel, value ? "true" : "false", true, es);
|
ExplainProperty(qlabel, NULL, value ? "true" : "false", true, es);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -93,10 +93,10 @@ extern void ExplainPropertyListNested(const char *qlabel, List *data,
|
|||||||
ExplainState *es);
|
ExplainState *es);
|
||||||
extern void ExplainPropertyText(const char *qlabel, const char *value,
|
extern void ExplainPropertyText(const char *qlabel, const char *value,
|
||||||
ExplainState *es);
|
ExplainState *es);
|
||||||
extern void ExplainPropertyInteger(const char *qlabel, int64 value,
|
extern void ExplainPropertyInteger(const char *qlabel, const char *unit,
|
||||||
ExplainState *es);
|
int64 value, ExplainState *es);
|
||||||
extern void ExplainPropertyFloat(const char *qlabel, double value, int ndigits,
|
extern void ExplainPropertyFloat(const char *qlabel, const char *unit,
|
||||||
ExplainState *es);
|
double value, int ndigits, ExplainState *es);
|
||||||
extern void ExplainPropertyBool(const char *qlabel, bool value,
|
extern void ExplainPropertyBool(const char *qlabel, bool value,
|
||||||
ExplainState *es);
|
ExplainState *es);
|
||||||
|
|
||||||
|
Loading…
x
Reference in New Issue
Block a user