Контрольные суммы

Создадим таблицу:

=> CREATE DATABASE wal_tuning;
CREATE DATABASE
=> \c wal_tuning
You are now connected to database "wal_tuning" as user "postgres".
=> CREATE TABLE t(id integer);
CREATE TABLE
=> INSERT INTO t VALUES (1),(2),(3);
INSERT 0 3

Вот файл, в котором находятся данные:

=> SELECT pg_relation_filepath('t');
 pg_relation_filepath 
----------------------
 base/24817/24818
(1 row)


Остановим сервер и поменяем несколько байтов в странице (сотрем из заголовка LSN последней журнальной записи).

=> \q
postgres$ pg_ctl -w -D /usr/local/pgsql/data stop
waiting for server to shut down.... done
server stopped
postgres$ dd if=/dev/zero of=/usr/local/pgsql/data/base/24817/24818 oflag=dsync conv=notrunc bs=1 count=8
8+0 records in
8+0 records out
8 bytes copied, 0,00405913 s, 2,0 kB/s

Можно было бы и не останавливать сервер. Достаточно, чтобы:


Теперь запускаем сервер.

postgres$ pg_ctl -w -l /home/postgres/logfile -D /usr/local/pgsql/data start
waiting for server to start.... done
server started
student$ psql wal_tuning

Попробуем прочитать таблицу:

=> SELECT * FROM t;
WARNING:  page verification failed, calculated checksum 3919 but expected 35129
ERROR:  invalid page in block 0 of relation base/24817/24818

Параметр ignore_checksum_failure позволяет попробовать прочитать таблицу с риском получить искаженные данные (например, если нет резервной копии):

=> SET ignore_checksum_failure = on;
SET
=> SELECT * FROM t;
WARNING:  page verification failed, calculated checksum 3919 but expected 35129
 id 
----
  1
  2
  3
(3 rows)


Влияние синхронной фиксации на производительность

Режим, включенный по умолчанию, - синхронная фиксация.

=> SHOW synchronous_commit;
 synchronous_commit 
--------------------
 on
(1 row)

Запустим простой тест производительности с помощью утилиты pgbench. Для этого сначала инициализируем необходимые таблицы.

student$ pgbench -i wal_tuning
NOTICE:  table "pgbench_history" does not exist, skipping
NOTICE:  table "pgbench_tellers" does not exist, skipping
NOTICE:  table "pgbench_accounts" does not exist, skipping
NOTICE:  table "pgbench_branches" does not exist, skipping
creating tables...
100000 of 100000 tuples (100%) done (elapsed 0.13 s, remaining 0.00 s)
vacuum...
set primary keys...
done.

Запускаем тест на 10 секунд.

student$ pgbench -P 1 -T 10 wal_tuning
starting vacuum...end.
progress: 1.0 s, 921.9 tps, lat 1.082 ms stddev 0.195
progress: 2.0 s, 941.0 tps, lat 1.062 ms stddev 0.128
progress: 3.0 s, 915.0 tps, lat 1.094 ms stddev 0.167
progress: 4.0 s, 910.1 tps, lat 1.099 ms stddev 0.744
progress: 5.0 s, 949.0 tps, lat 1.053 ms stddev 0.114
progress: 6.0 s, 881.9 tps, lat 1.134 ms stddev 0.230
progress: 7.0 s, 916.0 tps, lat 1.092 ms stddev 0.198
progress: 8.0 s, 867.0 tps, lat 1.154 ms stddev 0.249
progress: 9.0 s, 868.1 tps, lat 1.152 ms stddev 0.684
progress: 10.0 s, 721.0 tps, lat 1.387 ms stddev 1.777
transaction type: <builtin: TPC-B (sort of)>
scaling factor: 1
query mode: simple
number of clients: 1
number of threads: 1
duration: 10 s
number of transactions actually processed: 8892
latency average = 1.124 ms
latency stddev = 0.625 ms
tps = 889.156732 (including connections establishing)
tps = 889.416097 (excluding connections establishing)

В результатах нас интересует число транзакций или скорость (tps).


Теперь установим асинхронный режим.

=> ALTER SYSTEM SET synchronous_commit = off;
ALTER SYSTEM
=> SELECT pg_reload_conf();
 pg_reload_conf 
----------------
 t
(1 row)


Снова запускаем тест.

student$ pgbench -P 1 -T 10 wal_tuning
starting vacuum...end.
progress: 1.0 s, 1729.9 tps, lat 0.577 ms stddev 0.072
progress: 2.0 s, 1728.1 tps, lat 0.579 ms stddev 0.080
progress: 3.0 s, 1754.9 tps, lat 0.570 ms stddev 0.063
progress: 4.0 s, 1738.0 tps, lat 0.575 ms stddev 0.073
progress: 5.0 s, 1740.1 tps, lat 0.575 ms stddev 0.069
progress: 6.0 s, 1738.9 tps, lat 0.575 ms stddev 0.069
progress: 7.0 s, 1746.0 tps, lat 0.573 ms stddev 0.062
progress: 8.0 s, 1731.0 tps, lat 0.578 ms stddev 0.073
progress: 9.0 s, 1742.0 tps, lat 0.574 ms stddev 0.068
progress: 10.0 s, 1748.9 tps, lat 0.572 ms stddev 0.064
transaction type: <builtin: TPC-B (sort of)>
scaling factor: 1
query mode: simple
number of clients: 1
number of threads: 1
duration: 10 s
number of transactions actually processed: 17399
latency average = 0.575 ms
latency stddev = 0.069 ms
tps = 1739.800355 (including connections establishing)
tps = 1740.158900 (excluding connections establishing)

Разумеется, на реальной системе соотношение может быть другим, но видно, что в асинхронном режиме производительность выше.

Конец демонстрации.