有時候,可能有移除欄位的需要。但是移除欄位時,明明有這多的資料,移除欄位怎麼快速會完成?
在 PostgreSQL 裡面,ALTER TABLE 表格 DROP COLUMN 欄位; 所進行的動作,其實只是把欄位標記成不能使用,並沒有把資料從表格檔案裡面移除。
這麼一來,在刪除欄位之後,表格所佔空間並不會減低,而需要進行 VACUUM FULL 表格; 指令,才能夠把表格大小重新調整回來。
要是之前有刪一些欄位,但是忘記是哪個表格了要怎麼辦?
我們可以透過查找 pg_attribute 來找到被「移除」的欄位
edb=# select attname AS "Dropped Columns" from pg_attribute where attisdropped = true; Dropped Columns ------------------------------ ........pg.dropped.1........ ........pg.dropped.1........ ........pg.dropped.1........ ........pg.dropped.2........ ........pg.dropped.3........ (5 rows)
但是顯示結果看來怪怪的,出現很像系統欄位的東西~
直覺想到,應該可以用欄位比對,找出所在的表格名稱才對
edb=# select col.table_schema || '.' || col.table_name AS "Relation", att.attname AS "Dropped Columns" from pg_attribute att, information_schema.columns col where att.attname=col.column_name and att.attisdropped = true; Relation | Dropped Columns ----------+----------------- (0 rows)
結果沒找到半個表格 . . .
其實在直接查找 pg_attribute 系統表,可以看到欄位被「移除」,欄位仍在,但是欄位名字其實已經被更動,就是上面看起來很像系統物件的 pg.dropped ,所以比對欄位名稱會找不出來。
但是表格不會更動,所以應該是查詢表格才對,把上面的指令調整一下:
edb=# select rl.relnamespace::regnamespace || '.'|| rl.relname AS "Relation", att.attname AS "Dropped Columns" from pg_attribute att, pg_class rl where att.attrelid = rl.oid and att.attisdropped = true; Relation | Dropped Columns ----------------------------+------------------------------ enterprisedb.test02 | ........pg.dropped.1........ enterprisedb.test03_201701 | ........pg.dropped.1........ enterprisedb.test03 | ........pg.dropped.1........ enterprisedb.test_tab | ........pg.dropped.2........ enterprisedb.testt | ........pg.dropped.3........ (5 rows)
成功找出來了!
接著就是要安排時間進行 VACUUM FULL,重新謄寫一次表格檔案了(會有最大的 Table Lock,要注意)。如果真的覺得這 Lock 有點麻煩,可能可以去研究 pg_repack 工具~
參考資料
EDB 公司的客服團隊~訂閱諮詢服務
沒有留言:
張貼留言