Подтвердить что ты не робот

PostgreSQL бездействия в диагностике транзакций и чтении pg_locks

Настройка: несколько веб-серверов, работающие с mod_wsgi, Apache и pgbouncer, которые подключаются к совместно используемой базе данных, работающей с Postgres 8.3.6. Приложение запускает Django.

Что мы видим: запросы "бездействовать в транзакции" в БД, которые долгое время выходят на улицу. Чтобы увидеть их, я запустил что-то вроде этого:

SELECT query_start, procpid, client_addr, current_query FROM pg_stat_activity
WHERE query_start < NOW() - interval '5 minutes';

Большинство результатов, конечно же, - это просто IDLE-соединения, которые pgbouncer поддерживает для использования, но иногда это старые запросы IDLE в транзакции. Я понимаю, что это означает, что есть транзакция запроса, которая ждет чего-то или что-то, что имеет BEGIN, но не достигло COMMIT или ROLLBACK.

Следующим шагом было попытаться использовать pg_locks, чтобы определить, что ожидает процесс:

select pg_class.relname, pg_locks.transactionid, pg_locks.mode,
       pg_locks.granted as "g", pg_stat_activity.current_query,
       pg_stat_activity.query_start,
       age(now(),pg_stat_activity.query_start) as "age",
       pg_stat_activity.procpid 
from pg_stat_activity,pg_locks
left outer join pg_class on (pg_locks.relation = pg_class.oid)  
where pg_locks.pid=pg_stat_activity.procpid
and pg_stat_activity.procpid = <AN IDLE TRANSACTION PROCESS>
order by query_start;

Много раз результат, который я получаю, выглядит так:

 relname | transactionid |      mode       | g |     current_query     |         query_start          |       age       |  client_addr   | procpid 
---------+---------------+-----------------+---+-----------------------+------------------------------+-----------------+----------------+---------
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | ExclusiveLock   | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
         |               | AccessShareLock | t | <IDLE> in transaction | 2010-07-22 15:33:11.48136-04 | 00:23:35.029045 | 192.168.100.99 |    1991
(10 rows)

Я не уверен, как это прочитать (я думаю, это связано с непониманием pg_locks). Там нет переименования, так он говорит, что он ничего не ждет? Я думал, что если бы он был "правдой", у него был замок. Поскольку все эти результаты предоставлены, pg_locks показывает мне блокировки, которые у него есть, а не то, что они ждут?

Сейчас я "исправляю" это, перезапуская Apache, который, кажется, трясет транзакции, но, очевидно, это не настоящее решение. Я ищу Postgres, чтобы дать мне место, где искать, чтобы понять это, тем более, что Django должен автоматически управлять своими подключениями и транзакциями.

4b9b3361

Ответ 1

Для Django, в частности, этот элемент описывает, почему вы видите эту проблему:

Резьбовая задача Django...

Я говорю "конкретно" здесь, потому что настоящая проблема заключается в том, что веб-фреймворки/драйверы/ORM работают все время в режиме на основе транзакций (а иногда и вызывают откат после каждого запроса SELECT Freakin), когда они действительно должны работать в Auto-Commit и обработку транзакций только по мере необходимости. Модуль персистентности Apache:: Sessions PostgreSQL был катастрофой (по крайней мере несколько лет назад), поскольку он закрывал транзакции только тогда, когда был собран мусор. Хлоп!