Tôi có Postgres 9.2 DB trong đó một bảng nhất định có rất nhiều hàng chết không thể phá hủy:
# SELECT * FROM public.pgstattuple('mytable');
table_len | tuple_count | tuple_len | tuple_percent | dead_tuple_count | dead_tuple_len | dead_tuple_percent | free_space | free_percent
------------+-------------+-----------+---------------+------------------+----------------+--------------------+------------+--------------
2850512896 | 283439 | 100900882 | 3.54 | 2537195 | 2666909495 | 93.56 | 50480156 | 1.77
(1 row)
Hút bụi thông thường cũng cho thấy rất nhiều hàng chết không thể di chuyển:
# VACUUM VERBOSE mytable;
[...]
INFO: "mytable": found 0 removable, 2404332 nonremovable row versions in 309938 out of 316307 pages
DETAIL: 2298005 dead row versions cannot be removed yet.
There were 0 unused item pointers.
0 pages are entirely empty.
CPU 1.90s/2.05u sec elapsed 16.79 sec.
[...]
Bảng chỉ có khoảng 300.000 hàng dữ liệu thực tế, nhưng 2,3 triệu hàng chết (và điều này dường như làm cho các truy vấn nhất định rất chậm).
Theo SELECT * FROM pg_stat_activity where xact_start is not null and datname = 'mydb' order by xact_start;
đó không có giao dịch cũ truy cập cơ sở dữ liệu. Các giao dịch cũ nhất đã cũ vài phút và chưa sửa đổi bất cứ điều gì trên bàn.
Tôi cũng đã kiểm tra select * from pg_prepared_xacts
(để kiểm tra các giao dịch đã chuẩn bị) và select * from pg_stat_replication
(để kiểm tra các bản sao đang chờ xử lý), cả hai đều trống.
Có rất nhiều phần chèn, cập nhật và xóa được thực hiện trên bảng đó, vì vậy tôi có thể hiểu rằng có rất nhiều hàng chết đang được tạo. Nhưng tại sao chúng không bị xóa bởi lệnh VACUUM?