我们正在运行PostgreSQL版本9.1,之前我们在一个表中有超过10亿行,并且已被删除。然而,看起来\l+
命令仍然不准确地报告实际的数据库大小(它报告568GB但实际上它远远低于)。
568GB错误的证据是单个表的大小计数没有加起来,正如你所看到的,前20个关系的大小为4292MB,其余的985关系都远低于10MB。实际上所有这些都加起来大约不到6GB。
任何想法为什么PostgreSQL如此臃肿?如果确认,我怎么能脱离?我对VACUUM
不是很熟悉,我需要做什么?如果是这样,怎么样?
非常欣赏它。
pmlex=# \l+
List of databases
Name | Owner | Encoding | Collate | Ctype | Access privileges | Size | Tablespace | Description
-----------------+----------+----------+-------------+-------------+-----------------------+---------+------------+--------------------------------------------
pmlex | pmlex | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | 568 GB | pg_default |
pmlex_analytics | pmlex | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | 433 MB | pg_default |
postgres | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | | 5945 kB | pg_default | default administrative connection database
template0 | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | =c/postgres +| 5841 kB | pg_default | unmodifiable empty database
| | | | | postgres=CTc/postgres | | |
template1 | postgres | UTF8 | en_US.UTF-8 | en_US.UTF-8 | =c/postgres +| 5841 kB | pg_default | default template for new databases
| | | | | postgres=CTc/postgres | | |
(5 rows)
pmlex=# SELECT nspname || '.' || relname AS "relation",
pmlex-# pg_size_pretty(pg_relation_size(C.oid)) AS "size"
pmlex-# FROM pg_class C
pmlex-# LEFT JOIN pg_namespace N ON (N.oid = C.relnamespace)
pmlex-# WHERE nspname NOT IN ('pg_catalog', 'information_schema')
pmlex-# ORDER BY pg_relation_size(C.oid) DESC;
relation | size
-------------------------------------+---------
public.page_page | 1289 MB
public.page_pageimagehistory | 570 MB
pg_toast.pg_toast_158103 | 273 MB
public.celery_taskmeta_task_id_key | 233 MB
public.page_page_unique_hash_uniq | 140 MB
public.page_page_ad_text_id | 136 MB
public.page_page_kn_result_id | 125 MB
public.page_page_seo_term_id | 124 MB
public.page_page_kn_search_id | 124 MB
public.page_page_direct_network_tag | 124 MB
public.page_page_traffic_source_id | 123 MB
public.page_page_active | 123 MB
public.page_page_is_referrer | 123 MB
public.page_page_category_id | 123 MB
public.page_page_host_id | 123 MB
public.page_page_serp_id | 121 MB
public.page_page_domain_id | 120 MB
public.celery_taskmeta_pkey | 106 MB
public.page_pagerenderhistory | 102 MB
public.page_page_campaign_id | 89 MB
...
...
...
pg_toast.pg_toast_4354379 | 0 bytes
(1005 rows)
您的选择包括:
1)。确保启用autovacuum并积极设置。
2)。正如我在前面的评论中提到的那样重新创建表(create-table-as-select + truncate + reload the original table)。
3)。如果您能够锁定该表(独占锁定),则在表上运行CLUSTER。
4)。 VACUUM FULL,虽然CLUSTER更有效率和推荐。
5)。运行一次简单的VACUUM ANALYZE几次并保持原样,以便在新数据进入时最终填满空间。
6)。通过pg_dump转储并重新加载表
7)。 pg_repack(虽然我没有在生产中使用它)
如果使用pg_total_relation_size而不是pg_relation_size,它可能会有所不同
pg_relation_size没有给出表的总大小,请参阅
https://www.postgresql.org/docs/9.5/static/functions-admin.html#FUNCTIONS-ADMIN-DBSIZE