|
- <?xml version="1.0" encoding="UTF-8" standalone="no"?>
- <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"><html xmlns="http://www.w3.org/1999/xhtml"><head><meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /><title>pgbench</title><link rel="stylesheet" type="text/css" href="stylesheet.css" /><link rev="made" href="pgsql-docs@lists.postgresql.org" /><meta name="generator" content="DocBook XSL Stylesheets V1.79.1" /><link rel="prev" href="app-pgbasebackup.html" title="pg_basebackup" /><link rel="next" href="app-pgconfig.html" title="pg_config" /></head><body><div xmlns="http://www.w3.org/TR/xhtml1/transitional" class="navheader"><table width="100%" summary="Navigation header"><tr><th colspan="5" align="center"><span xmlns="http://www.w3.org/1999/xhtml" class="application">pgbench</span></th></tr><tr><td width="10%" align="left"><a accesskey="p" href="app-pgbasebackup.html" title="pg_basebackup">Prev</a> </td><td width="10%" align="left"><a accesskey="u" href="reference-client.html" title="PostgreSQL Client Applications">Up</a></td><th width="60%" align="center">PostgreSQL Client Applications</th><td width="10%" align="right"><a accesskey="h" href="index.html" title="PostgreSQL 12.4 Documentation">Home</a></td><td width="10%" align="right"> <a accesskey="n" href="app-pgconfig.html" title="pg_config">Next</a></td></tr></table><hr></hr></div><div class="refentry" id="PGBENCH"><div class="titlepage"></div><a id="id-1.9.4.10.1" class="indexterm"></a><div class="refnamediv"><h2><span class="refentrytitle"><span class="application">pgbench</span></span></h2><p>pgbench — run a benchmark test on <span class="productname">PostgreSQL</span></p></div><div class="refsynopsisdiv"><h2>Synopsis</h2><div class="cmdsynopsis"><p id="id-1.9.4.10.4.1"><code class="command">pgbench</code> <code class="option">-i</code> [<em class="replaceable"><code>option</code></em>...] [<em class="replaceable"><code>dbname</code></em>]</p></div><div class="cmdsynopsis"><p id="id-1.9.4.10.4.2"><code class="command">pgbench</code> [<em class="replaceable"><code>option</code></em>...] [<em class="replaceable"><code>dbname</code></em>]</p></div></div><div class="refsect1" id="id-1.9.4.10.5"><h2>Description</h2><p>
- <span class="application">pgbench</span> is a simple program for running benchmark
- tests on <span class="productname">PostgreSQL</span>. It runs the same sequence of SQL
- commands over and over, possibly in multiple concurrent database sessions,
- and then calculates the average transaction rate (transactions per second).
- By default, <span class="application">pgbench</span> tests a scenario that is
- loosely based on TPC-B, involving five <code class="command">SELECT</code>,
- <code class="command">UPDATE</code>, and <code class="command">INSERT</code> commands per transaction.
- However, it is easy to test other cases by writing your own transaction
- script files.
- </p><p>
- Typical output from <span class="application">pgbench</span> looks like:
-
- </p><pre class="screen">
- transaction type: <builtin: TPC-B (sort of)>
- scaling factor: 10
- query mode: simple
- number of clients: 10
- number of threads: 1
- number of transactions per client: 1000
- number of transactions actually processed: 10000/10000
- tps = 85.184871 (including connections establishing)
- tps = 85.296346 (excluding connections establishing)
- </pre><p>
-
- The first six lines report some of the most important parameter
- settings. The next line reports the number of transactions completed
- and intended (the latter being just the product of number of clients
- and number of transactions per client); these will be equal unless the run
- failed before completion. (In <code class="option">-T</code> mode, only the actual
- number of transactions is printed.)
- The last two lines report the number of transactions per second,
- figured with and without counting the time to start database sessions.
- </p><p>
- The default TPC-B-like transaction test requires specific tables to be
- set up beforehand. <span class="application">pgbench</span> should be invoked with
- the <code class="option">-i</code> (initialize) option to create and populate these
- tables. (When you are testing a custom script, you don't need this
- step, but will instead need to do whatever setup your test needs.)
- Initialization looks like:
-
- </p><pre class="programlisting">
- pgbench -i [<span class="optional"> <em class="replaceable"><code>other-options</code></em> </span>] <em class="replaceable"><code>dbname</code></em>
- </pre><p>
-
- where <em class="replaceable"><code>dbname</code></em> is the name of the already-created
- database to test in. (You may also need <code class="option">-h</code>,
- <code class="option">-p</code>, and/or <code class="option">-U</code> options to specify how to
- connect to the database server.)
- </p><div class="caution"><h3 class="title">Caution</h3><p>
- <code class="literal">pgbench -i</code> creates four tables <code class="structname">pgbench_accounts</code>,
- <code class="structname">pgbench_branches</code>, <code class="structname">pgbench_history</code>, and
- <code class="structname">pgbench_tellers</code>,
- destroying any existing tables of these names.
- Be very careful to use another database if you have tables having these
- names!
- </p></div><p>
- At the default <span class="quote">“<span class="quote">scale factor</span>”</span> of 1, the tables initially
- contain this many rows:
- </p><pre class="screen">
- table # of rows
- ---------------------------------
- pgbench_branches 1
- pgbench_tellers 10
- pgbench_accounts 100000
- pgbench_history 0
- </pre><p>
- You can (and, for most purposes, probably should) increase the number
- of rows by using the <code class="option">-s</code> (scale factor) option. The
- <code class="option">-F</code> (fillfactor) option might also be used at this point.
- </p><p>
- Once you have done the necessary setup, you can run your benchmark
- with a command that doesn't include <code class="option">-i</code>, that is
-
- </p><pre class="programlisting">
- pgbench [<span class="optional"> <em class="replaceable"><code>options</code></em> </span>] <em class="replaceable"><code>dbname</code></em>
- </pre><p>
-
- In nearly all cases, you'll need some options to make a useful test.
- The most important options are <code class="option">-c</code> (number of clients),
- <code class="option">-t</code> (number of transactions), <code class="option">-T</code> (time limit),
- and <code class="option">-f</code> (specify a custom script file).
- See below for a full list.
- </p></div><div class="refsect1" id="id-1.9.4.10.6"><h2>Options</h2><p>
- The following is divided into three subsections. Different options are
- used during database initialization and while running benchmarks, but some
- options are useful in both cases.
- </p><div class="refsect2" id="PGBENCH-INIT-OPTIONS"><h3>Initialization Options</h3><p>
- <span class="application">pgbench</span> accepts the following command-line
- initialization arguments:
-
- </p><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="option">-i</code><br /></span><span class="term"><code class="option">--initialize</code></span></dt><dd><p>
- Required to invoke initialization mode.
- </p></dd><dt><span class="term"><code class="option">-I <em class="replaceable"><code>init_steps</code></em></code><br /></span><span class="term"><code class="option">--init-steps=<em class="replaceable"><code>init_steps</code></em></code></span></dt><dd><p>
- Perform just a selected set of the normal initialization steps.
- <em class="replaceable"><code>init_steps</code></em> specifies the
- initialization steps to be performed, using one character per step.
- Each step is invoked in the specified order.
- The default is <code class="literal">dtgvp</code>.
- The available steps are:
-
- </p><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="literal">d</code> (Drop)</span></dt><dd><p>
- Drop any existing <span class="application">pgbench</span> tables.
- </p></dd><dt><span class="term"><code class="literal">t</code> (create Tables)</span></dt><dd><p>
- Create the tables used by the
- standard <span class="application">pgbench</span> scenario, namely
- <code class="structname">pgbench_accounts</code>,
- <code class="structname">pgbench_branches</code>,
- <code class="structname">pgbench_history</code>, and
- <code class="structname">pgbench_tellers</code>.
- </p></dd><dt><span class="term"><code class="literal">g</code> (Generate data)</span></dt><dd><p>
- Generate data and load it into the standard tables,
- replacing any data already present.
- </p></dd><dt><span class="term"><code class="literal">v</code> (Vacuum)</span></dt><dd><p>
- Invoke <code class="command">VACUUM</code> on the standard tables.
- </p></dd><dt><span class="term"><code class="literal">p</code> (create Primary keys)</span></dt><dd><p>
- Create primary key indexes on the standard tables.
- </p></dd><dt><span class="term"><code class="literal">f</code> (create Foreign keys)</span></dt><dd><p>
- Create foreign key constraints between the standard tables.
- (Note that this step is not performed by default.)
- </p></dd></dl></div><p>
- </p></dd><dt><span class="term"><code class="option">-F</code> <em class="replaceable"><code>fillfactor</code></em><br /></span><span class="term"><code class="option">--fillfactor=</code><em class="replaceable"><code>fillfactor</code></em></span></dt><dd><p>
- Create the <code class="structname">pgbench_accounts</code>,
- <code class="structname">pgbench_tellers</code> and
- <code class="structname">pgbench_branches</code> tables with the given fillfactor.
- Default is 100.
- </p></dd><dt><span class="term"><code class="option">-n</code><br /></span><span class="term"><code class="option">--no-vacuum</code></span></dt><dd><p>
- Perform no vacuuming during initialization.
- (This option suppresses the <code class="literal">v</code> initialization step,
- even if it was specified in <code class="option">-I</code>.)
- </p></dd><dt><span class="term"><code class="option">-q</code><br /></span><span class="term"><code class="option">--quiet</code></span></dt><dd><p>
- Switch logging to quiet mode, producing only one progress message per 5
- seconds. The default logging prints one message each 100000 rows, which
- often outputs many lines per second (especially on good hardware).
- </p></dd><dt><span class="term"><code class="option">-s</code> <em class="replaceable"><code>scale_factor</code></em><br /></span><span class="term"><code class="option">--scale=</code><em class="replaceable"><code>scale_factor</code></em></span></dt><dd><p>
- Multiply the number of rows generated by the scale factor.
- For example, <code class="literal">-s 100</code> will create 10,000,000 rows
- in the <code class="structname">pgbench_accounts</code> table. Default is 1.
- When the scale is 20,000 or larger, the columns used to
- hold account identifiers (<code class="structfield">aid</code> columns)
- will switch to using larger integers (<code class="type">bigint</code>),
- in order to be big enough to hold the range of account
- identifiers.
- </p></dd><dt><span class="term"><code class="option">--foreign-keys</code></span></dt><dd><p>
- Create foreign key constraints between the standard tables.
- (This option adds the <code class="literal">f</code> step to the initialization
- step sequence, if it is not already present.)
- </p></dd><dt><span class="term"><code class="option">--index-tablespace=<em class="replaceable"><code>index_tablespace</code></em></code></span></dt><dd><p>
- Create indexes in the specified tablespace, rather than the default
- tablespace.
- </p></dd><dt><span class="term"><code class="option">--tablespace=<em class="replaceable"><code>tablespace</code></em></code></span></dt><dd><p>
- Create tables in the specified tablespace, rather than the default
- tablespace.
- </p></dd><dt><span class="term"><code class="option">--unlogged-tables</code></span></dt><dd><p>
- Create all tables as unlogged tables, rather than permanent tables.
- </p></dd></dl></div><p>
- </p></div><div class="refsect2" id="PGBENCH-RUN-OPTIONS"><h3>Benchmarking Options</h3><p>
- <span class="application">pgbench</span> accepts the following command-line
- benchmarking arguments:
-
- </p><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="option">-b</code> <em class="replaceable"><code>scriptname[@weight]</code></em><br /></span><span class="term"><code class="option">--builtin</code>=<em class="replaceable"><code>scriptname[@weight]</code></em></span></dt><dd><p>
- Add the specified built-in script to the list of executed scripts.
- An optional integer weight after <code class="literal">@</code> allows to adjust the
- probability of drawing the script. If not specified, it is set to 1.
- Available built-in scripts are: <code class="literal">tpcb-like</code>,
- <code class="literal">simple-update</code> and <code class="literal">select-only</code>.
- Unambiguous prefixes of built-in names are accepted.
- With special name <code class="literal">list</code>, show the list of built-in scripts
- and exit immediately.
- </p></dd><dt><span class="term"><code class="option">-c</code> <em class="replaceable"><code>clients</code></em><br /></span><span class="term"><code class="option">--client=</code><em class="replaceable"><code>clients</code></em></span></dt><dd><p>
- Number of clients simulated, that is, number of concurrent database
- sessions. Default is 1.
- </p></dd><dt><span class="term"><code class="option">-C</code><br /></span><span class="term"><code class="option">--connect</code></span></dt><dd><p>
- Establish a new connection for each transaction, rather than
- doing it just once per client session.
- This is useful to measure the connection overhead.
- </p></dd><dt><span class="term"><code class="option">-d</code><br /></span><span class="term"><code class="option">--debug</code></span></dt><dd><p>
- Print debugging output.
- </p></dd><dt><span class="term"><code class="option">-D</code> <em class="replaceable"><code>varname</code></em><code class="literal">=</code><em class="replaceable"><code>value</code></em><br /></span><span class="term"><code class="option">--define=</code><em class="replaceable"><code>varname</code></em><code class="literal">=</code><em class="replaceable"><code>value</code></em></span></dt><dd><p>
- Define a variable for use by a custom script (see below).
- Multiple <code class="option">-D</code> options are allowed.
- </p></dd><dt><span class="term"><code class="option">-f</code> <em class="replaceable"><code>filename[@weight]</code></em><br /></span><span class="term"><code class="option">--file=</code><em class="replaceable"><code>filename[@weight]</code></em></span></dt><dd><p>
- Add a transaction script read from <em class="replaceable"><code>filename</code></em> to
- the list of executed scripts.
- An optional integer weight after <code class="literal">@</code> allows to adjust the
- probability of drawing the test.
- See below for details.
- </p></dd><dt><span class="term"><code class="option">-j</code> <em class="replaceable"><code>threads</code></em><br /></span><span class="term"><code class="option">--jobs=</code><em class="replaceable"><code>threads</code></em></span></dt><dd><p>
- Number of worker threads within <span class="application">pgbench</span>.
- Using more than one thread can be helpful on multi-CPU machines.
- Clients are distributed as evenly as possible among available threads.
- Default is 1.
- </p></dd><dt><span class="term"><code class="option">-l</code><br /></span><span class="term"><code class="option">--log</code></span></dt><dd><p>
- Write information about each transaction to a log file.
- See below for details.
- </p></dd><dt><span class="term"><code class="option">-L</code> <em class="replaceable"><code>limit</code></em><br /></span><span class="term"><code class="option">--latency-limit=</code><em class="replaceable"><code>limit</code></em></span></dt><dd><p>
- Transactions that last more than <em class="replaceable"><code>limit</code></em> milliseconds
- are counted and reported separately, as <em class="firstterm">late</em>.
- </p><p>
- When throttling is used (<code class="option">--rate=...</code>), transactions that
- lag behind schedule by more than <em class="replaceable"><code>limit</code></em> ms, and thus
- have no hope of meeting the latency limit, are not sent to the server
- at all. They are counted and reported separately as
- <em class="firstterm">skipped</em>.
- </p></dd><dt><span class="term"><code class="option">-M</code> <em class="replaceable"><code>querymode</code></em><br /></span><span class="term"><code class="option">--protocol=</code><em class="replaceable"><code>querymode</code></em></span></dt><dd><p>
- Protocol to use for submitting queries to the server:
- </p><div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; "><li class="listitem"><p><code class="literal">simple</code>: use simple query protocol.</p></li><li class="listitem"><p><code class="literal">extended</code>: use extended query protocol.</p></li><li class="listitem"><p><code class="literal">prepared</code>: use extended query protocol with prepared statements.</p></li></ul></div><p>
-
- In the <code class="literal">prepared</code> mode, <span class="application">pgbench</span>
- reuses the parse analysis result starting from the second query
- iteration, so <span class="application">pgbench</span> runs faster
- than in other modes.
- </p><p>
- The default is simple query protocol. (See <a class="xref" href="protocol.html" title="Chapter 52. Frontend/Backend Protocol">Chapter 52</a>
- for more information.)
- </p></dd><dt><span class="term"><code class="option">-n</code><br /></span><span class="term"><code class="option">--no-vacuum</code></span></dt><dd><p>
- Perform no vacuuming before running the test.
- This option is <span class="emphasis"><em>necessary</em></span>
- if you are running a custom test scenario that does not include
- the standard tables <code class="structname">pgbench_accounts</code>,
- <code class="structname">pgbench_branches</code>, <code class="structname">pgbench_history</code>, and
- <code class="structname">pgbench_tellers</code>.
- </p></dd><dt><span class="term"><code class="option">-N</code><br /></span><span class="term"><code class="option">--skip-some-updates</code></span></dt><dd><p>
- Run built-in simple-update script.
- Shorthand for <code class="option">-b simple-update</code>.
- </p></dd><dt><span class="term"><code class="option">-P</code> <em class="replaceable"><code>sec</code></em><br /></span><span class="term"><code class="option">--progress=</code><em class="replaceable"><code>sec</code></em></span></dt><dd><p>
- Show progress report every <em class="replaceable"><code>sec</code></em> seconds. The report
- includes the time since the beginning of the run, the TPS since the
- last report, and the transaction latency average and standard
- deviation since the last report. Under throttling (<code class="option">-R</code>),
- the latency is computed with respect to the transaction scheduled
- start time, not the actual transaction beginning time, thus it also
- includes the average schedule lag time.
- </p></dd><dt><span class="term"><code class="option">-r</code><br /></span><span class="term"><code class="option">--report-latencies</code></span></dt><dd><p>
- Report the average per-statement latency (execution time from the
- perspective of the client) of each command after the benchmark
- finishes. See below for details.
- </p></dd><dt><span class="term"><code class="option">-R</code> <em class="replaceable"><code>rate</code></em><br /></span><span class="term"><code class="option">--rate=</code><em class="replaceable"><code>rate</code></em></span></dt><dd><p>
- Execute transactions targeting the specified rate instead of running
- as fast as possible (the default). The rate is given in transactions
- per second. If the targeted rate is above the maximum possible rate,
- the rate limit won't impact the results.
- </p><p>
- The rate is targeted by starting transactions along a
- Poisson-distributed schedule time line. The expected start time
- schedule moves forward based on when the client first started, not
- when the previous transaction ended. That approach means that when
- transactions go past their original scheduled end time, it is
- possible for later ones to catch up again.
- </p><p>
- When throttling is active, the transaction latency reported at the
- end of the run is calculated from the scheduled start times, so it
- includes the time each transaction had to wait for the previous
- transaction to finish. The wait time is called the schedule lag time,
- and its average and maximum are also reported separately. The
- transaction latency with respect to the actual transaction start time,
- i.e. the time spent executing the transaction in the database, can be
- computed by subtracting the schedule lag time from the reported
- latency.
- </p><p>
- If <code class="option">--latency-limit</code> is used together with <code class="option">--rate</code>,
- a transaction can lag behind so much that it is already over the
- latency limit when the previous transaction ends, because the latency
- is calculated from the scheduled start time. Such transactions are
- not sent to the server, but are skipped altogether and counted
- separately.
- </p><p>
- A high schedule lag time is an indication that the system cannot
- process transactions at the specified rate, with the chosen number of
- clients and threads. When the average transaction execution time is
- longer than the scheduled interval between each transaction, each
- successive transaction will fall further behind, and the schedule lag
- time will keep increasing the longer the test run is. When that
- happens, you will have to reduce the specified transaction rate.
- </p></dd><dt><span class="term"><code class="option">-s</code> <em class="replaceable"><code>scale_factor</code></em><br /></span><span class="term"><code class="option">--scale=</code><em class="replaceable"><code>scale_factor</code></em></span></dt><dd><p>
- Report the specified scale factor in <span class="application">pgbench</span>'s
- output. With the built-in tests, this is not necessary; the
- correct scale factor will be detected by counting the number of
- rows in the <code class="structname">pgbench_branches</code> table.
- However, when testing only custom benchmarks (<code class="option">-f</code> option),
- the scale factor will be reported as 1 unless this option is used.
- </p></dd><dt><span class="term"><code class="option">-S</code><br /></span><span class="term"><code class="option">--select-only</code></span></dt><dd><p>
- Run built-in select-only script.
- Shorthand for <code class="option">-b select-only</code>.
- </p></dd><dt><span class="term"><code class="option">-t</code> <em class="replaceable"><code>transactions</code></em><br /></span><span class="term"><code class="option">--transactions=</code><em class="replaceable"><code>transactions</code></em></span></dt><dd><p>
- Number of transactions each client runs. Default is 10.
- </p></dd><dt><span class="term"><code class="option">-T</code> <em class="replaceable"><code>seconds</code></em><br /></span><span class="term"><code class="option">--time=</code><em class="replaceable"><code>seconds</code></em></span></dt><dd><p>
- Run the test for this many seconds, rather than a fixed number of
- transactions per client. <code class="option">-t</code> and
- <code class="option">-T</code> are mutually exclusive.
- </p></dd><dt><span class="term"><code class="option">-v</code><br /></span><span class="term"><code class="option">--vacuum-all</code></span></dt><dd><p>
- Vacuum all four standard tables before running the test.
- With neither <code class="option">-n</code> nor <code class="option">-v</code>, <span class="application">pgbench</span> will vacuum the
- <code class="structname">pgbench_tellers</code> and <code class="structname">pgbench_branches</code>
- tables, and will truncate <code class="structname">pgbench_history</code>.
- </p></dd><dt><span class="term"><code class="option">--aggregate-interval=<em class="replaceable"><code>seconds</code></em></code></span></dt><dd><p>
- Length of aggregation interval (in seconds). May be used only
- with <code class="option">-l</code> option. With this option, the log contains
- per-interval summary data, as described below.
- </p></dd><dt><span class="term"><code class="option">--log-prefix=<em class="replaceable"><code>prefix</code></em></code></span></dt><dd><p>
- Set the filename prefix for the log files created by
- <code class="option">--log</code>. The default is <code class="literal">pgbench_log</code>.
- </p></dd><dt><span class="term"><code class="option">--progress-timestamp</code></span></dt><dd><p>
- When showing progress (option <code class="option">-P</code>), use a timestamp
- (Unix epoch) instead of the number of seconds since the
- beginning of the run. The unit is in seconds, with millisecond
- precision after the dot.
- This helps compare logs generated by various tools.
- </p></dd><dt><span class="term"><code class="option">--random-seed=</code><em class="replaceable"><code>SEED</code></em></span></dt><dd><p>
- Set random generator seed. Seeds the system random number generator,
- which then produces a sequence of initial generator states, one for
- each thread.
- Values for <em class="replaceable"><code>SEED</code></em> may be:
- <code class="literal">time</code> (the default, the seed is based on the current time),
- <code class="literal">rand</code> (use a strong random source, failing if none
- is available), or an unsigned decimal integer value.
- The random generator is invoked explicitly from a pgbench script
- (<code class="literal">random...</code> functions) or implicitly (for instance option
- <code class="option">--rate</code> uses it to schedule transactions).
- When explicitly set, the value used for seeding is shown on the terminal.
- Any value allowed for <em class="replaceable"><code>SEED</code></em> may also be
- provided through the environment variable
- <code class="literal">PGBENCH_RANDOM_SEED</code>.
- To ensure that the provided seed impacts all possible uses, put this option
- first or use the environment variable.
- </p><p>
- Setting the seed explicitly allows to reproduce a <code class="command">pgbench</code>
- run exactly, as far as random numbers are concerned.
- As the random state is managed per thread, this means the exact same
- <code class="command">pgbench</code> run for an identical invocation if there is one
- client per thread and there are no external or data dependencies.
- From a statistical viewpoint reproducing runs exactly is a bad idea because
- it can hide the performance variability or improve performance unduly,
- e.g. by hitting the same pages as a previous run.
- However, it may also be of great help for debugging, for instance
- re-running a tricky case which leads to an error.
- Use wisely.
- </p></dd><dt><span class="term"><code class="option">--sampling-rate=<em class="replaceable"><code>rate</code></em></code></span></dt><dd><p>
- Sampling rate, used when writing data into the log, to reduce the
- amount of log generated. If this option is given, only the specified
- fraction of transactions are logged. 1.0 means all transactions will
- be logged, 0.05 means only 5% of the transactions will be logged.
- </p><p>
- Remember to take the sampling rate into account when processing the
- log file. For example, when computing TPS values, you need to multiply
- the numbers accordingly (e.g. with 0.01 sample rate, you'll only get
- 1/100 of the actual TPS).
- </p></dd></dl></div><p>
- </p></div><div class="refsect2" id="PGBENCH-COMMON-OPTIONS"><h3>Common Options</h3><p>
- <span class="application">pgbench</span> accepts the following command-line
- common arguments:
-
- </p><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="option">-h</code> <em class="replaceable"><code>hostname</code></em><br /></span><span class="term"><code class="option">--host=</code><em class="replaceable"><code>hostname</code></em></span></dt><dd><p>
- The database server's host name
- </p></dd><dt><span class="term"><code class="option">-p</code> <em class="replaceable"><code>port</code></em><br /></span><span class="term"><code class="option">--port=</code><em class="replaceable"><code>port</code></em></span></dt><dd><p>
- The database server's port number
- </p></dd><dt><span class="term"><code class="option">-U</code> <em class="replaceable"><code>login</code></em><br /></span><span class="term"><code class="option">--username=</code><em class="replaceable"><code>login</code></em></span></dt><dd><p>
- The user name to connect as
- </p></dd><dt><span class="term"><code class="option">-V</code><br /></span><span class="term"><code class="option">--version</code></span></dt><dd><p>
- Print the <span class="application">pgbench</span> version and exit.
- </p></dd><dt><span class="term"><code class="option">-?</code><br /></span><span class="term"><code class="option">--help</code></span></dt><dd><p>
- Show help about <span class="application">pgbench</span> command line
- arguments, and exit.
- </p></dd></dl></div><p>
- </p></div></div><div class="refsect1" id="id-1.9.4.10.7"><h2>Exit Status</h2><p>
- A successful run will exit with status 0. Exit status 1 indicates static
- problems such as invalid command-line options. Errors during the run such
- as database errors or problems in the script will result in exit status 2.
- In the latter case, <span class="application">pgbench</span> will print partial
- results.
- </p></div><div class="refsect1" id="id-1.9.4.10.8"><h2>Environment</h2><div class="variablelist"><dl class="variablelist"><dt><span class="term"><code class="envar">PGHOST</code><br /></span><span class="term"><code class="envar">PGPORT</code><br /></span><span class="term"><code class="envar">PGUSER</code></span></dt><dd><p>
- Default connection parameters.
- </p></dd></dl></div><p>
- This utility, like most other <span class="productname">PostgreSQL</span> utilities,
- uses the environment variables supported by <span class="application">libpq</span>
- (see <a class="xref" href="libpq-envars.html" title="33.14. Environment Variables">Section 33.14</a>).
- </p></div><div class="refsect1" id="id-1.9.4.10.9"><h2>Notes</h2><div class="refsect2" id="id-1.9.4.10.9.2"><h3>What Is the <span class="quote">“<span class="quote">Transaction</span>”</span> Actually Performed in <span class="application">pgbench</span>?</h3><p>
- <span class="application">pgbench</span> executes test scripts chosen randomly
- from a specified list.
- They include built-in scripts with <code class="option">-b</code> and
- user-provided custom scripts with <code class="option">-f</code>.
- Each script may be given a relative weight specified after a
- <code class="literal">@</code> so as to change its drawing probability.
- The default weight is <code class="literal">1</code>.
- Scripts with a weight of <code class="literal">0</code> are ignored.
- </p><p>
- The default built-in transaction script (also invoked with <code class="option">-b tpcb-like</code>)
- issues seven commands per transaction over randomly chosen <code class="literal">aid</code>,
- <code class="literal">tid</code>, <code class="literal">bid</code> and <code class="literal">delta</code>.
- The scenario is inspired by the TPC-B benchmark, but is not actually TPC-B,
- hence the name.
- </p><div class="orderedlist"><ol class="orderedlist" type="1"><li class="listitem"><p><code class="literal">BEGIN;</code></p></li><li class="listitem"><p><code class="literal">UPDATE pgbench_accounts SET abalance = abalance + :delta WHERE aid = :aid;</code></p></li><li class="listitem"><p><code class="literal">SELECT abalance FROM pgbench_accounts WHERE aid = :aid;</code></p></li><li class="listitem"><p><code class="literal">UPDATE pgbench_tellers SET tbalance = tbalance + :delta WHERE tid = :tid;</code></p></li><li class="listitem"><p><code class="literal">UPDATE pgbench_branches SET bbalance = bbalance + :delta WHERE bid = :bid;</code></p></li><li class="listitem"><p><code class="literal">INSERT INTO pgbench_history (tid, bid, aid, delta, mtime) VALUES (:tid, :bid, :aid, :delta, CURRENT_TIMESTAMP);</code></p></li><li class="listitem"><p><code class="literal">END;</code></p></li></ol></div><p>
- If you select the <code class="literal">simple-update</code> built-in (also <code class="option">-N</code>),
- steps 4 and 5 aren't included in the transaction.
- This will avoid update contention on these tables, but
- it makes the test case even less like TPC-B.
- </p><p>
- If you select the <code class="literal">select-only</code> built-in (also <code class="option">-S</code>),
- only the <code class="command">SELECT</code> is issued.
- </p></div><div class="refsect2" id="id-1.9.4.10.9.3"><h3>Custom Scripts</h3><p>
- <span class="application">pgbench</span> has support for running custom
- benchmark scenarios by replacing the default transaction script
- (described above) with a transaction script read from a file
- (<code class="option">-f</code> option). In this case a <span class="quote">“<span class="quote">transaction</span>”</span>
- counts as one execution of a script file.
- </p><p>
- A script file contains one or more SQL commands terminated by
- semicolons. Empty lines and lines beginning with
- <code class="literal">--</code> are ignored. Script files can also contain
- <span class="quote">“<span class="quote">meta commands</span>”</span>, which are interpreted by <span class="application">pgbench</span>
- itself, as described below.
- </p><div class="note"><h3 class="title">Note</h3><p>
- Before <span class="productname">PostgreSQL</span> 9.6, SQL commands in script files
- were terminated by newlines, and so they could not be continued across
- lines. Now a semicolon is <span class="emphasis"><em>required</em></span> to separate consecutive
- SQL commands (though a SQL command does not need one if it is followed
- by a meta command). If you need to create a script file that works with
- both old and new versions of <span class="application">pgbench</span>, be sure to write
- each SQL command on a single line ending with a semicolon.
- </p></div><p>
- There is a simple variable-substitution facility for script files.
- Variable names must consist of letters (including non-Latin letters),
- digits, and underscores.
- Variables can be set by the command-line <code class="option">-D</code> option,
- explained above, or by the meta commands explained below.
- In addition to any variables preset by <code class="option">-D</code> command-line options,
- there are a few variables that are preset automatically, listed in
- <a class="xref" href="pgbench.html#PGBENCH-AUTOMATIC-VARIABLES" title="Table 257. Automatic Variables">Table 257</a>. A value specified for these
- variables using <code class="option">-D</code> takes precedence over the automatic presets.
- Once set, a variable's
- value can be inserted into a SQL command by writing
- <code class="literal">:</code><em class="replaceable"><code>variablename</code></em>. When running more than
- one client session, each session has its own set of variables.
- <span class="application">pgbench</span> supports up to 255 variable uses in one
- statement.
- </p><div class="table" id="PGBENCH-AUTOMATIC-VARIABLES"><p class="title"><strong>Table 257. Automatic Variables</strong></p><div class="table-contents"><table class="table" summary="Automatic Variables" border="1"><colgroup><col /><col /></colgroup><thead><tr><th>Variable</th><th>Description</th></tr></thead><tbody><tr><td> <code class="literal">client_id</code> </td><td>unique number identifying the client session (starts from zero)</td></tr><tr><td> <code class="literal">default_seed</code> </td><td>seed used in hash functions by default</td></tr><tr><td> <code class="literal">random_seed</code> </td><td>random generator seed (unless overwritten with <code class="option">-D</code>)</td></tr><tr><td> <code class="literal">scale</code> </td><td>current scale factor</td></tr></tbody></table></div></div><br class="table-break" /><p>
- Script file meta commands begin with a backslash (<code class="literal">\</code>) and
- normally extend to the end of the line, although they can be continued
- to additional lines by writing backslash-return.
- Arguments to a meta command are separated by white space.
- These meta commands are supported:
- </p><div class="variablelist"><dl class="variablelist"><dt id="PGBENCH-METACOMMAND-GSET"><span class="term">
- <code class="literal">\gset [<em class="replaceable"><code>prefix</code></em>]</code>
- </span></dt><dd><p>
- This command may be used to end SQL queries, taking the place of the
- terminating semicolon (<code class="literal">;</code>).
- </p><p>
- When this command is used, the preceding SQL query is expected to
- return one row, the columns of which are stored into variables named after
- column names, and prefixed with <em class="replaceable"><code>prefix</code></em> if provided.
- </p><p>
- The following example puts the final account balance from the first query
- into variable <em class="replaceable"><code>abalance</code></em>, and fills variables
- <em class="replaceable"><code>p_two</code></em> and <em class="replaceable"><code>p_three</code></em>
- with integers from the third query.
- The result of the second query is discarded.
- </p><pre class="programlisting">
- UPDATE pgbench_accounts
- SET abalance = abalance + :delta
- WHERE aid = :aid
- RETURNING abalance \gset
- -- compound of two queries
- SELECT 1 \;
- SELECT 2 AS two, 3 AS three \gset p_
- </pre><p>
- </p></dd><dt><span class="term"><code class="literal">\if</code> <em class="replaceable"><code>expression</code></em><br /></span><span class="term"><code class="literal">\elif</code> <em class="replaceable"><code>expression</code></em><br /></span><span class="term"><code class="literal">\else</code><br /></span><span class="term"><code class="literal">\endif</code></span></dt><dd><p>
- This group of commands implements nestable conditional blocks,
- similarly to <code class="literal">psql</code>'s <a class="xref" href="app-psql.html#PSQL-METACOMMAND-IF"><code class="literal">\if</code> <em class="replaceable"><code>expression</code></em></a>.
- Conditional expressions are identical to those with <code class="literal">\set</code>,
- with non-zero values interpreted as true.
- </p></dd><dt id="PGBENCH-METACOMMAND-SET"><span class="term">
- <code class="literal">\set <em class="replaceable"><code>varname</code></em> <em class="replaceable"><code>expression</code></em></code>
- </span></dt><dd><p>
- Sets variable <em class="replaceable"><code>varname</code></em> to a value calculated
- from <em class="replaceable"><code>expression</code></em>.
- The expression may contain the <code class="literal">NULL</code> constant,
- Boolean constants <code class="literal">TRUE</code> and <code class="literal">FALSE</code>,
- integer constants such as <code class="literal">5432</code>,
- double constants such as <code class="literal">3.14159</code>,
- references to variables <code class="literal">:</code><em class="replaceable"><code>variablename</code></em>,
- <a class="link" href="pgbench.html#PGBENCH-BUILTIN-OPERATORS" title="Built-in Operators">operators</a>
- with their usual SQL precedence and associativity,
- <a class="link" href="pgbench.html#PGBENCH-BUILTIN-FUNCTIONS" title="Built-In Functions">function calls</a>,
- SQL <a class="link" href="functions-conditional.html#FUNCTIONS-CASE" title="9.17.1. CASE"><code class="token">CASE</code> generic conditional
- expressions</a> and parentheses.
- </p><p>
- Functions and most operators return <code class="literal">NULL</code> on
- <code class="literal">NULL</code> input.
- </p><p>
- For conditional purposes, non zero numerical values are
- <code class="literal">TRUE</code>, zero numerical values and <code class="literal">NULL</code>
- are <code class="literal">FALSE</code>.
- </p><p>
- Too large or small integer and double constants, as well as
- integer arithmetic operators (<code class="literal">+</code>,
- <code class="literal">-</code>, <code class="literal">*</code> and <code class="literal">/</code>)
- raise errors on overflows.
- </p><p>
- When no final <code class="token">ELSE</code> clause is provided to a
- <code class="token">CASE</code>, the default value is <code class="literal">NULL</code>.
- </p><p>
- Examples:
- </p><pre class="programlisting">
- \set ntellers 10 * :scale
- \set aid (1021 * random(1, 100000 * :scale)) % \
- (100000 * :scale) + 1
- \set divx CASE WHEN :x <> 0 THEN :y/:x ELSE NULL END
- </pre></dd><dt><span class="term">
- <code class="literal">\sleep <em class="replaceable"><code>number</code></em> [ us | ms | s ]</code>
- </span></dt><dd><p>
- Causes script execution to sleep for the specified duration in
- microseconds (<code class="literal">us</code>), milliseconds (<code class="literal">ms</code>) or seconds
- (<code class="literal">s</code>). If the unit is omitted then seconds are the default.
- <em class="replaceable"><code>number</code></em> can be either an integer constant or a
- <code class="literal">:</code><em class="replaceable"><code>variablename</code></em> reference to a variable
- having an integer value.
- </p><p>
- Example:
- </p><pre class="programlisting">
- \sleep 10 ms
- </pre></dd><dt><span class="term">
- <code class="literal">\setshell <em class="replaceable"><code>varname</code></em> <em class="replaceable"><code>command</code></em> [ <em class="replaceable"><code>argument</code></em> ... ]</code>
- </span></dt><dd><p>
- Sets variable <em class="replaceable"><code>varname</code></em> to the result of the shell command
- <em class="replaceable"><code>command</code></em> with the given <em class="replaceable"><code>argument</code></em>(s).
- The command must return an integer value through its standard output.
- </p><p>
- <em class="replaceable"><code>command</code></em> and each <em class="replaceable"><code>argument</code></em> can be either
- a text constant or a <code class="literal">:</code><em class="replaceable"><code>variablename</code></em> reference
- to a variable. If you want to use an <em class="replaceable"><code>argument</code></em> starting
- with a colon, write an additional colon at the beginning of
- <em class="replaceable"><code>argument</code></em>.
- </p><p>
- Example:
- </p><pre class="programlisting">
- \setshell variable_to_be_assigned command literal_argument :variable ::literal_starting_with_colon
- </pre></dd><dt><span class="term">
- <code class="literal">\shell <em class="replaceable"><code>command</code></em> [ <em class="replaceable"><code>argument</code></em> ... ]</code>
- </span></dt><dd><p>
- Same as <code class="literal">\setshell</code>, but the result of the command
- is discarded.
- </p><p>
- Example:
- </p><pre class="programlisting">
- \shell command literal_argument :variable ::literal_starting_with_colon
- </pre></dd></dl></div></div><div class="refsect2" id="PGBENCH-BUILTIN-OPERATORS"><h3>Built-in Operators</h3><p>
- The arithmetic, bitwise, comparison and logical operators listed in
- <a class="xref" href="pgbench.html#PGBENCH-OPERATORS" title="Table 258. pgbench Operators by Increasing Precedence">Table 258</a> are built into <span class="application">pgbench</span>
- and may be used in expressions appearing in
- <a class="link" href="pgbench.html#PGBENCH-METACOMMAND-SET"><code class="literal">\set</code></a>.
- </p><div class="table" id="PGBENCH-OPERATORS"><p class="title"><strong>Table 258. pgbench Operators by Increasing Precedence</strong></p><div class="table-contents"><table class="table" summary="pgbench Operators by Increasing Precedence" border="1"><colgroup><col /><col /><col /><col /></colgroup><thead><tr><th>Operator</th><th>Description</th><th>Example</th><th>Result</th></tr></thead><tbody><tr><td><code class="literal">OR</code></td><td>logical or</td><td><code class="literal">5 or 0</code></td><td><code class="literal">TRUE</code></td></tr><tr><td><code class="literal">AND</code></td><td>logical and</td><td><code class="literal">3 and 0</code></td><td><code class="literal">FALSE</code></td></tr><tr><td><code class="literal">NOT</code></td><td>logical not</td><td><code class="literal">not false</code></td><td><code class="literal">TRUE</code></td></tr><tr><td><code class="literal">IS [NOT] (NULL|TRUE|FALSE)</code></td><td>value tests</td><td><code class="literal">1 is null</code></td><td><code class="literal">FALSE</code></td></tr><tr><td><code class="literal">ISNULL|NOTNULL</code></td><td>null tests</td><td><code class="literal">1 notnull</code></td><td><code class="literal">TRUE</code></td></tr><tr><td><code class="literal">=</code></td><td>is equal</td><td><code class="literal">5 = 4</code></td><td><code class="literal">FALSE</code></td></tr><tr><td><code class="literal"><></code></td><td>is not equal</td><td><code class="literal">5 <> 4</code></td><td><code class="literal">TRUE</code></td></tr><tr><td><code class="literal">!=</code></td><td>is not equal</td><td><code class="literal">5 != 5</code></td><td><code class="literal">FALSE</code></td></tr><tr><td><code class="literal"><</code></td><td>lower than</td><td><code class="literal">5 < 4</code></td><td><code class="literal">FALSE</code></td></tr><tr><td><code class="literal"><=</code></td><td>lower or equal</td><td><code class="literal">5 <= 4</code></td><td><code class="literal">FALSE</code></td></tr><tr><td><code class="literal">></code></td><td>greater than</td><td><code class="literal">5 > 4</code></td><td><code class="literal">TRUE</code></td></tr><tr><td><code class="literal">>=</code></td><td>greater or equal</td><td><code class="literal">5 >= 4</code></td><td><code class="literal">TRUE</code></td></tr><tr><td><code class="literal">|</code></td><td>integer bitwise OR</td><td><code class="literal">1 | 2</code></td><td><code class="literal">3</code></td></tr><tr><td><code class="literal">#</code></td><td>integer bitwise XOR</td><td><code class="literal">1 # 3</code></td><td><code class="literal">2</code></td></tr><tr><td><code class="literal">&</code></td><td>integer bitwise AND</td><td><code class="literal">1 & 3</code></td><td><code class="literal">1</code></td></tr><tr><td><code class="literal">~</code></td><td>integer bitwise NOT</td><td><code class="literal">~ 1</code></td><td><code class="literal">-2</code></td></tr><tr><td><code class="literal"><<</code></td><td>integer bitwise shift left</td><td><code class="literal">1 << 2</code></td><td><code class="literal">4</code></td></tr><tr><td><code class="literal">>></code></td><td>integer bitwise shift right</td><td><code class="literal">8 >> 2</code></td><td><code class="literal">2</code></td></tr><tr><td><code class="literal">+</code></td><td>addition</td><td><code class="literal">5 + 4</code></td><td><code class="literal">9</code></td></tr><tr><td><code class="literal">-</code></td><td>subtraction</td><td><code class="literal">3 - 2.0</code></td><td><code class="literal">1.0</code></td></tr><tr><td><code class="literal">*</code></td><td>multiplication</td><td><code class="literal">5 * 4</code></td><td><code class="literal">20</code></td></tr><tr><td><code class="literal">/</code></td><td>division (integer truncates the results)</td><td><code class="literal">5 / 3</code></td><td><code class="literal">1</code></td></tr><tr><td><code class="literal">%</code></td><td>modulo</td><td><code class="literal">3 % 2</code></td><td><code class="literal">1</code></td></tr><tr><td><code class="literal">-</code></td><td>opposite</td><td><code class="literal">- 2.0</code></td><td><code class="literal">-2.0</code></td></tr></tbody></table></div></div><br class="table-break" /></div><div class="refsect2" id="PGBENCH-BUILTIN-FUNCTIONS"><h3>Built-In Functions</h3><p>
- The functions listed in <a class="xref" href="pgbench.html#PGBENCH-FUNCTIONS" title="Table 259. pgbench Functions">Table 259</a> are built
- into <span class="application">pgbench</span> and may be used in expressions appearing in
- <a class="link" href="pgbench.html#PGBENCH-METACOMMAND-SET"><code class="literal">\set</code></a>.
- </p><div class="table" id="PGBENCH-FUNCTIONS"><p class="title"><strong>Table 259. pgbench Functions</strong></p><div class="table-contents"><table class="table" summary="pgbench Functions" border="1"><colgroup><col /><col /><col /><col /><col /></colgroup><thead><tr><th>Function</th><th>Return Type</th><th>Description</th><th>Example</th><th>Result</th></tr></thead><tbody><tr><td><code class="literal"><code class="function">abs(<em class="replaceable"><code>a</code></em>)</code></code></td><td>same as <em class="replaceable"><code>a</code></em></td><td>absolute value</td><td><code class="literal">abs(-17)</code></td><td><code class="literal">17</code></td></tr><tr><td><code class="literal"><code class="function">debug(<em class="replaceable"><code>a</code></em>)</code></code></td><td>same as <em class="replaceable"><code>a</code></em> </td><td>print <em class="replaceable"><code>a</code></em> to <span class="systemitem">stderr</span>,
- and return <em class="replaceable"><code>a</code></em></td><td><code class="literal">debug(5432.1)</code></td><td><code class="literal">5432.1</code></td></tr><tr><td><code class="literal"><code class="function">double(<em class="replaceable"><code>i</code></em>)</code></code></td><td>double</td><td>cast to double</td><td><code class="literal">double(5432)</code></td><td><code class="literal">5432.0</code></td></tr><tr><td><code class="literal"><code class="function">exp(<em class="replaceable"><code>x</code></em>)</code></code></td><td>double</td><td>exponential</td><td><code class="literal">exp(1.0)</code></td><td><code class="literal">2.718281828459045</code></td></tr><tr><td><code class="literal"><code class="function">greatest(<em class="replaceable"><code>a</code></em> [, <em class="replaceable"><code>...</code></em> ] )</code></code></td><td>double if any <em class="replaceable"><code>a</code></em> is double, else integer</td><td>largest value among arguments</td><td><code class="literal">greatest(5, 4, 3, 2)</code></td><td><code class="literal">5</code></td></tr><tr><td><code class="literal"><code class="function">hash(<em class="replaceable"><code>a</code></em> [, <em class="replaceable"><code>seed</code></em> ] )</code></code></td><td>integer</td><td>alias for <code class="literal">hash_murmur2()</code></td><td><code class="literal">hash(10, 5432)</code></td><td><code class="literal">-5817877081768721676</code></td></tr><tr><td><code class="literal"><code class="function">hash_fnv1a(<em class="replaceable"><code>a</code></em> [, <em class="replaceable"><code>seed</code></em> ] )</code></code></td><td>integer</td><td><a class="ulink" href="https://en.wikipedia.org/wiki/Fowler%E2%80%93Noll%E2%80%93Vo_hash_function" target="_top">FNV-1a hash</a></td><td><code class="literal">hash_fnv1a(10, 5432)</code></td><td><code class="literal">-7793829335365542153</code></td></tr><tr><td><code class="literal"><code class="function">hash_murmur2(<em class="replaceable"><code>a</code></em> [, <em class="replaceable"><code>seed</code></em> ] )</code></code></td><td>integer</td><td><a class="ulink" href="https://en.wikipedia.org/wiki/MurmurHash" target="_top">MurmurHash2 hash</a></td><td><code class="literal">hash_murmur2(10, 5432)</code></td><td><code class="literal">-5817877081768721676</code></td></tr><tr><td><code class="literal"><code class="function">int(<em class="replaceable"><code>x</code></em>)</code></code></td><td>integer</td><td>cast to int</td><td><code class="literal">int(5.4 + 3.8)</code></td><td><code class="literal">9</code></td></tr><tr><td><code class="literal"><code class="function">least(<em class="replaceable"><code>a</code></em> [, <em class="replaceable"><code>...</code></em> ] )</code></code></td><td>double if any <em class="replaceable"><code>a</code></em> is double, else integer</td><td>smallest value among arguments</td><td><code class="literal">least(5, 4, 3, 2.1)</code></td><td><code class="literal">2.1</code></td></tr><tr><td><code class="literal"><code class="function">ln(<em class="replaceable"><code>x</code></em>)</code></code></td><td>double</td><td>natural logarithm</td><td><code class="literal">ln(2.718281828459045)</code></td><td><code class="literal">1.0</code></td></tr><tr><td><code class="literal"><code class="function">mod(<em class="replaceable"><code>i</code></em>, <em class="replaceable"><code>j</code></em>)</code></code></td><td>integer</td><td>modulo</td><td><code class="literal">mod(54, 32)</code></td><td><code class="literal">22</code></td></tr><tr><td><code class="literal"><code class="function">pi()</code></code></td><td>double</td><td>value of the constant PI</td><td><code class="literal">pi()</code></td><td><code class="literal">3.14159265358979323846</code></td></tr><tr><td><code class="literal"><code class="function">pow(<em class="replaceable"><code>x</code></em>, <em class="replaceable"><code>y</code></em>)</code>, <code class="function">power(<em class="replaceable"><code>x</code></em>, <em class="replaceable"><code>y</code></em>)</code></code></td><td>double</td><td>exponentiation</td><td><code class="literal">pow(2.0, 10)</code>, <code class="literal">power(2.0, 10)</code></td><td><code class="literal">1024.0</code></td></tr><tr><td><code class="literal"><code class="function">random(<em class="replaceable"><code>lb</code></em>, <em class="replaceable"><code>ub</code></em>)</code></code></td><td>integer</td><td>uniformly-distributed random integer in <code class="literal">[lb, ub]</code></td><td><code class="literal">random(1, 10)</code></td><td>an integer between <code class="literal">1</code> and <code class="literal">10</code></td></tr><tr><td><code class="literal"><code class="function">random_exponential(<em class="replaceable"><code>lb</code></em>, <em class="replaceable"><code>ub</code></em>, <em class="replaceable"><code>parameter</code></em>)</code></code></td><td>integer</td><td>exponentially-distributed random integer in <code class="literal">[lb, ub]</code>,
- see below</td><td><code class="literal">random_exponential(1, 10, 3.0)</code></td><td>an integer between <code class="literal">1</code> and <code class="literal">10</code></td></tr><tr><td><code class="literal"><code class="function">random_gaussian(<em class="replaceable"><code>lb</code></em>, <em class="replaceable"><code>ub</code></em>, <em class="replaceable"><code>parameter</code></em>)</code></code></td><td>integer</td><td>Gaussian-distributed random integer in <code class="literal">[lb, ub]</code>,
- see below</td><td><code class="literal">random_gaussian(1, 10, 2.5)</code></td><td>an integer between <code class="literal">1</code> and <code class="literal">10</code></td></tr><tr><td><code class="literal"><code class="function">random_zipfian(<em class="replaceable"><code>lb</code></em>, <em class="replaceable"><code>ub</code></em>, <em class="replaceable"><code>parameter</code></em>)</code></code></td><td>integer</td><td>Zipfian-distributed random integer in <code class="literal">[lb, ub]</code>,
- see below</td><td><code class="literal">random_zipfian(1, 10, 1.5)</code></td><td>an integer between <code class="literal">1</code> and <code class="literal">10</code></td></tr><tr><td><code class="literal"><code class="function">sqrt(<em class="replaceable"><code>x</code></em>)</code></code></td><td>double</td><td>square root</td><td><code class="literal">sqrt(2.0)</code></td><td><code class="literal">1.414213562</code></td></tr></tbody></table></div></div><br class="table-break" /><p>
- The <code class="literal">random</code> function generates values using a uniform
- distribution, that is all the values are drawn within the specified
- range with equal probability. The <code class="literal">random_exponential</code>,
- <code class="literal">random_gaussian</code> and <code class="literal">random_zipfian</code>
- functions require an additional double parameter which determines the precise
- shape of the distribution.
- </p><div class="itemizedlist"><ul class="itemizedlist" style="list-style-type: disc; "><li class="listitem"><p>
- For an exponential distribution, <em class="replaceable"><code>parameter</code></em>
- controls the distribution by truncating a quickly-decreasing
- exponential distribution at <em class="replaceable"><code>parameter</code></em>, and then
- projecting onto integers between the bounds.
- To be precise, with
- </p><div class="literallayout"><p><br />
- f(x) = exp(-parameter * (x - min) / (max - min + 1)) / (1 - exp(-parameter))<br />
- </p></div><p>
- Then value <em class="replaceable"><code>i</code></em> between <em class="replaceable"><code>min</code></em> and
- <em class="replaceable"><code>max</code></em> inclusive is drawn with probability:
- <code class="literal">f(i) - f(i + 1)</code>.
- </p><p>
- Intuitively, the larger the <em class="replaceable"><code>parameter</code></em>, the more
- frequently values close to <em class="replaceable"><code>min</code></em> are accessed, and the
- less frequently values close to <em class="replaceable"><code>max</code></em> are accessed.
- The closer to 0 <em class="replaceable"><code>parameter</code></em> is, the flatter (more
- uniform) the access distribution.
- A crude approximation of the distribution is that the most frequent 1%
- values in the range, close to <em class="replaceable"><code>min</code></em>, are drawn
- <em class="replaceable"><code>parameter</code></em>% of the time.
- The <em class="replaceable"><code>parameter</code></em> value must be strictly positive.
- </p></li><li class="listitem"><p>
- For a Gaussian distribution, the interval is mapped onto a standard
- normal distribution (the classical bell-shaped Gaussian curve) truncated
- at <code class="literal">-parameter</code> on the left and <code class="literal">+parameter</code>
- on the right.
- Values in the middle of the interval are more likely to be drawn.
- To be precise, if <code class="literal">PHI(x)</code> is the cumulative distribution
- function of the standard normal distribution, with mean <code class="literal">mu</code>
- defined as <code class="literal">(max + min) / 2.0</code>, with
- </p><div class="literallayout"><p><br />
- f(x) = PHI(2.0 * parameter * (x - mu) / (max - min + 1)) /<br />
- (2.0 * PHI(parameter) - 1)<br />
- </p></div><p>
- then value <em class="replaceable"><code>i</code></em> between <em class="replaceable"><code>min</code></em> and
- <em class="replaceable"><code>max</code></em> inclusive is drawn with probability:
- <code class="literal">f(i + 0.5) - f(i - 0.5)</code>.
- Intuitively, the larger the <em class="replaceable"><code>parameter</code></em>, the more
- frequently values close to the middle of the interval are drawn, and the
- less frequently values close to the <em class="replaceable"><code>min</code></em> and
- <em class="replaceable"><code>max</code></em> bounds. About 67% of values are drawn from the
- middle <code class="literal">1.0 / parameter</code>, that is a relative
- <code class="literal">0.5 / parameter</code> around the mean, and 95% in the middle
- <code class="literal">2.0 / parameter</code>, that is a relative
- <code class="literal">1.0 / parameter</code> around the mean; for instance, if
- <em class="replaceable"><code>parameter</code></em> is 4.0, 67% of values are drawn from the
- middle quarter (1.0 / 4.0) of the interval (i.e. from
- <code class="literal">3.0 / 8.0</code> to <code class="literal">5.0 / 8.0</code>) and 95% from
- the middle half (<code class="literal">2.0 / 4.0</code>) of the interval (second and third
- quartiles). The minimum allowed <em class="replaceable"><code>parameter</code></em>
- value is 2.0.
- </p></li><li class="listitem"><p>
- <code class="literal">random_zipfian</code> generates a bounded Zipfian
- distribution.
- <em class="replaceable"><code>parameter</code></em> defines how skewed the distribution
- is. The larger the <em class="replaceable"><code>parameter</code></em>, the more
- frequently values closer to the beginning of the interval are drawn.
- The distribution is such that, assuming the range starts from 1,
- the ratio of the probability of drawing <em class="replaceable"><code>k</code></em>
- versus drawing <em class="replaceable"><code>k+1</code></em> is
- <code class="literal">((<em class="replaceable"><code>k</code></em>+1)/<em class="replaceable"><code>k</code></em>)**<em class="replaceable"><code>parameter</code></em></code>.
- For example, <code class="literal">random_zipfian(1, ..., 2.5)</code> produces
- the value <code class="literal">1</code> about <code class="literal">(2/1)**2.5 =
- 5.66</code> times more frequently than <code class="literal">2</code>, which
- itself is produced <code class="literal">(3/2)**2.5 = 2.76</code> times more
- frequently than <code class="literal">3</code>, and so on.
- </p><p>
- <span class="application">pgbench</span>'s implementation is based on
- "Non-Uniform Random Variate Generation", Luc Devroye, p. 550-551,
- Springer 1986. Due to limitations of that algorithm,
- the <em class="replaceable"><code>parameter</code></em> value is restricted to
- the range [1.001, 1000].
- </p></li></ul></div><p>
- Hash functions <code class="literal">hash</code>, <code class="literal">hash_murmur2</code> and
- <code class="literal">hash_fnv1a</code> accept an input value and an optional seed parameter.
- In case the seed isn't provided the value of <code class="literal">:default_seed</code>
- is used, which is initialized randomly unless set by the command-line
- <code class="literal">-D</code> option. Hash functions can be used to scatter the
- distribution of random functions such as <code class="literal">random_zipfian</code> or
- <code class="literal">random_exponential</code>. For instance, the following pgbench
- script simulates possible real world workload typical for social media and
- blogging platforms where few accounts generate excessive load:
-
- </p><pre class="programlisting">
- \set r random_zipfian(0, 100000000, 1.07)
- \set k abs(hash(:r)) % 1000000
- </pre><p>
-
- In some cases several distinct distributions are needed which don't correlate
- with each other and this is when implicit seed parameter comes in handy:
-
- </p><pre class="programlisting">
- \set k1 abs(hash(:r, :default_seed + 123)) % 1000000
- \set k2 abs(hash(:r, :default_seed + 321)) % 1000000
- </pre><p>
- </p><p>
- As an example, the full definition of the built-in TPC-B-like
- transaction is:
-
- </p><pre class="programlisting">
- \set aid random(1, 100000 * :scale)
- \set bid random(1, 1 * :scale)
- \set tid random(1, 10 * :scale)
- \set delta random(-5000, 5000)
- BEGIN;
- UPDATE pgbench_accounts SET abalance = abalance + :delta WHERE aid = :aid;
- SELECT abalance FROM pgbench_accounts WHERE aid = :aid;
- UPDATE pgbench_tellers SET tbalance = tbalance + :delta WHERE tid = :tid;
- UPDATE pgbench_branches SET bbalance = bbalance + :delta WHERE bid = :bid;
- INSERT INTO pgbench_history (tid, bid, aid, delta, mtime) VALUES (:tid, :bid, :aid, :delta, CURRENT_TIMESTAMP);
- END;
- </pre><p>
-
- This script allows each iteration of the transaction to reference
- different, randomly-chosen rows. (This example also shows why it's
- important for each client session to have its own variables —
- otherwise they'd not be independently touching different rows.)
- </p></div><div class="refsect2" id="id-1.9.4.10.9.6"><h3>Per-Transaction Logging</h3><p>
- With the <code class="option">-l</code> option (but without
- the <code class="option">--aggregate-interval</code> option),
- <span class="application">pgbench</span> writes information about each transaction
- to a log file. The log file will be named
- <code class="filename"><em class="replaceable"><code>prefix</code></em>.<em class="replaceable"><code>nnn</code></em></code>,
- where <em class="replaceable"><code>prefix</code></em> defaults to <code class="literal">pgbench_log</code>, and
- <em class="replaceable"><code>nnn</code></em> is the PID of the
- <span class="application">pgbench</span> process.
- The prefix can be changed by using the <code class="option">--log-prefix</code> option.
- If the <code class="option">-j</code> option is 2 or higher, so that there are multiple
- worker threads, each will have its own log file. The first worker will
- use the same name for its log file as in the standard single worker case.
- The additional log files for the other workers will be named
- <code class="filename"><em class="replaceable"><code>prefix</code></em>.<em class="replaceable"><code>nnn</code></em>.<em class="replaceable"><code>mmm</code></em></code>,
- where <em class="replaceable"><code>mmm</code></em> is a sequential number for each worker starting
- with 1.
- </p><p>
- The format of the log is:
-
- </p><pre class="synopsis">
- <em class="replaceable"><code>client_id</code></em> <em class="replaceable"><code>transaction_no</code></em> <em class="replaceable"><code>time</code></em> <em class="replaceable"><code>script_no</code></em> <em class="replaceable"><code>time_epoch</code></em> <em class="replaceable"><code>time_us</code></em> [<span class="optional"> <em class="replaceable"><code>schedule_lag</code></em> </span>]
- </pre><p>
-
- where
- <em class="replaceable"><code>client_id</code></em> indicates which client session ran the transaction,
- <em class="replaceable"><code>transaction_no</code></em> counts how many transactions have been
- run by that session,
- <em class="replaceable"><code>time</code></em> is the total elapsed transaction time in microseconds,
- <em class="replaceable"><code>script_no</code></em> identifies which script file was used (useful when
- multiple scripts were specified with <code class="option">-f</code> or <code class="option">-b</code>),
- and <em class="replaceable"><code>time_epoch</code></em>/<em class="replaceable"><code>time_us</code></em> are a
- Unix-epoch time stamp and an offset
- in microseconds (suitable for creating an ISO 8601
- time stamp with fractional seconds) showing when
- the transaction completed.
- The <em class="replaceable"><code>schedule_lag</code></em> field is the difference between the
- transaction's scheduled start time, and the time it actually started, in
- microseconds. It is only present when the <code class="option">--rate</code> option is used.
- When both <code class="option">--rate</code> and <code class="option">--latency-limit</code> are used,
- the <em class="replaceable"><code>time</code></em> for a skipped transaction will be reported as
- <code class="literal">skipped</code>.
- </p><p>
- Here is a snippet of a log file generated in a single-client run:
- </p><pre class="screen">
- 0 199 2241 0 1175850568 995598
- 0 200 2465 0 1175850568 998079
- 0 201 2513 0 1175850569 608
- 0 202 2038 0 1175850569 2663
- </pre><p>
-
- Another example with <code class="literal">--rate=100</code>
- and <code class="literal">--latency-limit=5</code> (note the additional
- <em class="replaceable"><code>schedule_lag</code></em> column):
- </p><pre class="screen">
- 0 81 4621 0 1412881037 912698 3005
- 0 82 6173 0 1412881037 914578 4304
- 0 83 skipped 0 1412881037 914578 5217
- 0 83 skipped 0 1412881037 914578 5099
- 0 83 4722 0 1412881037 916203 3108
- 0 84 4142 0 1412881037 918023 2333
- 0 85 2465 0 1412881037 919759 740
- </pre><p>
- In this example, transaction 82 was late, because its latency (6.173 ms) was
- over the 5 ms limit. The next two transactions were skipped, because they
- were already late before they were even started.
- </p><p>
- When running a long test on hardware that can handle a lot of transactions,
- the log files can become very large. The <code class="option">--sampling-rate</code> option
- can be used to log only a random sample of transactions.
- </p></div><div class="refsect2" id="id-1.9.4.10.9.7"><h3>Aggregated Logging</h3><p>
- With the <code class="option">--aggregate-interval</code> option, a different
- format is used for the log files:
-
- </p><pre class="synopsis">
- <em class="replaceable"><code>interval_start</code></em> <em class="replaceable"><code>num_transactions</code></em> <em class="replaceable"><code>sum_latency</code></em> <em class="replaceable"><code>sum_latency_2</code></em> <em class="replaceable"><code>min_latency</code></em> <em class="replaceable"><code>max_latency</code></em> [<span class="optional"> <em class="replaceable"><code>sum_lag</code></em> <em class="replaceable"><code>sum_lag_2</code></em> <em class="replaceable"><code>min_lag</code></em> <em class="replaceable"><code>max_lag</code></em> [<span class="optional"> <em class="replaceable"><code>skipped</code></em> </span>] </span>]
- </pre><p>
-
- where
- <em class="replaceable"><code>interval_start</code></em> is the start of the interval (as a Unix
- epoch time stamp),
- <em class="replaceable"><code>num_transactions</code></em> is the number of transactions
- within the interval,
- <em class="replaceable"><code>sum_latency</code></em> is the sum of the transaction
- latencies within the interval,
- <em class="replaceable"><code>sum_latency_2</code></em> is the sum of squares of the
- transaction latencies within the interval,
- <em class="replaceable"><code>min_latency</code></em> is the minimum latency within the interval,
- and
- <em class="replaceable"><code>max_latency</code></em> is the maximum latency within the interval.
- The next fields,
- <em class="replaceable"><code>sum_lag</code></em>, <em class="replaceable"><code>sum_lag_2</code></em>, <em class="replaceable"><code>min_lag</code></em>,
- and <em class="replaceable"><code>max_lag</code></em>, are only present if the <code class="option">--rate</code>
- option is used.
- They provide statistics about the time each transaction had to wait for the
- previous one to finish, i.e. the difference between each transaction's
- scheduled start time and the time it actually started.
- The very last field, <em class="replaceable"><code>skipped</code></em>,
- is only present if the <code class="option">--latency-limit</code> option is used, too.
- It counts the number of transactions skipped because they would have
- started too late.
- Each transaction is counted in the interval when it was committed.
- </p><p>
- Here is some example output:
- </p><pre class="screen">
- 1345828501 5601 1542744 483552416 61 2573
- 1345828503 7884 1979812 565806736 60 1479
- 1345828505 7208 1979422 567277552 59 1391
- 1345828507 7685 1980268 569784714 60 1398
- 1345828509 7073 1979779 573489941 236 1411
- </pre><p>
- Notice that while the plain (unaggregated) log file shows which script
- was used for each transaction, the aggregated log does not. Therefore if
- you need per-script data, you need to aggregate the data on your own.
- </p></div><div class="refsect2" id="id-1.9.4.10.9.8"><h3>Per-Statement Latencies</h3><p>
- With the <code class="option">-r</code> option, <span class="application">pgbench</span> collects
- the elapsed transaction time of each statement executed by every
- client. It then reports an average of those values, referred to
- as the latency for each statement, after the benchmark has finished.
- </p><p>
- For the default script, the output will look similar to this:
- </p><pre class="screen">
- starting vacuum...end.
- transaction type: <builtin: TPC-B (sort of)>
- scaling factor: 1
- query mode: simple
- number of clients: 10
- number of threads: 1
- number of transactions per client: 1000
- number of transactions actually processed: 10000/10000
- latency average = 15.844 ms
- latency stddev = 2.715 ms
- tps = 618.764555 (including connections establishing)
- tps = 622.977698 (excluding connections establishing)
- statement latencies in milliseconds:
- 0.002 \set aid random(1, 100000 * :scale)
- 0.005 \set bid random(1, 1 * :scale)
- 0.002 \set tid random(1, 10 * :scale)
- 0.001 \set delta random(-5000, 5000)
- 0.326 BEGIN;
- 0.603 UPDATE pgbench_accounts SET abalance = abalance + :delta WHERE aid = :aid;
- 0.454 SELECT abalance FROM pgbench_accounts WHERE aid = :aid;
- 5.528 UPDATE pgbench_tellers SET tbalance = tbalance + :delta WHERE tid = :tid;
- 7.335 UPDATE pgbench_branches SET bbalance = bbalance + :delta WHERE bid = :bid;
- 0.371 INSERT INTO pgbench_history (tid, bid, aid, delta, mtime) VALUES (:tid, :bid, :aid, :delta, CURRENT_TIMESTAMP);
- 1.212 END;
- </pre><p>
- </p><p>
- If multiple script files are specified, the averages are reported
- separately for each script file.
- </p><p>
- Note that collecting the additional timing information needed for
- per-statement latency computation adds some overhead. This will slow
- average execution speed and lower the computed TPS. The amount
- of slowdown varies significantly depending on platform and hardware.
- Comparing average TPS values with and without latency reporting enabled
- is a good way to measure if the timing overhead is significant.
- </p></div><div class="refsect2" id="id-1.9.4.10.9.9"><h3>Good Practices</h3><p>
- It is very easy to use <span class="application">pgbench</span> to produce completely
- meaningless numbers. Here are some guidelines to help you get useful
- results.
- </p><p>
- In the first place, <span class="emphasis"><em>never</em></span> believe any test that runs
- for only a few seconds. Use the <code class="option">-t</code> or <code class="option">-T</code> option
- to make the run last at least a few minutes, so as to average out noise.
- In some cases you could need hours to get numbers that are reproducible.
- It's a good idea to try the test run a few times, to find out if your
- numbers are reproducible or not.
- </p><p>
- For the default TPC-B-like test scenario, the initialization scale factor
- (<code class="option">-s</code>) should be at least as large as the largest number of
- clients you intend to test (<code class="option">-c</code>); else you'll mostly be
- measuring update contention. There are only <code class="option">-s</code> rows in
- the <code class="structname">pgbench_branches</code> table, and every transaction wants to
- update one of them, so <code class="option">-c</code> values in excess of <code class="option">-s</code>
- will undoubtedly result in lots of transactions blocked waiting for
- other transactions.
- </p><p>
- The default test scenario is also quite sensitive to how long it's been
- since the tables were initialized: accumulation of dead rows and dead space
- in the tables changes the results. To understand the results you must keep
- track of the total number of updates and when vacuuming happens. If
- autovacuum is enabled it can result in unpredictable changes in measured
- performance.
- </p><p>
- A limitation of <span class="application">pgbench</span> is that it can itself become
- the bottleneck when trying to test a large number of client sessions.
- This can be alleviated by running <span class="application">pgbench</span> on a different
- machine from the database server, although low network latency will be
- essential. It might even be useful to run several <span class="application">pgbench</span>
- instances concurrently, on several client machines, against the same
- database server.
- </p></div><div class="refsect2" id="id-1.9.4.10.9.10"><h3>Security</h3><p>
- If untrusted users have access to a database that has not adopted a
- <a class="link" href="ddl-schemas.html#DDL-SCHEMAS-PATTERNS" title="5.9.6. Usage Patterns">secure schema usage pattern</a>,
- do not run <span class="application">pgbench</span> in that
- database. <span class="application">pgbench</span> uses unqualified names and
- does not manipulate the search path.
- </p></div></div></div><div class="navfooter"><hr /><table width="100%" summary="Navigation footer"><tr><td width="40%" align="left"><a accesskey="p" href="app-pgbasebackup.html">Prev</a> </td><td width="20%" align="center"><a accesskey="u" href="reference-client.html">Up</a></td><td width="40%" align="right"> <a accesskey="n" href="app-pgconfig.html">Next</a></td></tr><tr><td width="40%" align="left" valign="top">pg_basebackup </td><td width="20%" align="center"><a accesskey="h" href="index.html">Home</a></td><td width="40%" align="right" valign="top"> pg_config</td></tr></table></div></body></html>
|